FasterXML/jackson-databind · error · IllegalArgumentException

Argument `allowedSchemes` must not be null

Error message

Argument `allowedSchemes` must not be null

What it means

NioPathDeserializer (the deserializer for java.nio.file.Path) requires a non-null collection of allowed URI schemes; passing null is a programmer error because the allow-list semantics need an explicit (possibly empty) set. The constructor throws IllegalArgumentException at JDKFromStringDeserializer.java:402. The public no-arg constructor already supplies DEFAULT_ALLOWED_SCHEMES, so this only fires when the Collection overload is called directly.

Solutions

  1. Pass NioPathDeserializer.DEFAULT_ALLOWED_SCHEMES (file only) when you want default behavior.
  2. Pass Collections.emptyList() when you want to accept only scheme-less (local path) values.
  3. Pass an explicit allow-list such as List.of("file","jar") to permit exactly those schemes.
  4. Prefer the no-arg constructor new NioPathDeserializer() unless you need a custom scheme set.

Example fix

// before
SimpleModule m = new SimpleModule();
m.addDeserializer(Path.class, new NioPathDeserializer(null));

// after
m.addDeserializer(Path.class, new NioPathDeserializer(NioPathDeserializer.DEFAULT_ALLOWED_SCHEMES));
Defensive patterns

Strategy: validation

Validate before calling

Collection<String> schemes = (configured == null)
    ? NioPathDeserializer.DEFAULT_ALLOWED_SCHEMES
    : configured;
m.addDeserializer(Path.class, new NioPathDeserializer(schemes));

Prevention

When it happens

Trigger: Manually instantiating new NioPathDeserializer(null); registering a custom Path deserializer via a SimpleModule and passing null for the scheme allow-list; wrapping NioPathDeserializer in a delegating deserializer that forwards a null configuration.

Common situations: Building a security-hardened Path deserializer (see databind#6129) and forgetting to initialize the scheme list; copy-paste from older code that pre-dates the allowedSchemes constructor; DI frameworks that inject null for an optional-looking Collection parameter.

Related errors


AI-assisted analysis of FasterXML/jackson-databind@87876ca5c0 (2026-08-11). Data as JSON: /api/errors/5f4f9a6b8c06723f. Report an issue: GitHub.

Appendix: source

Thrown at src/main/java/tools/jackson/databind/deser/jdk/JDKFromStringDeserializer.java:402

        public NioPathDeserializer() { this(DEFAULT_ALLOWED_SCHEMES); }

        /**
         * Constructor for specifying URI schemes to accept: matching is done
         * case-insensitively, same as by {@code java.nio.file.Path.of(URI)}.
         *<p>
         * NOTE: for allowed schemes that have no provider installed for the system
         * class loader, look up is also attempted using this thread's context class
         * loader (see [databind#2120]); this is never done for schemes that are not
         * allowed.
         *
         * @param allowedSchemes URI schemes to accept; must not be {@code null}
         *   (but may be empty to only accept scheme-less values)
         */
        public NioPathDeserializer(Collection<String> allowedSchemes) {
            super(Path.class, -1);
            if (allowedSchemes == null) {
                throw new IllegalArgumentException("Argument `allowedSchemes` must not be null");
            }
            _allowedSchemes = allowedSchemes;
        }

        @Override
        public Object _deserialize(String value, DeserializationContext ctxt) throws JacksonException {
            return deserialize(ctxt, value, _allowedSchemes);
        }

        public static Path deserialize(DeserializationContext ctxt, String value,
                Collection<String> allowedSchemes) throws JacksonException {
            // If someone gives us an input with no : at all, treat as local path,
            // instead of failing with invalid URI.

            int colonIx = value.indexOf(':');
            if (colonIx < 0) {
                return Path.of(value);
            }

View on GitHub (pinned to 87876ca5c0)