Agent skill

Nullaway

by nwjs in nwjs/chromium.src

Guide for resolving NullAway static analysis errors. An agent skill from nwjs/chromium.src.

BSD-3-ClauseAuto-check passedSecurity

Install Nullaway

skills CLI
$ npx skills add nwjs/chromium.src --skill nullaway -a claude-code

Project install by default; add -g for ~/.claude/skills/.

GitHub CLI
$ gh skill install nwjs/chromium.src nullaway --agent claude-code

Project scope by default; add --scope user for a personal install. Needs GitHub CLI 2.90.0 or later (public preview).

Manual copy
$ git clone --depth 1 https://github.com/nwjs/chromium.src.git skills-src && mkdir -p .claude/skills && cp -r skills-src/agents/skills/nullaway .claude/skills/nullaway && rm -rf skills-src

Use ~/.claude/skills/ instead of .claude/skills for a personal install. The folder must contain SKILL.md.

Claude Code skills documentation · loads skills from .claude/skills/

Facts

Skill name
nullaway
GitHub stars
160
Token cost
~3k tokens
SKILL.md length
1,414 words
Files
2
Skills in repo
64
Repo updated
First seen
Licence
BSD-3-Clause

At a glance

Guide for resolving NullAway static analysis errors. An agent skill from nwjs/chromium.src.

  • Works in 7 steps: Migration to @NullMarked vs New Code → No Functional Changes (For Migration) → assumeNonNull vs assert != null → …
  • Tasks that involve Static analysis and SAST
  • SKILL.md covers Core Principles, Common Patterns & Recipes, Preferred Null Safety Patterns and Testing, plus 1 more section
  • Instructions only: no scripts, shell commands, URLs or credentials in SKILL.md

What it does

Nullaway is an agent skill from nwjs/chromium.src. Guide for resolving NullAway static analysis errors. Best practices for: - Passing ObservableSupplier/Supplier<@Nullable T - Dereferencing potentially @Nullable values - Adding @NullMarked to Java code

Its SKILL.md is about 3k tokens, which your agent loads only when the skill is triggered. The skill folder holds 1 other file.

It sits in Security, covering Static analysis and SAST. It works with Java. The repository describes itself as: Chromium codebase with NW.js modifications. Based on https://chromium.googlesource.com/chromium/src.git. The licence is BSD-3-Clause.

When your agent uses it

  • Tasks that involve Static analysis and SAST

Example prompts

  • “/nullaway”

Workflow steps

7 steps, taken from the step headings in SKILL.md.

  1. Migration to @NullMarked vs New Code
  2. No Functional Changes (For Migration)
  3. assumeNonNull vs assert != null
  4. Handling Suppliers and Generics
  5. Annotations Placement
  6. Constructor Parameters for Nullable Fields
  7. Deciding on @Nullable for Getters

What it can do on your machine

Read from SKILL.md and the folder at commit a9e8946. It shows what the files ask for, not the result of running them.

  • Tool permissions

    Pre-approves nothing: there is no allowed-tools line, so your agent's usual permission prompts apply.

    From allowed-tools in the SKILL.md frontmatter.

  • Runs code

    No scripts in the folder and no shell commands in SKILL.md (its code samples are java).

    From the folder's file list and the shell code blocks in SKILL.md.

  • Network

    No URLs in SKILL.md.

    From URLs in SKILL.md, links to its own repository left out.

  • Credentials

    Names no API keys, tokens, secrets or passwords.

    From names ending in _API_KEY, _TOKEN, _SECRET, _KEY or _PASSWORD in SKILL.md.

Context cost

Nullaway loads about 3k tokens when it runs. Until then it costs about 53 tokens; SKILL.md has 1,414 words of instructions outside code blocks.

Always · name and description, kept in context so the agent knows when to use it
~53
When it runs · the whole SKILL.md, loaded when a task matches
~3k

Estimates: characters ÷ 4, the usual rule of thumb; real counts depend on the model's tokenizer. Scripts and assets cost tokens only if the agent reads them.

Safety

Auto-check passed

The automated check found no risky patterns in SKILL.md.

Automated static check — not a guarantee. Review scripts before installing. It scans the text of SKILL.md for risky patterns (piping downloads into a shell, reading credential files, hidden Unicode, destructive commands); files beside SKILL.md are not scanned.

SKILL.md

The full file from nwjs/chromium.src at commit a9e8946, republished under its BSD-3-Clause licence (© nwjs). 1,414 words, ~2,999 tokens.

Download SKILL.mdSave it as .claude/skills/nullaway/SKILL.md (or your agent's skills folder). This skill also uses 1 other file; get the full folder from GitHub.
name
nullaway
description
Guide for resolving NullAway static analysis errors. Best practices for: - Passing ObservableSupplier/Supplier<@Nullable T> - Dereferencing potentially @Nullable values - Adding @NullMarked to Java code

Core Principles

1. Migration to @NullMarked vs New Code

The approach differs significantly depending on whether you are migrating existing code to @NullMarked or writing new code in an already @NullMarked context:

  • Migration to @NullMarked:
    • Goal: Satisfy the static analyzer while minimizing functional changes to avoid regressions.
    • Practice: Use NullUtil.assumeNonNull() when dereferencing immediately to satisfy the analyzer without runtime overhead. Use assert when storing or returning values. Use if guards occasionally if it helps avoid assertions, but avoid changing the logic.
  • New Code (and modifying already @NullMarked code):
    • Goal: Build robust, null-safe components from the ground up.
    • Practice: Be more liberal with asserts to enforce contracts. Rely on correct annotations (or their absence for implicit @NonNull) and only use null guards for @Nullable values. assumeNonNull() should generally not be used for new code.
2. No Functional Changes (For Migration)
  • Rule: When migrating existing code, avoid adding new throwing runtime checks where they did not exist before, unless guided by the rules below.
3. assumeNonNull vs assert != null

The choice between assumeNonNull and Java assert depends on how the value is used:

  • Dereferencing @Nullable values immediately: Use NullUtil.assumeNonNull(x).
    • Example:
      java
      var value = mSupplier.get();
      assumeNonNull(value);
      value.doSomething();
    • Why: If it is null, it will NPE on the dereference anyway. assumeNonNull is a no-op that satisfies the analyzer without adding redundant runtime checks.
    • Style Rule: assumeNonNull() should be on a separate line, almost always, rather than used inline.
    • Note: This rule is primarily for migrations to avoid functional changes. For new code, rely on correct annotations and avoid assumeNonNull().
  • Passing @Nullable values to non-null parameters: First, look into the call tree of the receiver class and see if that parameter should be annotated as @Nullable or not. If it can natively handle null, update the method signature instead of adding an assertion. If it strictly requires a non-null value, THEN you MUST use a Java assert x != null; on a preceding line before passing or storing it.

    [!CAUTION] NEVER use assumeNonNull(x) to pass a @Nullable value to a non-null parameter or to return it from a non-nullable method. This is STRICTLY FORBIDDEN. You MUST use a Java assert on a preceding line to add a runtime check.

    • Bad Example:
      java
      mReceiver.setSomething(assumeNonNull(nullableValue));
    • Good Example:
      java
      assert nullableValue != null;
      mReceiver.setSomething(nullableValue);
  • Returning @Nullable values from non-nullable methods: First, consider if the method's return type can be safely updated to @Nullable. If it cannot (e.g., because it implements an interface or strictly enforces a non-null contract), you MUST use a Java assert x != null; on a preceding line before returning the value. Using assumeNonNull(x) inline within a return statement is strictly forbidden.
    • Bad Example:
      java
      return assumeNonNull(nullableValue);
    • Good Example:
      java
      assert nullableValue != null;
      return nullableValue;
  • Why: Asserts add a runtime check (active in tests/debug) which is an acceptable functional change. We rely on instrumentation tests to validate these changes.
    • Deep Investigation Rule: Before asserting or assuming non-null for a passed value, investigate the call tree. If the method being called can be updated to consider the parameter @Nullable, prefer updating the method signature over adding an assertion.
    • Warning: Be careful with assert value != null on Supplier.get() during initialization. If the supplier value is set LATER (as is common with UI wiring), the assert might fail immediately during construction. In such cases, the getter should return @Nullable and callers should handle it, rather than asserting non-null immediately.
4. Handling Suppliers and Generics
  • Problem: Passing a Supplier<@Nullable T> to a constructor that expects Supplier<T> (non-nullable), or vice versa.
  • Preference: Prefer using exact types like Supplier<@Nullable T> rather than wildcards like Supplier<? extends @Nullable T> in method signatures and fields.
  • Upcasting: SupplierUtils.upcast() is strictly for upcasting the type parameter to a base class (e.g., Supplier<DerivedT> to Supplier<BaseT>). Do NOT use it solely for handling nullability differences (e.g., Supplier<T> to Supplier<@Nullable T>).
  • Handling Nullability Generic Invariance: You generally shouldn't need to use lambdas or upcast to bridge nullability differences (e.g., passing Supplier<T> to Supplier<@Nullable T>) if you are passing around subclasses of ObservableSupplier.
  • Design Principle: If a supplier can return null, the receiver class must be updated to accept Supplier<@Nullable T> and handle the nullity. Never use hacks or assertions to force a Supplier<@Nullable T> to act as a non-nullable Supplier<T>.
  • Good Fix: Alter the receiver class to accept Supplier<@Nullable T>.
    • Then, handle the nullability inside the receiver class using the rules above (assumeNonNull or assert).
  • Supplier Wrappers (Anti-Pattern): Do NOT introduce a new lambda just to wrap a supplier call with an assertion. For example, do not do this: () -> assumeNonNull(supplier.get()) or this: () -> { var x = getter(); assert x != null; return x; }. These are anti-patterns.
    • If using ObservableSupplier: Pass supplier.asNonNull() directly. This returns a NonNullObservableSupplier which satisfies Supplier<@NonNull T>.
    • Otherwise: Change the receiver's parameter type to Supplier<@Nullable T> and handle the nullity inside the receiver class. Do not force non-nullability at the call site with hacks.
  • Supplier Argument Types: Consider changing Supplier arguments to Supplier<@Nullable T> or MonotonicObservableSupplier<T> in method signatures to avoid forcing non-nullability on callers.
Show full SKILL.md (640 more words)Show less
5. Annotations Placement
  • Correct Imports: ALWAYS use org.chromium.build.annotations.Nullable and org.chromium.build.annotations.NullMarked. Do NOT use androidx.annotation or javax.annotation variations.
  • @NullMarked: Apply to the class level when you are ready to make the whole class null-safe.
  • @Nullable: Apply to fields, parameters, and return types that can be null.
  • @NonNull Default: Values are @NonNull by default in a @NullMarked class. Do NOT use @NonNull explicitly on fields, parameters, or return types. Use @NonNull only in the context of nullable generic parameters if absolutely necessary.
  • @SuppressWarnings("NullAway"):
    • Use as a last resort.
    • Do NOT add to constructors. Fix the warnings in the constructor instead.
    • Highly Recommended for destroy() or onDestroy(): If fields are nulled out during teardown to prevent memory leaks, do NOT mark the fields as @Nullable just to satisfy this one assignment. Instead, mark the fields as @MonotonicNonNull (if late-initialized) or @NonNull (if initialized in constructor), and add @SuppressWarnings("NullAway") to the destroy() or onDestroy() method. This prevents having to null-check the fields everywhere else in the class.
6. Constructor Parameters for Nullable Fields
  • Rule: If a constructor parameter is stored directly into a @Nullable field, the parameter itself should usually be marked @Nullable as well, even if it is not immediately used as nullable in the constructor. This avoids artificial non-null requirements at construction time.
7. Deciding on @Nullable for Getters
  • Rule: When deciding whether to make a getter return @Nullable, look at how callers handle the return value:
    • If most callers check for null before use, it is likely intended to be @Nullable.
    • If most callers assume it is non-null (and would crash if null), consider keeping it non-null or refactoring to ensure it is non-null, rather than forcing all callers to handle null.

Common Patterns & Recipes

Recipe: Refactoring Receiver for Nullable Supplier

Before (in Caller):

java
mReceiver = new Receiver(() -> assumeNonNull(nullableSupplier.get()));

After:

  1. In Receiver Class:
    java
    // Change constructor to take exact Supplier<@Nullable Item>
    public Receiver(Supplier<@Nullable Item> supplier) {
        mSupplier = supplier;
    }
    
    // In usage (Dereferenced right away)
    void doSomething() {
        var item = mSupplier.get();
        assumeNonNull(item);
        item.use();
    }
    
    // In usage (Stored or Passed)
    void storeItem() {
        var item = mSupplier.get();
        assert item != null;
        mStoredItem = item;
    }
  2. In Caller: If the caller has a Supplier<DerivedItem> and the receiver expects Supplier<@Nullable BaseItem>, use SupplierUtils.upcast() to pass it:
    java
    mReceiver = new Receiver(SupplierUtils.upcast(derivedSupplier, BaseItem.class));
    If the caller already has a Supplier<@Nullable Item>, pass it directly:
    java
    mReceiver = new Receiver(nullableSupplier);
Note on Deep Investigation for Suppliers

Before applying the recipe above to force non-nullability or add assertions, investigate the receiver. If the receiver (or classes it passes the supplier to) already checks for null or can easily be updated to handle null, prefer updating the signature to accept Supplier<@Nullable T> instead of forcing non-nullability.

Preferred Null Safety Patterns

  • ObservableSupplier / MonotonicObservableSupplier: Prefer supplier.asNonNull().get() over var x = supplier.get(); assert x != null;.
  • Assertions and Chaining: Use assumeNonNull(object) from org.chromium.build.NullUtil instead of assert object != null when you want to chain calls on the non-null object (e.g., assumeNonNull(mLayoutManager).getSomething()). It returns the non-null object.
  • Asserting over Silent Checks: If a code path guarantees that an object must be non-null, use an explicit assertion instead of a silent null check (e.g., changing if (x != null) to assert x != null).
  • Testing Getters: get*ForTesting() methods should just return @Nullable (and be annotated as such) rather than asserting non-null, if the underlying field is nullable. Let the test handle the nullity.

Testing

  • Smoke Test: Use PublicTransitLeakTest as a smoke test locally before running all tests on CQ to validate functional changes introduced by assertions.

Troubleshooting

  • Warning in Constructor: If NullAway warns that a field is not initialized in the constructor, ensure it is marked @Nullable or @MonotonicNonNull if it's initialized later (e.g., in init or initWithProfile).
  • Method returns @Nullable but signature doesn't say so: Add @Nullable to the method signature.
  • Satisfying Non-Null Callbacks: Do NOT use assumeNonNull(null) to satisfy a callback that expects a non-null value if the value can actually be null. Update the callback definition to accept @Nullable T.

© nwjs, BSD-3-Clause. Rendered from Markdown: HTML in the file is shown as text, images as links, and headings moved down two levels. Raw file

Files

SKILL.md and 1 other file in agents/skills/nullaway of nwjs/chromium.src.

  • SKILL.md
  • OWNERS

Open the folder on GitHubat commit a9e8946

Compare with similar skills

Nullaway next to the 5 skills that share the most tags, products or categories with it. Stars are the repository's; “used in” counts other GitHub owners with a copy.

Nullaway compared with similar skills
SkillStarsUsed inTokensAuto-checkLicenceRepo updated
Nullaway this skillnwjs/chromium.src160—~3kAutomated safety check: PassBSD-3-Clause
Sast Xxeutkusen/sast-skills1.3k—~7.2kAutomated safety check: PassMIT
Java API Consistency ValidatorArabelaTso/Skills-4-SE253—~660Automated safety check: PassApache-2.0
CodeQL Security Scantrailofbits/skills7.4k—~4.6kAutomated safety check: NotesCC-BY-SA-4.0
Skylosduriantaco/skylos843—~581Automated safety check: PassApache-2.0
Skylos Securityduriantaco/skylos843—~545Automated safety check: PassApache-2.0

Similar skills

  • Sast Xxe

    utkusen/sast-skills

    Detect XML External Entity (XXE) vulnerabilities in a codebase using a three-phase approach: recon (find XML parsing sites without external-entity hardening), batched verify (trace user input to…

    1.3k GitHub stars~7.2k tokensUpdated 6 mo ago
    SecurityAuto-check passed
  • Java API Consistency Validator

    ArabelaTso/Skills-4-SE

    Validate API consistency between two versions of Java libraries.

    253 GitHub stars~660 tokensUpdated 1 mo ago
    SecurityAuto-check passed
  • CodeQL Security Scan

    trailofbits/skills

    Official

    Scans a codebase for vulnerabilities with CodeQL's data flow and taint tracking in run-all or important-only modes, including data extensions for project-specific sources and sinks.

    7.4k GitHub stars~4.6k tokensUpdated yesterday
    SecurityAuto-check: notes
  • Skylos

    duriantaco/skylos

    Run, interpret, or modify Skylos safely. An agent skill from duriantaco/skylos.

    843 GitHub stars~581 tokensUpdated today
    SecurityAuto-check passed
  • Skylos Security

    duriantaco/skylos

    Investigate and harden Skylos security behavior. An agent skill from duriantaco/skylos.

    843 GitHub stars~545 tokensUpdated today
    SecurityAuto-check passed
  • Constant-Time Analysis

    trailofbits/skills

    Official

    Compiles cryptographic code and inspects the assembly or bytecode for variable-time instructions, then triages which flagged operations actually touch secrets.

    7.4k GitHub stars~3.3k tokensUpdated yesterday
    SecurityAuto-check: notes

More from nwjs/chromium.src

All 64 skills in this repo
  • Analyzing SQL Traces

    nwjs/chromium.src

    Extracts raw trace data from Perfetto traces, runs arbitrary SQL queries for custom follow-up analysis, and applies expert cognitive principles (Tiered Flow Analysis, Semantic Mismatch, Redundancy)…

    160 GitHub stars~2.9k tokensUpdated 5 days ago
    Auto-check passed
  • Autonomous multi-agent performance optimization loop for Chromium and V8.

    160 GitHub stars~4.2k tokensUpdated 5 days ago
    Auto-check passed
  • Automated Tracing

    nwjs/chromium.src

    Automated Tracing & Performance Telemetry in Chromium using Perfetto and Telemetry benchmarks.

    160 GitHub stars~1.5k tokensUpdated 5 days ago
    Auto-check passed
  • Chrome Releases

    nwjs/chromium.src

    Queries Chrome commit, version, release, and milestone metadata.

    160 GitHub stars~1.3k tokensUpdated 5 days ago
    Auto-check passed
  • Chromium Docs

    nwjs/chromium.src

    Search and reference Chromium documentation from the local docs index, including design docs, APIs, and development guides.

    160 GitHub stars~1.2k tokensUpdated 5 days ago
    Auto-check passed
  • Gn Deps Debugging

    nwjs/chromium.src

    Diagnose Chromium GN dependency and include-visibility failures, including BUILD.gn deps/publicdeps, DEPS include rules, private headers, and circular dependencies.

    160 GitHub stars~1.5k tokensUpdated 5 days ago
    Auto-check passed

Works with

Categories

Questions about Nullaway

What does Nullaway do?

Guide for resolving NullAway static analysis errors. An agent skill from nwjs/chromium.src. src. Guide for resolving NullAway static analysis errors.

When should I use Nullaway?

Nullaway fits situations like: tasks that involve Static analysis and SAST.

How do I install Nullaway in Claude Code?

Run `npx skills add nwjs/chromium.src --skill nullaway -a claude-code`. Or copy the skill folder (agents/skills/nullaway in nwjs/chromium.src) into .claude/skills/nullaway in your project. Claude Code loads it when a task matches its description.

How do I install Nullaway in Codex?

Run `npx skills add nwjs/chromium.src --skill nullaway -a codex`. Or copy the skill folder (agents/skills/nullaway in nwjs/chromium.src) into .agents/skills/nullaway in your project. Codex loads it when a task matches its description.

Can I use Nullaway in Cursor, Gemini CLI or GitHub Copilot?

Cursor, Gemini CLI, GitHub Copilot and OpenCode also load SKILL.md folders. With the skills CLI, run `npx skills add nwjs/chromium.src --skill nullaway -a cursor` (or -a gemini-cli, github-copilot or opencode for the others). To copy it by hand, put the folder in .cursor/skills/nullaway, .gemini/skills/nullaway, .github/skills/nullaway and .opencode/skills/nullaway in your project.

What does Nullaway need to run?

SKILL.md names no scripts, command-line tools or credentials: Nullaway is instructions for the agent only.

Does Nullaway access the network?

SKILL.md contains no URLs. Any network use would come from the scripts or tools the agent runs. This is read from the text; nothing was executed.

Is Nullaway safe to install?

Our automated static check of SKILL.md found no risky patterns, such as piping downloads into a shell, reading credential files or hidden Unicode. It is not a guarantee. Review the folder before installing.

What licence does Nullaway use?

Nullaway is published under the BSD-3-Clause licence (the repository's licence). It allows redistribution, so the full SKILL.md is shown on this page.

How many tokens does Nullaway use?

About 3k tokens (SKILL.md is roughly 12k characters). Agents keep only the skill's name and description in context until a task matches; then they load SKILL.md in full.

What are the alternatives to Nullaway?

Skills that share tags, products or a category with Nullaway: Sast Xxe (utkusen/sast-skills, 1.3k stars), Java API Consistency Validator (ArabelaTso/Skills-4-SE, 253 stars), CodeQL Security Scan (trailofbits/skills, 7.4k stars) and Skylos (duriantaco/skylos, 843 stars). The comparison table on this page puts their stars, adoption, token cost, safety result and licence side by side.

Who maintains Nullaway?

nwjs (a GitHub organization) maintains it in nwjs/chromium.src, which has 160 GitHub stars. The repository holds 64 skills in this directory. The repository was last updated on October 3, 2026.

Source: nwjs/chromium.src on GitHub. Facts on this page come from the repository at the commit we read; the author's words are quoted as theirs.