{"record":{"id":"e37ac94f6797a371","repo":"apache/flink","slug":"the-number-of-iterations-must-be-at-least-one","errorCode":null,"errorMessage":"The number of iterations must be at least one.","messagePattern":"The number of iterations must be at least one\\.","errorType":"exception","errorClass":"IllegalArgumentException","httpStatus":null,"severity":"error","filePath":"flink-core/src/main/java/org/apache/flink/api/common/operators/base/BulkIterationBase.java","lineNumber":149,"sourceCode":"                        new TerminationCriterionMapper<X>(),\n                        new UnaryOperatorInformation<X, X>(type, type),\n                        \"Termination Criterion Aggregation Wrapper\");\n        mapper.setInput(criterion);\n\n        this.terminationCriterion = mapper;\n        this.getAggregators()\n                .registerAggregationConvergenceCriterion(\n                        TERMINATION_CRITERION_AGGREGATOR_NAME,\n                        new TerminationCriterionAggregator(),\n                        new TerminationCriterionAggregationConvergence());\n    }\n\n    /**\n     * @param num\n     */\n    public void setMaximumNumberOfIterations(int num) {\n        if (num < 1) {\n            throw new IllegalArgumentException(\"The number of iterations must be at least one.\");\n        }\n        this.numberOfIterations = num;\n    }\n\n    public int getMaximumNumberOfIterations() {\n        return this.numberOfIterations;\n    }\n\n    @Override\n    public AggregatorRegistry getAggregators() {\n        return this.aggregators;\n    }\n\n    /**\n     * @throws InvalidProgramException\n     */\n    public void validate() throws InvalidProgramException {\n        if (this.input == null) {","sourceCodeStart":131,"sourceCodeEnd":167,"githubUrl":"https://github.com/apache/flink/blob/2f3c205e9266cb30240eb7f4fdab15cad629a70f/flink-core/src/main/java/org/apache/flink/api/common/operators/base/BulkIterationBase.java#L131-L167","documentation":"Thrown by BulkIterationBase.setMaximumNumberOfIterations(int num) when num is less than 1. A bulk iteration must run at least one iteration; zero or negative iteration counts are nonsensical and indicate a configuration error.","triggerScenarios":"Calling iteration.setMaximumNumberOfIterations(0) or with a negative value. Passing a computed iteration count that could be zero or negative due to upstream logic.","commonSituations":"Dynamically computing the number of iterations from data or config (e.g., Math.max(0, someValue)) without clamping to at least 1. Passing a user-provided configuration value that was not validated. Integer underflow or off-by-one in iteration count calculation.","solutions":["Validate the iteration count is >= 1 before calling setMaximumNumberOfIterations; clamp or fail early.","Use Math.max(1, num) to guarantee a minimum of one iteration when the value comes from external config.","If the iteration count is genuinely zero (no work to do), skip creating the iteration entirely.","Alternatively, use a termination criterion (setTerminationCriterion) instead of a fixed count when the number of iterations is uncertain."],"exampleFix":"// before\nint maxIters = getConfiguredIterations(); // could be 0\niteration.setMaximumNumberOfIterations(maxIters); // throws if < 1\n\n// after\nint maxIters = Math.max(1, getConfiguredIterations());\niteration.setMaximumNumberOfIterations(maxIters);","handlingStrategy":"validation","validationCode":"void safeSetMaxIterations(BulkIterationBase<?> iter, int num) {\n    if (num < 1) {\n        throw new IllegalArgumentException(\"Iteration count must be >= 1, got: \" + num);\n    }\n    iter.setMaximumNumberOfIterations(num);\n}","typeGuard":"boolean isValidIterationCount(int num) {\n    return num >= 1;\n}","tryCatchPattern":"try {\n    iteration.setMaximumNumberOfIterations(computedCount);\n} catch (IllegalArgumentException e) {\n    // count was < 1; clamp or fail\n    iteration.setMaximumNumberOfIterations(Math.max(1, computedCount));\n}","preventionTips":["Validate iteration counts come from configuration with a minimum of 1.","Use Math.max(1, value) when the count is dynamically computed.","If the count is zero, skip creating the iteration entirely."],"tags":["bulk-iteration","validation","iteration-count","dataset-api","flink-core"],"backgroundTag":null,"analyzedSha":"2f3c205e9266cb30240eb7f4fdab15cad629a70f","analyzedAt":"2026-08-14T08:48:24.518Z","schemaVersion":2},"datasetVersion":"2026-08-14T10:17:34.591Z"}