{"record":{"id":"03fab41ad3b6d8f4","repo":"remotion-dev/remotion","slug":"invalid-lut-content-expected-expectedrows-color-rows-for-lut","errorCode":null,"errorMessage":"Invalid LUT content: expected ${expectedRows} color rows for LUT_3D_SIZE ${size}, but got ${dataRows}","messagePattern":"Invalid LUT content: expected (.+?) color rows for LUT_3D_SIZE (.+?), but got (.+?)","errorType":"validation","errorClass":"TypeError","httpStatus":null,"severity":"error","filePath":"packages/effects/src/lut/parse-cube-lut.ts","lineNumber":200,"sourceCode":"\t\t\t);\n\t\t}\n\t}\n\n\tif (size === null) {\n\t\tthrow new TypeError('Invalid LUT content: LUT_3D_SIZE is missing');\n\t}\n\n\tfor (let channel = 0; channel < 3; channel++) {\n\t\tif (domainMin[channel] >= domainMax[channel]) {\n\t\t\tthrow new TypeError(\n\t\t\t\t`Invalid LUT content: DOMAIN_MIN must be smaller than DOMAIN_MAX for every channel`,\n\t\t\t);\n\t\t}\n\t}\n\n\tconst expectedRows = size ** 3;\n\tif (dataRows !== expectedRows) {\n\t\tthrow new TypeError(\n\t\t\t`Invalid LUT content: expected ${expectedRows} color rows for LUT_3D_SIZE ${size}, but got ${dataRows}`,\n\t\t);\n\t}\n\n\tconst data = new Float32Array(expectedRows * 4);\n\tlet dataIndex = 0;\n\n\tfor (let index = 0; index < lines.length; index++) {\n\t\tconst line = stripComment(lines[index]).trim();\n\t\tif (line.length === 0) {\n\t\t\tcontinue;\n\t\t}\n\n\t\tconst [keyword, ...values] = line.split(/\\s+/);\n\t\tif (HEADER_DIRECTIVES.has(keyword)) {\n\t\t\tcontinue;\n\t\t}\n","sourceCodeStart":182,"sourceCodeEnd":218,"githubUrl":"https://github.com/remotion-dev/remotion/blob/46a3a6bf13ca367376ff18bbb06dae2e87e0d068/packages/effects/src/lut/parse-cube-lut.ts#L182-L218","documentation":"parseCubeLut() counts non-header color data rows and requires exactly size^3 rows for the declared LUT_3D_SIZE. If the number of data rows differs (too few or too many), the file is inconsistent with its declared size and a TypeError is thrown naming expected vs actual row counts.","triggerScenarios":"Calling parseCubeLut(content) on a truncated .cube file (download cut off), a file where LUT_3D_SIZE was edited without regenerating the data table (e.g. says 33 but contains 17^3=4913 rows), extra garbage lines parsed as data rows, or rows removed/added by hand-editing.","commonSituations":"Incomplete uploads/downloads, converting a smaller LUT by only editing the size header, files that mix CRLF/LF or contain stray tokens miscounted as data, and LUTs from tools writing fewer rows than declared.","solutions":["Compare the reported got/expected counts: fix LUT_3D_SIZE to match the actual number of color rows, or regenerate the LUT with the correct size","Re-download/re-export the LUT — truncation is the most common cause when got < expected","Remove trailing junk lines or duplicated rows so exactly size^3 data rows remain","Check the file size math: each row is one line of 3 numbers; a 33-size LUT must have 35937 data lines"],"exampleFix":"// before (.cube header mismatch)\nLUT_3D_SIZE 33\n// ...only 4913 data rows (a 17-size cube)\n// after\nLUT_3D_SIZE 17\n// (or regenerate the table with 35937 rows for size 33)","handlingStrategy":"validation","validationCode":"const lines = content.split(/\\r?\\n/)\n  .map((l) => l.split('#')[0].trim())\n  .filter((l) => l.length > 0);\nconst sizeLine = lines.find((l) => /^LUT_3D_SIZE\\s+\\d+$/.test(l));\nconst size = sizeLine ? Number(sizeLine.split(/\\s+/)[1]) : null;\nconst isData = (l: string) => /^[\\d.eE+-]+\\s+[\\d.eE+-]+\\s+[\\d.eE+-]+$/.test(l);\nif (size !== null) {\n  const dataRows = lines.filter(isData).length;\n  if (dataRows !== size ** 3) throw new Error(`Expected ${size ** 3} rows, found ${dataRows}`);\n}","typeGuard":null,"tryCatchPattern":"try {\n  lut = parseCubeLut(content);\n} catch (e) {\n  if (e instanceof TypeError && /color rows for LUT_3D_SIZE/.test(e.message)) {\n    // re-download or regenerate the LUT; message states expected vs got\n  }\n  throw e;\n}","preventionTips":["Re-download truncated LUT files instead of parsing them anyway","Never edit LUT_3D_SIZE without regenerating the data table","Sanity-check the file's line count against size^3 before parsing"],"tags":["lut","validation","file-format"],"backgroundTag":"schema-validation-failed","analyzedSha":"46a3a6bf13ca367376ff18bbb06dae2e87e0d068","analyzedAt":"2026-09-18T00:12:20.256Z","contentChangedAt":"2026-09-18T00:12:20.256Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}