{"record":{"id":"ca474508fff232de","repo":"gitbutlerapp/gitbutler","slug":"argument-must-be-an-integer-that-fits-in-isize","errorCode":null,"errorMessage":"argument '{}' must be an integer that fits in isize","messagePattern":"argument '(.+?)' must be an integer that fits in isize","errorType":"validation","errorClass":"napi::Error","httpStatus":null,"severity":"error","filePath":"crates/but-api-macros/src/lib.rs","lineNumber":1672,"sourceCode":"                        // Type needs remapping (e.g., usize → i64)\n                        params.push(quote! { #ident: #napi_ty });\n                        names.push(ident.to_string());\n                        let arg_name = ident.to_string();\n                        let conversion = match type_name.as_deref() {\n                            Some(\"usize\") => quote! {\n                                let #ident: usize = ::std::convert::TryFrom::try_from(#ident).map_err(|_| {\n                                    napi::Error::new(\n                                        napi::Status::InvalidArg,\n                                        format!(\n                                            \"argument '{}' must be a non-negative integer that fits in usize\",\n                                            #arg_name\n                                        ),\n                                    )\n                                })?;\n                            },\n                            Some(\"isize\") => quote! {\n                                let #ident: isize = ::std::convert::TryFrom::try_from(#ident).map_err(|_| {\n                                    napi::Error::new(\n                                        napi::Status::InvalidArg,\n                                        format!(\n                                            \"argument '{}' must be an integer that fits in isize\",\n                                            #arg_name\n                                        ),\n                                    )\n                                })?;\n                            },\n                            _ => quote! {},\n                        };\n                        conversions.push(conversion);\n                        call_arg_idents.push(quote! { #ident });\n                    } else if is_simple_napi_type(base_ty) {\n                        // Simple types (String, bool, numbers) can be passed directly\n                        params.push(quote! { #ident: #ty });\n                        names.push(ident.to_string());\n                        call_arg_idents.push(quote! { #ident });\n                    } else {","sourceCodeStart":1654,"sourceCodeEnd":1690,"githubUrl":"https://github.com/gitbutlerapp/gitbutler/blob/58e5313667b857ef39a730e380af31816a7b1768/crates/but-api-macros/src/lib.rs#L1654-L1690","documentation":"Same mechanism as the usize case: the macro converts the incoming napi integer into Rust isize via TryFrom and fails when the value doesn't fit in isize (larger than isize::MAX on the platform, typically only from huge JS numbers).","triggerScenarios":"Calling a generated but_api NAPI function with an isize-remapped parameter receiving a value beyond isize::MAX (e.g. a JS Number larger than ~9.2e18) or a non-integer.","commonSituations":"Passing an unvalidated timestamp/ID from JS where a float or oversized Number (e.g. from Date.now() arithmetic or a concatenated ID) exceeds isize range.","solutions":["Validate the number fits within Number.MIN_SAFE_INTEGER..Number.MAX_SAFE_INTEGER and is an integer before calling","Convert BigInt values down to safe Numbers only when actually in range","Check where the oversized number originates (IDs concatenated as numbers are a common cause)"],"exampleFix":"// before\napi.seek(2 ** 63)  // exceeds isize\n// after\napi.seek(Number.MAX_SAFE_INTEGER)","handlingStrategy":"validation","validationCode":"const fitsIsize = (n) => Number.isInteger(n) && Math.abs(n) <= Number.MAX_SAFE_INTEGER;","typeGuard":"const fitsIsize = (v: unknown): v is number => typeof v === 'number' && Number.isInteger(v) && v <= Number.MAX_SAFE_INTEGER;","tryCatchPattern":"try { api.call(n); } catch (e) { if (/fits in isize/.test(e.message)) console.error('number too large:', n); throw e; }","preventionTips":["Keep numeric IDs as strings/BigInt in JS, converting only at API boundaries","Guard against Number overflow from arithmetic on timestamps","Run lint rules discouraging unvalidated large numeric literals"],"tags":["napi","isize","integer-overflow","invalid-argument"],"backgroundTag":"value-out-of-range","analyzedSha":"58e5313667b857ef39a730e380af31816a7b1768","analyzedAt":"2026-09-18T06:50:32.052Z","contentChangedAt":"2026-09-18T06:50:32.052Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}