agentsclimarketplace

Jackson injection security

Skill cxcscmu/SkillLearnBench/skills/b1-one-shot-claude-sonnet-4-6/fix-security-bug/jackson-injection-security

[COLM'26] SkillLearnBench is the first benchmark for evaluating continual learning methods that automatically generate agent skills.

Install
npx -y skills add cxcscmu/SkillLearnBench --skill jackson-injection-security

Assembled from the repository path, not quoted from the project. Check it against their README if it does not work.

What its author says it does

Copied from the file, not written here

Security considerations for Jackson @JacksonInject - preventing JSON input from overriding injected values, covering CVE patterns and defense strategies.

SKILL.md

2.7 KB, 586 tokens by cl100k_base, as published. Nobody here has run it

Jackson @JacksonInject Security

The Vulnerability Pattern

When a @JsonCreator constructor uses @JacksonInject without useInput = OptBoolean.FALSE, Jackson can fall back to JSON input to provide the injectable value. This is exploitable when:

  1. The injectable ID (default: empty string "") matches a JSON property key
  2. The JSON property contains a deserializable value of the expected type
  3. This overrides the server-configured injected value (e.g., security settings)

Example Vulnerable Code

@JsonCreator
public SomeFilter(
    @JsonProperty("dimension") String dimension,
    @JacksonInject SecurityConfig config  // VULNERABLE: can be overridden via JSON ""
)

Exploit Pattern

{
  "dimension": "value",
  "": {"securityEnabled": false}  // Empty key "" overrides @JacksonInject default id
}

The Fix

Option 1: useInput = OptBoolean.FALSE (Recommended for Jackson 2.9+)

import com.fasterxml.jackson.annotation.OptBoolean;

@JsonCreator
public SomeFilter(
    @JsonProperty("dimension") String dimension,
    @JacksonInject(useInput = OptBoolean.FALSE) SecurityConfig config  // FIXED
)

This tells Jackson: NEVER use JSON to provide this value, ALWAYS use InjectableValues only.

Option 2: Explicit Injectable ID (prevents empty string match)

@JacksonInject("securityConfig")  // Named ID that won't match "" key
SecurityConfig config

Option 3: Server-side validation before processing

// Validate BEFORE Jackson deserialization or AFTER using Guice-injected config
@Inject
public MyService(SecurityConfig trustedConfig) {
    this.trustedConfig = trustedConfig;  // From Guice, not from Jackson
}

@JacksonInject Behavior Summary

useInput valueBehavior
OptBoolean.DEFAULTUse InjectableValues if present; may fall back to JSON
OptBoolean.TRUEJSON input takes precedence over InjectableValues
OptBoolean.FALSEONLY use InjectableValues; NEVER read from JSON

Druid-Specific Context

In Apache Druid, Jackson InjectableValues are configured via Guice's GuiceInjectableValues. The injectable ID lookup uses the parameter type's class name by default.

When @JacksonInject.value() is "" (empty string default), Jackson may use the empty string as the lookup key, which fails to find the Guice-bound value, causing fallback to JSON.

Detection

Look for @JacksonInject without useInput = OptBoolean.FALSE in @JsonCreator constructors where the injected value controls security behavior.

Keep looking

Skills are one crate of 328,083. Ordering is by how many stacks a row turns up in, so the top of any crate is what has actually been picked rather than what has the most stars.