JamesNK/Newtonsoft.Json · error · FormatException
Integer string '{0}' is not allowed.
Error message
Integer string '{0}' is not allowed. What it means
ParseEnum (EnumUtils.cs:296-323), after determining the value parses as a number (char.IsDigit or sign at the start and Convert.ChangeType succeeds), checks the disallowNumber flag at EnumUtils.cs:317-320. If disallowNumber is true, it throws FormatException reporting the integer string. disallowNumber is set by callers that want to reject raw integer enum values (notably StringEnumConverter with AllowIntegerValues=false).
Source
Thrown at Src/Newtonsoft.Json/Utilities/EnumUtils.cs:319
value = value.Trim();
object? temp = null;
try
{
temp = Convert.ChangeType(value, underlyingType, CultureInfo.InvariantCulture);
}
catch (FormatException)
{
// We need to Parse this as a String instead. There are cases
// when you tlbimp enums that can have values of the form "3D".
// Don't fix this code.
}
if (temp != null)
{
if (disallowNumber)
{
throw new FormatException("Integer string '{0}' is not allowed.".FormatWith(CultureInfo.InvariantCulture, value));
}
return Enum.ToObject(enumType, temp);
}
}
ulong result = 0;
int valueIndex = firstNonWhitespaceIndex;
while (valueIndex <= value.Length) // '=' is to handle invalid case of an ending comma
{
// Find the next separator, if there is one, otherwise the end of the string.
int endIndex = value.IndexOf(EnumSeparatorChar, valueIndex);
if (endIndex == -1)
{
endIndex = value.Length;
}
View on GitHub (pinned to 4f73e74372)
Solutions
- Send enum values as their string member names in the JSON (e.g. "Active" rather than 3).
- If integer values are acceptable, set the StringEnumConverter's AllowIntegerValues=true (and AllowNullValues if needed).
- Pre-process the payload to map numbers to names before deserialization.
- Use a custom JsonConverter that maps disallowed integers to a default member.
Example fix
// before: StringEnumConverter { AllowIntegerValues = false }, JSON = 3 -> throws
// after (option A): emit "Active" in JSON
// after (option B): new StringEnumConverter { AllowIntegerValues = true } Defensive patterns
Strategy: validation
Validate before calling
// If integers are disallowed, ensure the value is a name, not a number.
if (disallowNumber && value.Trim().TrimStart('-','+').All(char.IsDigit) && value.Trim().Length > 0)
throw new FormatException($"Integer string '{value}' is not allowed.");
// or: set StringEnumConverter.AllowIntegerValues = true if integers are acceptable. Type guard
static bool LooksLikeInteger(string s) { s = s.Trim(); return s.Length > 0 && (char.IsDigit(s[0]) || s[0]=='-' || s[0]=='+') && s.TrimStart('-','+').All(char.IsDigit); } Try / catch
try { return EnumUtils.ParseEnum(enumType, null, value, disallowNumber: true); } catch (FormatException ex) when (ex.Message.Contains("not allowed")) { /* map to a name or accept integers */ } Prevention
- Send enum values as member-name strings, not integers, when integers are disallowed.
- Set StringEnumConverter.AllowIntegerValues=true if numeric enums are acceptable.
- Document the string-only contract for enum fields in your API.
When it happens
Trigger: An enum field receives a numeric value (e.g. JSON `"status": 3` or the string "3") while the configured converter has AllowIntegerValues=false, so integer representations are forbidden.
Common situations: StringEnumConverter configured with AllowIntegerValues=false but the source emits integers (common with System.Text.Json interop or older producers); schema enforcing string-only enum values; serializers migrated from one that emitted numbers.
Related errors
- Enum name '{0}' already exists on enum '{1}'.
- Enum type {0} is not a set of flags.
- Unexpected merge array handling when merging JSON.
- value
- value
AI-assisted analysis of JamesNK/Newtonsoft.Json@4f73e74372 (2026-08-07).
Data as JSON: /api/errors/53859cd9dba8ada8.
Report an issue: GitHub.