{"record":{"id":"885306632baf1e75","repo":"dotnet/efcore","slug":"the-specified-maxbatchsize-value-value-is-no","errorCode":null,"errorMessage":"The specified 'MaxBatchSize' value '{value}' is not valid. It must be a positive number.","messagePattern":"The specified 'MaxBatchSize' value '(.+?)' is not valid\\. It must be a positive number\\.","errorType":"exception","errorClass":"InvalidOperationException","httpStatus":null,"severity":"error","filePath":"src/EFCore.Relational/Infrastructure/RelationalOptionsExtension.cs","lineNumber":197,"sourceCode":"    /// <summary>\n    ///     The maximum number of statements that will be included in commands sent to the database\n    ///     during <see cref=\"DbContext.SaveChanges()\" /> or <see langword=\"null\" /> if none has been set.\n    /// </summary>\n    public virtual int? MaxBatchSize\n        => _maxBatchSize;\n\n    /// <summary>\n    ///     Creates a new instance with all options the same as for this instance, but with the given option changed.\n    ///     It is unusual to call this method directly. Instead use <see cref=\"DbContextOptionsBuilder\" />.\n    /// </summary>\n    /// <param name=\"maxBatchSize\">The option to change.</param>\n    /// <returns>A new instance with the option changed.</returns>\n    public virtual RelationalOptionsExtension WithMaxBatchSize(int? maxBatchSize)\n    {\n        if (maxBatchSize.HasValue\n            && maxBatchSize <= 0)\n        {\n            throw new InvalidOperationException(RelationalStrings.InvalidMaxBatchSize(maxBatchSize));\n        }\n\n        var clone = Clone();\n\n        clone._maxBatchSize = maxBatchSize;\n\n        return clone;\n    }\n\n    /// <summary>\n    ///     The minimum number of statements that are needed for a multi-statement command sent to the database\n    ///     during <see cref=\"DbContext.SaveChanges()\" /> or <see langword=\"null\" /> if none has been set.\n    /// </summary>\n    public virtual int? MinBatchSize\n        => _minBatchSize;\n\n    /// <summary>\n    ///     Creates a new instance with all options the same as for this instance, but with the given option changed.","sourceCodeStart":179,"sourceCodeEnd":215,"githubUrl":"https://github.com/dotnet/efcore/blob/3a2006ef569de08368d59db5e1468aa8f407e4f8/src/EFCore.Relational/Infrastructure/RelationalOptionsExtension.cs#L179-L215","documentation":"RelationalOptionsExtension.WithMaxBatchSize requires the value be null (unset) or strictly greater than zero; 0 and negatives are rejected. This bounds the number of statements grouped into one multi-statement command during SaveChanges.","triggerScenarios":"Calling optionsBuilder.MaxBatchSize(0) or .MaxBatchSize(-3); computing MaxBatchSize from config that can resolve to 0.","commonSituations":"Defaulting to 0 to mean 'disabled'; mis-parsed config; tests that pass 0 expecting batching off (you should leave it unset instead).","solutions":["Pass a positive int (>= 1) for an explicit cap, or leave unset / pass null to use the provider default.","Validate config: treat 0/negative as 'unset' (null).","To disable batching, set MaxBatchSize to 1, not 0."],"exampleFix":"// before\noptionsBuilder.UseSqlServer(conn).MaxBatchSize(0);\n\n// after\noptionsBuilder.UseSqlServer(conn).MaxBatchSize(1); // or omit to use default","handlingStrategy":"validation","validationCode":"static int? SafeMaxBatchSize(string? raw)\n    => int.TryParse(raw, out var v) && v > 0 ? v : (int?)null;","typeGuard":"static bool IsValidMaxBatchSize(int? value) => value is null || value > 0;","tryCatchPattern":null,"preventionTips":["Do not pass 0 to mean 'disabled' — use 1 to effectively disable multi-statement batching, or leave unset.","Validate config before applying; treat 0/negative as unset.","Keep options construction in one place."],"tags":["configuration","options","batching","relational"],"backgroundTag":null,"analyzedSha":"3a2006ef569de08368d59db5e1468aa8f407e4f8","analyzedAt":"2026-08-11T23:42:04.146Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}