---
id: java-security
track: coding
version: 0.7.0
label: blocks
keyword: block
where: write turn-end
sha256: 9ef2d2c9c8a10ee629b2ce34d21e17a69b84ecdf07ff11dd475c3f62b99cd60b
source: https://github.com/open-coder-ai/chock-catalog/tree/1e60d211c1bb767152c6ab0167932da06ab3a10f/base/java-security
catalog_ref: 1e60d211c1bb767152c6ab0167932da06ab3a10f
---

# Java Security Rules

java-security · version 0.7.0

Blocks — Blocks on an agent's file writes and at turn end. Chock adds friction. It is not a security boundary. 

In a git repo: at commit (Chock refuses the commit, locally and in CI.)



## What it does

Trigger: writing Java or Kotlin (Spring, Jakarta EE, Quarkus, Android), SQL/JPA/MyBatis, templates, application.properties/.yml, web.xml, pom.xml, Gradle; "customize java security" opens the guided page. avoid: injection, XXE, SSRF, unsafe deserialization, path traversal, weak crypto, trust-all TLS, Spring Security off, exposed secrets, known-exploited deps, SpotBugs/Sonar/PMD/Checkstyle findings. 129 rules, 16 packs, each allow|deny|ask in .chock/security.json; absent = deny (quality: allow).

## Its label on each agent

- Claude Code (tested): Blocks — Blocks on an agent's file writes and at turn end. Builder: /coding/builder/#client=claude-code&p=java-security
- Cursor (tested): Blocks — Blocks on an agent's file writes and at turn end. Builder: /coding/builder/#client=cursor&p=java-security
- Codex (tested): Blocks — Blocks on an agent's file writes and at turn end. If the hook errors, the action goes through (not witnessed; the vendor's row is only partly live-run). Builder: /coding/builder/#client=codex&p=java-security
- GitHub Copilot (tested): Blocks — Blocks at turn end only. It does not check a file write when it happens. If the hook errors, the action goes through (not witnessed; the vendor's row is only partly live-run). Builder: /coding/builder/#client=copilot&p=java-security
- Devin (tested): Blocks — Blocks at turn end only. It does not check a file write when it happens. If the hook errors, the action goes through (vendor docs only, not witnessed). Builder: /coding/builder/#client=devin&p=java-security
- Grok (tested): Not graded yet for Grok. Builder: /coding/builder/#client=grok&p=java-security
- goose (tested): Not graded yet for goose. Builder: /coding/builder/#client=goose&p=java-security
- Antigravity (tested): Not graded yet for Antigravity. Builder: /coding/builder/#client=antigravity&p=java-security
- OpenHands (untested): Not graded yet for OpenHands. Builder: /coding/builder/#client=openhands&p=java-security
- Kimi Code (untested): Not graded yet for Kimi Code. Builder: /coding/builder/#client=kimi-code&p=java-security
- Factory Droid (untested): Not graded yet for Factory Droid. Builder: /coding/builder/#client=factory-droid&p=java-security

## What it misses

This policy does not state what it misses.

## Examples

- Refused: A MyBatis mapper orders by a column taken from the request, written as ORDER BY ${col}.
- Allowed: A MyBatis mapper binds a parameter as WHERE id =

## Latest change

0.7.0 · 2026-10-02 — Owner-approved loosening (plan decision D2, roadmap 4.5 #11): a rule no selection speaks for now takes its pack's tier default. The nine security packs (79 rules) still deny; the seven quality packs -- bugs, concurrency, resources, exceptions, performance, style, testing (50 rules) -- now allow, so a legacy file's existing quality findings no longer refuse an edit. A pack kind with no written default, or a pack this build lacks, denies. A verdict a selection file spells keeps its value; only silence changed meaning. A file that spells every rule (what the setup page wrote when nothing was unticked) reads exactly as before. A rule a file leaves unspoken now takes its tier's default: that includes every quality rule in a version-1 file, which predates the quality packs, and any quality row someone unticked on the page (shown then as \`unspoken -\> deny\`). Such a file now allows those quality rules. To keep enforcing a quality pack, spell it: \`{"version": 2, "packs": {"exceptions": {"verdict": "deny"}}}\`. The description says \`absent = deny (quality: allow)\`, its wording shortened to stay within the 500-char budget. The setup page preselects each rule's pack default (from the pack's kind). It marks a row weakened when its verdict (an unticked row: the pack default it falls to) is weaker than the stricter of that default and the repository's current selection, and it leaves a quality rule at allow unspoken unless something stricter stood before. Not yet mirrored by the engine: chock's check-baseline and chock_guidance still read a silent quality rule as deny. Deleting a quality pack's entry from a committed selection is therefore not reported as a loosening, and guidance may name a quality rule that no longer enforces. Security rules are unaffected: silence denies them in both. Known limit: an empty catch around a security check (\`checkServerTrusted\`, \`parseClaimsJws\`, \`verify\`) was refused only by the quality rule exceptions-empty-catch, so with no selection it now passes; spell the exceptions pack as deny to keep that refusal.

## Provenance

- Tested by 167 of 177 cases run automatically
- SHA-256: `9ef2d2c9c8a10ee629b2ce34d21e17a69b84ecdf07ff11dd475c3f62b99cd60b`
- Catalog commit: https://github.com/open-coder-ai/chock-catalog/commit/1e60d211c1bb767152c6ab0167932da06ab3a10f
- Source: https://github.com/open-coder-ai/chock-catalog/tree/1e60d211c1bb767152c6ab0167932da06ab3a10f/base/java-security (catalog path `base/java-security`)
- Presets: none
- JSON: `/api/coding/policies/java-security.json`
- Report a problem: https://chock.sh/report/?policy=java-security&version=0.7.0&page=%2Fcoding%2Fpolicies%2Fjava-security%2F
