{"record":{"id":"f39c6fa8fe003bbf","repo":"remotion-dev/remotion","slug":"the-parameter-passed-into-continuerender-must-be","errorCode":null,"errorMessage":"The parameter passed into continueRender() must be the return value of delayRender() which is a number. Got: ${JSON.stringify(handle)}","messagePattern":"The parameter passed into continueRender\\(\\) must be the return value of delayRender\\(\\) which is a number\\. Got: (.+?)","errorType":"exception","errorClass":"TypeError","httpStatus":null,"severity":"error","filePath":"packages/core/src/delay-render.ts","lineNumber":160,"sourceCode":"\thandle: number;\n\tenvironment: RemotionEnvironment;\n\tlogLevel: LogLevel;\n};\n\nexport const continueRenderInternal = ({\n\tscope,\n\thandle,\n\tenvironment,\n\tlogLevel,\n}: ContinueRenderInternalOptions): void => {\n\tif (typeof handle === 'undefined') {\n\t\tthrow new TypeError(\n\t\t\t'The continueRender() method must be called with a parameter that is the return value of delayRender(). No value was passed.',\n\t\t);\n\t}\n\n\tif (typeof handle !== 'number') {\n\t\tthrow new TypeError(\n\t\t\t'The parameter passed into continueRender() must be the return value of delayRender() which is a number. Got: ' +\n\t\t\t\tJSON.stringify(handle),\n\t\t);\n\t}\n\n\tconst handleExists = scope.remotion_delayRenderHandles.includes(handle);\n\tconst timeoutEntry = scope.remotion_delayRenderTimeouts[handle];\n\tif (handleExists && environment.isRendering && timeoutEntry) {\n\t\tconst {label, startTime, timeout} = timeoutEntry;\n\t\tclearTimeout(timeout);\n\t\tconst message = [\n\t\t\tlabel ? `\"${label}\"` : 'A handle',\n\t\t\tDELAY_RENDER_CLEAR_TOKEN,\n\t\t\t`${Date.now() - startTime}ms`,\n\t\t]\n\t\t\t.filter(truthy)\n\t\t\t.join(' ');\n\t\tLog.verbose({logLevel, tag: 'delayRender()'}, message);","sourceCodeStart":142,"sourceCodeEnd":178,"githubUrl":"https://github.com/remotion-dev/remotion/blob/78fe4bb3fdb5a2cd68724393d63cb223db333fa7/packages/core/src/delay-render.ts#L142-L178","documentation":"continueRender() validates that its argument is the number returned by delayRender() (a Math.random() float). Passing a string, object, or other non-number is rejected because the handle is used to look up the matching timeout entry; a non-number can never match and indicates a logic error (e.g. passing a label or an options object by mistake).","triggerScenarios":"Calling continueRender('load') (passing the label), continueRender({handle}), continueRender(event), or any non-numeric value. Often the result of confusing the label string with the handle.","commonSituations":"Swapping label and handle in call order; storing the handle in state that coerces it to a string; passing an event or DOM node by accident.","solutions":["Pass exactly the value returned by delayRender(): continueRender(handle).","Keep the handle in a variable/ref typed as number to avoid coercion.","Double-check you are not passing the label or an options object."],"exampleFix":"// before\nconst label = 'load';\ndelayRender(label);\nfetchData().then(() => continueRender(label)); // wrong: string\n\n// after\nconst handle = delayRender('load');\nfetchData().then(() => continueRender(handle));","handlingStrategy":"validation","validationCode":"if (typeof handle !== 'number') {\n  throw new TypeError('continueRender requires the delayRender handle');\n}\ncontinueRender(handle);","typeGuard":"const isDelayHandle = (h: unknown): h is number =>\n  typeof h === 'number' && Number.isFinite(h);","tryCatchPattern":null,"preventionTips":["Store the handle as a number; avoid coercing through string state.","Never pass the label or options object to continueRender.","Lint for continueRender called with non-identifier arguments."],"tags":["rendering","validation","delay-render","typescript"],"backgroundTag":null,"analyzedSha":"78fe4bb3fdb5a2cd68724393d63cb223db333fa7","analyzedAt":"2026-08-12T17:18:50.444Z","schemaVersion":2},"datasetVersion":"2026-08-12T23:17:12.415Z"}