{"record":{"id":"75e55db7b766fe5c","repo":"jwtk/jjwt","slug":"value-must-be-a-positive-integer","errorCode":null,"errorMessage":"Value must be a positive integer.","messagePattern":"Value must be a positive integer\\.","errorType":"validation","errorClass":"IllegalArgumentException","httpStatus":null,"severity":"error","filePath":"impl/src/main/java/io/jsonwebtoken/impl/lang/PositiveIntegerConverter.java","lineNumber":51,"sourceCode":"        Assert.notNull(o, \"Argument cannot be null.\");\n        int i;\n        if (o instanceof Byte || o instanceof Short || o instanceof Integer || o instanceof AtomicInteger) {\n            i = ((Number) o).intValue();\n        } else {  // could be Long, AtomicLong, Float, Decimal, BigInteger, BigDecimal, String, etc., all of which\n            // may not be accurately converted into an Integer, either due to overflow or fractional values.  The\n            // easiest way to account for all of them is to parse the string value as an int instead of testing all\n            // the types:\n            String sval = String.valueOf(o);\n            try {\n                i = Integer.parseInt(sval);\n            } catch (NumberFormatException e) {\n                String msg = \"Value cannot be represented as a java.lang.Integer.\";\n                throw new IllegalArgumentException(msg, e);\n            }\n        }\n        if (i <= 0) {\n            String msg = \"Value must be a positive integer.\";\n            throw new IllegalArgumentException(msg);\n        }\n        return i;\n    }\n}\n","sourceCodeStart":33,"sourceCodeEnd":56,"githubUrl":"https://github.com/jwtk/jjwt/blob/fb71496164c71442d08adec4571d9616ed5e1b8d/impl/src/main/java/io/jsonwebtoken/impl/lang/PositiveIntegerConverter.java#L33-L56","documentation":"Thrown by PositiveIntegerConverter.applyFrom when a raw value destined for a parameter that must be a positive integer either cannot be converted to an int (overflow, fractional number, non-numeric string) or converts to a value <= 0. It is a parameter-conversion guard: the offending input is whatever Object was passed for that parameter (e.g. an expiration/leeway-style setting).","triggerScenarios":"Passing 0 or a negative number (or a string like \"0\", \"-3\") to any claim/converter configured with PositiveIntegerConverter.","commonSituations":"Zero initialized counters used as default values; negative offsets; computing a value like timeout = end - start that evaluated to <= 0.","solutions":["Ensure the value is >= 1 before passing it.","Clamp or validate: if (v <= 0) throw/adjust before setting the claim.","Check upstream computation for off-by-one or sign errors that produced the non-positive value."],"exampleFix":"// before\nlong seconds = (end - start) / 1000; // could be 0\njwtBuilder.claim(\"ttl\", (int) seconds);\n// after\nint seconds = Math.max(1, (int) ((end - start) / 1000));\njwtBuilder.claim(\"ttl\", seconds);","handlingStrategy":"validation","validationCode":"int requirePositive(int v) {\n    if (v <= 0) throw new IllegalArgumentException(\"Value must be a positive integer, got: \" + v);\n    return v;\n}","typeGuard":null,"tryCatchPattern":"try {\n    converter.applyFrom(value);\n} catch (IllegalArgumentException e) {\n    if (\"Value must be a positive integer.\".equals(e.getMessage())) {\n        // clamp or reject the non-positive input\n    }\n    throw e;\n}","preventionTips":["Validate >= 1 at boundaries where the value is computed or configured","Beware of defaults of 0 for counters, TTLs and limits","Check subtraction-based computations for negative/zero results"],"tags":["validation","integer","value-range"],"backgroundTag":"value-out-of-range","analyzedSha":"fb71496164c71442d08adec4571d9616ed5e1b8d","analyzedAt":"2026-09-09T00:33:09.982Z","contentChangedAt":"2026-09-09T00:33:09.982Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}