{"record":{"id":"fcee496de0667994","repo":"elastic/elasticsearch","slug":"dataset-dimensions-must-be-positive-rows-feat","errorCode":null,"errorMessage":"Dataset dimensions must be positive: rows={}, features={}","messagePattern":"Dataset dimensions must be positive: rows=(.+?), features=(.+?)","errorType":"validation","errorClass":"IllegalArgumentException","httpStatus":null,"severity":"error","filePath":"libs/gpu-codec/src/main/java/org/elasticsearch/gpu/codec/CuVSIvfPqParamsFactory.java","lineNumber":50,"sourceCode":"     * Creates {@link CuVSIvfPqParams} with automatically calculated parameters based on the\n     * dataset dimensions, distance metric, and efConstruction parameter.\n     *\n     * <p>This method replicates the parameter calculation logic from the C++ function:\n     * {@code cuvs::neighbors::graph_build_params::ivf_pq_params(dataset_extents, metric)}\n     *\n     * @param numVectors the number of vectors in the dataset\n     * @param dims the dimensionality of the vectors\n     * @param distanceType the distance metric to use (e.g., L2Expanded, Cosine)\n     * @param efConstruction the efConstruction parameter in an HNSW graph\n     * @return a {@link CuVSIvfPqParams} instance with calculated parameters\n     * @throws IllegalArgumentException if dimensions are invalid\n     */\n    static CuVSIvfPqParams create(int numVectors, int dims, CagraIndexParams.CuvsDistanceType distanceType, int efConstruction) {\n        long nRows = numVectors;\n        long nFeatures = dims;\n\n        if (nRows <= 0 || nFeatures <= 0) {\n            throw new IllegalArgumentException(\"Dataset dimensions must be positive: rows=\" + nRows + \", features=\" + nFeatures);\n        }\n        return createFromDimensions(nRows, nFeatures, distanceType, efConstruction);\n    }\n\n    /**\n     * Creates {@link CuVSIvfPqParams} with automatically calculated parameters based on dataset\n     * dimensions and construction parameter.\n     *\n     * <p>This is a convenience method when you have the dataset dimensions but not the dataset\n     * object itself. The calculation logic is identical to {@link #create(int, int,\n     * CagraIndexParams.CuvsDistanceType, int)}.\n     *\n     * @param nRows the number of rows (vectors) in the dataset\n     * @param nFeatures the number of features (dimensions) per vector\n     * @param distanceType the distance metric to use (e.g., L2Expanded, Cosine)\n     * @param efConstruction the construction parameter for parameter calculation\n     * @return a {@link CuVSIvfPqParams} instance with calculated parameters\n     * @throws IllegalArgumentException if dimensions are invalid","sourceCodeStart":32,"sourceCodeEnd":68,"githubUrl":"https://github.com/elastic/elasticsearch/blob/db6a809a667c081ca1dc7500389d26975573215f/libs/gpu-codec/src/main/java/org/elasticsearch/gpu/codec/CuVSIvfPqParamsFactory.java#L32-L68","documentation":"Thrown by CuVSIvfPqParamsFactory.create when either numVectors or dims is <= 0. This factory computes IVF-PQ (inverted file + product quantization) index parameters that require a concrete dataset shape; zero or negative dimensions make the parameter math meaningless, so it rejects up front.","triggerScenarios":"Calling CuVSIvfPqParamsFactory.create(numVectors, dims, distanceType, efConstruction) with numVectors <= 0 or dims <= 0. The values are widened to long (nRows, nFeatures) and checked: nRows <= 0 || nFeatures <= 0 triggers the throw.","commonSituations":"An empty or not-yet-populated dataset passed to the factory (numVectors = 0); a vector dimension config of 0 from a misconfigured mapping; a bug computing dims from the model definition that yields 0 or negative.","solutions":["Ensure the dataset has at least one vector and dims is a positive integer before calling create.","If the dataset can be empty at this point, skip IVF-PQ parameter computation until vectors are present.","Validate the field mapping's dims setting is positive (Elasticsearch dense_vector dims are 1..4096)."],"exampleFix":"// before: calling create on an empty dataset\nCuVSIvfPqParams params = CuVSIvfPqParamsFactory.create(0, dims, distanceType, ef);\n\n// after: guard for non-empty dataset\nif (numVectors <= 0 || dims <= 0) {\n    throw new IllegalStateException(\"cannot build IVF-PQ params: dataset is empty or dims invalid\");\n}\nCuVSIvfPqParams params = CuVSIvfPqParamsFactory.create(numVectors, dims, distanceType, ef);","handlingStrategy":"validation","validationCode":"static CuVSIvfPqParams safeCreate(int numVectors, int dims, CagraIndexParams.CuvsDistanceType dt, int ef) {\n    if (numVectors <= 0 || dims <= 0) {\n        throw new IllegalStateException(\"cannot compute IVF-PQ params: numVectors=\" + numVectors + \", dims=\" + dims);\n    }\n    return CuVSIvfPqParamsFactory.create(numVectors, dims, dt, ef);\n}","typeGuard":null,"tryCatchPattern":"try {\n    return CuVSIvfPqParamsFactory.create(numVectors, dims, dt, ef);\n} catch (IllegalArgumentException e) {\n    if (e.getMessage().contains(\"Dataset dimensions must be positive\")) {\n        // defer parameter computation until dataset is populated\n        return null;\n    }\n    throw e;\n}","preventionTips":["Ensure the dataset has at least one vector before computing params.","Validate dense_vector dims mapping is positive.","Skip IVF-PQ param computation for empty segments."],"tags":["gpu","validation","elasticsearch","codec","vector-search"],"backgroundTag":null,"analyzedSha":"db6a809a667c081ca1dc7500389d26975573215f","analyzedAt":"2026-08-12T01:39:14.192Z","schemaVersion":2},"datasetVersion":"2026-08-12T13:17:24.610Z"}