Documentation
Install, scan, fix. No account required to scan — Pro features unlock with a license.
Requirements
Editor-only, on Windows, macOS and Linux — pure managed C#, no native plug-ins, nothing to install alongside it. The scan needs no network and no account; Explain and AI Fix work out of the box with no API key.
Install
Three ways in — pick whichever fits your workflow.
In Unity: Window ▸ Package Manager ▸ + ▸ Add package from git URL…, then paste this and hit Add.
https://github.com/cnxiaom/perflint-unity.git Want a fixed version instead of latest? Append a release tag — #v1.7.1.
Prefer the store? Get PerfLint on the Asset Store — add it to your assets, then import from Window ▸ Package Manager ▸ My Assets. It installs under Assets/PerfLint/; same package, same features.
Or declare it directly in Packages/manifest.json — useful when the project is provisioned from source control.
{
"dependencies": {
"com.perflint.unity": "https://github.com/cnxiaom/perflint-unity.git"
}
} Run your first scan
No account, no key, no setup. Four steps from install to a report.
- Open the panel.
Tools ▸ PerfLint ▸ Scan Project, orCtrl/Cmd + Alt + L. - Click Scan Project. A report appears in seconds. Everything runs on your machine.
- Read the findings. Grouped Performance / Assets / Migration / ProjectSettings, each with a severity, an exact location, what it costs you, and a fix.
- Narrow it down. Filter by Critical / Warning / Info, flip on “only fixable”, or search. Export anything to CSV.
Every finding carries a stable rule code (PERF.TEX005, ASSET.DUP001…). The
rules reference has a page per rule: what triggers it, what it costs, how to fix it by
hand, and whether PerfLint can fix it for you.
Applying fixes
Three kinds, and they differ in what they touch and how you get back.
Focused script-level issues. Only the flagged snippet is sent; every written change is compile-verified and rolled back automatically if the build breaks.
Free: 10 hosted credits/day. Pro: a much larger monthly pool.
Deterministic, low-risk changes such as import settings, with a preview first.
Not Edit ▸ Undo territory — these write importer settings and reimport, which Unity's undo stack does not record. Commit first; restore from there.
Curated whole-file Unity upgrade work: diff preview, compile verification, automatic rollback on failure.
AI Fix & Explain
Works with no setup at all. Bring your own key if you would rather the calls never touch us.
Nothing to configure — no API key, no account. Calls run through PerfLint's zero-log proxy to the hosted model.
Metered by your plan's AI credits: Free 10/day, Pro 5,000/month.
Toolbar LLM button → Advanced: bring your own API key. Pick Claude (Anthropic) or DeepSeek and paste the key.
Stored in local EditorPrefs only. Calls go direct to the provider, never through our servers, and are unlimited — never counted against credits.
Routine explanations use a cheap, fast model; migration-domain rules automatically use a stronger one.
Use it from your AI agent (MCP)
Unity's CLI exposes every Pipeline command as an MCP tool, and PerfLint registers its diagnosis as exactly those commands — so there is no separate MCP server to install. Point your agent at Unity's, and PerfLint's commands appear in its tool list alongside Unity's own. Your agent then asks a deterministic engine what's wrong instead of inferring it from files.
Requires Unity's com.unity.pipeline package and an open editor. One line:
unity mcp configure claude-code --project-path /path/to/YourProject
unity mcp configure --list # every supported client + where its config lives
Swap claude-code for claude, cursor, codex,
copilot-cli, windsurf, zed — or run --list to see
them all.
Three things that cost us time, so they don't cost you any:
- More than one editor open? Pin the project. Each editor runs its own Pipeline server, and without
--project-paththe CLI can't tell which one you mean — your agent ends up talking to the wrong project, or to none. - Restart the agent session. MCP servers are loaded when a session starts, so a session that was already running won't see the newly-added server. A health check that says “connected” only means the server starts — not that your open session can see it.
- It's the CLI's MCP server, not the in-editor panel.
Project Settings ▸ AI ▸ Unity MCPserves Unity's own built-in tool set; custom commands like PerfLint's don't appear there. Custom tools ride the CLI's Pipeline path.
unity mcp configure codex writes an
older [[mcp.servers]] table that current Codex doesn't read. If your agent reports no
PerfLint tools, add the server to ~/.codex/config.toml by hand instead:
[mcp_servers.unity]
command = "/absolute/path/to/unity"
args = ["mcp", "--project-path", "/path/to/YourProject"]
startup_timeout_sec = 120 Just ask, in your own words
This is the part worth trying first. You don't call the commands — you say what you want, and the agent works out which of them to run, in what order, and what it needs to check before touching anything. Paste any of these into your agent with the project open:
Apply the safe fixes with PerfLint. Scan with PerfLint and tell me which findings actually block the build. Use PerfLint to cut my build size — show me what's safe before you apply anything. Fix the Unity 6 migration blockers PerfLint found, one file at a time. On Unity's own Viking Village sample, “apply the safe fixes with PerfLint” scanned first, then stopped before writing anything — because disabling Read/Write on 95 model importers breaks any script that reads mesh data at runtime, so it went and checked:
Only hit is WaterSystemFeature.cs writing to a procedurally-built mesh — that's a
runtime Mesh, unaffected by import Read/Write. Nothing reads imported model geometry, so disabling it on
the 95 FBXs is safe.
Then 204 fixes, 0 failed, three findings handed back as judgment calls, under two minutes. That check is the whole point. Fix All applies the same 204 changes and is quicker to click — but a button cannot read your code, so it has to assume nothing reads mesh data at runtime. The agent verified it. Given 857 findings it also did the half a button can't: which five actually blocked the build, and why two-thirds of the rest were noise.
What your agent gets
Six tools, and you rarely name them yourself — the agent picks. Your agent sees them as MCP tools and you see them as CLI commands; they are the same thing underneath, with nothing extra to install or configure per tool.
| Command | What it does | |
|---|---|---|
perflint_scan | Findings by severity — Critical / Warning / Info counts, and how many are auto-fixable. | Free |
perflint_list_findings | The itemised problems behind those counts. Filter with --rule_id / --domain / --min_severity. | Free |
perflint_gate | Pass/fail against thresholds. Exit code is the verdict. | Free |
perflint_optimize_plan | --goal build|memory — what is safe to automate vs. what is your call, with the cost of each. | Free |
perflint_optimize_apply | Applies only the safe tier, re-scans, reports the verified delta. | Pro |
perflint_fix | The Fix All batch. Narrow it with --rule_id / --domain / --min_severity, preview with --dry_run. | Pro |
What it will and won't do on its own
The line is the same one PerfLint holds everywhere: waste is automatable; trade-offs are yours. Over the wire, apply only touches the safe, reversible tier — import-settings changes you can restore from version control (Unity's undo stack does not record them). Trade-offs (disabling Static Batching, enabling Mipmap Streaming) come back described with their cost and are left for you in the editor. Irreversible operations — merging duplicate assets, which deletes files — are never executed over the wire regardless of what the agent asks; they're reported and pointed back at the editor, where each still shows its own confirmation. That's enforced in the tool, not left to the agent's judgement. An open PerfLint window re-syncs itself after a run.
Headless CLI & CI
Two ways to drive PerfLint without clicking — they differ in whether an editor is running.
unity commandEditor openTalks to the editor you already have open, via Unity's CLI and its com.unity.pipeline package. No editor path, no -batchmode, nothing to close. Same commands your AI agent gets.
-batchmodeNo editorLaunches Unity headless and runs one entry point. This is what CI uses. Scanning and reports need no Pro licence; the analysis stays local and nothing in your project is modified.
Against an open editor
The same six commands your agent gets — see the table above. From a terminal they look like this:
unity command # every command, with its parameters
unity command perflint_scan # counts by severity
unity command perflint_gate # pass/fail; any Critical fails
unity command perflint_fix --dry_run # preview, then drop --dry_run to apply
Every figure these report comes from a re-scan rather than a tally of attempts, so a plain
perflint_scan after a fix run is the number that counts. A worked example — Unity's Viking
Village sample, and what the tool refused to touch — is on the blog.
Your AI agent can call all of these too; see Use it from your AI agent.
Headless, for CI
Three entry points, each launched the same way:
Unity -batchmode -nographics -projectPath . \
-executeMethod PerfLint.Ci.PerfLintCli.RunGate \
-perflintMaxCritical 0 \
-perflintReportHtml perflint-report.html \
-logFile - | Entry point | Does | Exit codes |
|---|---|---|
PerfLintCli.RunGate | Scans, checks your thresholds, fails the build when they are breached. | 0 pass · 1 gate failed · 2 error |
PerfLintCli.ExportReport | Writes the self-contained HTML report — handy as a build artifact. | 0 ok · 2 error |
PerfLintCli.RunFix Pro | Applies the deterministic, low-risk fixes, then re-scans and reports what changed. Trade-offs and AI fixes are never auto-applied. | 0 ok · 2 error · 3 Pro required |
| Flag | Effect |
|---|---|
-perflintMaxCritical N | Fail if Criticals > N. Default 0 — any Critical fails the build. This is the gate worth setting. |
-perflintMaxWarning N | Fail if Warnings > N. Off by default. |
-perflintMinScore N | Fail below a health score. Off by default, and kept mainly for existing scripts — severity counts say more about whether a build should ship. |
-perflintGateJson <path> | Write the verdict as JSON, if you would rather parse than read an exit code. |
-perflintReportHtml <path> | Also write the shareable HTML report. |
-perflintFixJson <path> | For RunFix: machine-readable result of what was applied. |
-perflintDryRun | For RunFix: report what would change without touching anything. (A run against an already-open editor is always dry-run.) |
-logFile - to stream Unity's output and PerfLint's live progress to your terminal. Without it everything goes to the Unity log and the terminal stays silent until the run ends — which on a large project looks exactly like a hang.-perflintLicense <key>, or the PERFLINT_LICENSE env var) and it persists. The gate and report export stay free.GitHub Actions
# .github/workflows/perflint.yml — self-hosted runner with Unity installed
name: PerfLint health gate
on: [pull_request]
jobs:
gate:
runs-on: [self-hosted, unity]
steps:
- uses: actions/checkout@v4
- shell: bash
env:
UNITY: /path/to/Unity # e.g. C:/Program Files/Unity/Hub/Editor/6000.5.0f1/Editor/Unity.exe
run: |
"$UNITY" -batchmode -nographics -projectPath "$GITHUB_WORKSPACE" \
-executeMethod PerfLint.Ci.PerfLintCli.RunGate \
-perflintMaxCritical 0 \
-perflintReportHtml perflint-report.html -logFile -
- uses: actions/upload-artifact@v4
if: always()
with:
name: perflint-report
path: perflint-report.html On a Windows runner under Git Bash, pass the project as -projectPath . from inside the project directory (absolute drive-letter paths can be mangled by msys).
Activating Pro
- Get a licence key. Get Pro — $9.99/mo, or $95.88/yr (save 20%). The key arrives by email.
- Open the License window. In Unity, the Free / Pro button in the PerfLint toolbar → License.
- Paste and Activate. Status flips to Pro, unlocking one-click and batch fixes, the Migration Assistant, and a larger monthly AI allowance.
Activation works offline for a grace period and re-checks periodically. Deactivate on a machine to free the seat for another.
Privacy
The scan is 100% local — your code and art assets never leave your machine. The only outbound data is, when you explicitly trigger Explain or AI Fix, the finding metadata or the single snippet you selected. By default it goes through PerfLint's proxy — which never logs request bodies — to deepseek; if a Pro user adds their own provider key under Advanced, it goes direct to the provider and never through our servers. License checks send only your license key.
One more path worth stating plainly: if you connect an AI agent over MCP, the findings it requests include asset paths and line numbers, and those go to that agent — a cloud model in most setups. The scan itself still uploads nothing (no code, no art), detection spends no tokens, and every tool response repeats this disclosure. If you'd rather nothing at all left the machine, don't connect an agent — the editor UI and the local CLI cover the same diagnosis.