Skip to main content

Skylos cleanup

skylos cleanup turns quality, AI-code and dead-code findings into a focused workflow: choose a task, inspect its evidence, preview a supported patch, apply it explicitly, and check the result.

Detection comes from Skylos's existing rule engines. Cleanup adds the work queue, source context, ordered plans and explicit edit/check loop. Each task names a rule, file, line and reason; it does not identify who wrote the code or assign an AI-authorship score.

These options describe current development source. Check skylos cleanup --help in your installed release before using a new option. The stricter Python replacement verification and test reachability/collection handling described below are preview changes in PR #1207 and require a CLI build containing those changes.

The default scan leaves source unchanged and saves task history locally. Tests run only with --test-cmd; model review runs only with --review. The default cleanup scan does not query dependency registries or upload results.

Build a queue​

Run from the repository root, or pass a source file or directory:

skylos cleanup . --next
skylos cleanup . --top 5
skylos cleanup src --format json
skylos cleanup . --all-advice
skylos cleanup . --diff origin/main --context

The path defaults to .. Human output is the default; --format json supports agents and scripts. --top N accepts a positive integer and defaults to 10. It limits each queue separately while keeping the full eligible counts.

Defects and findings needing contextual review appear in tasks. Maintainability recommendations appear in advisories. Optional advice follows the existing listing policy; --all-advice includes it without changing raw severity or gate policy. JSON retains the original finding under finding.

Tasks include a rule, location, severity, finding purpose, original evidence and suggested next action. Related items are grouped by rule and directory; that grouping helps review and does not prove a shared root cause.

--diff BASE scans the full Git project and selects tasks in changed files, including staged, unstaged and untracked source. It pins the Git comparison and retains the complete inventory in local history. A finding in a changed file can predate your edit; this is a review selection, not proof of a new defect. Saved reports cannot provide this live diff context.

Review Python test quality​

Preview: requires a CLI build containing SKY-L040–SKY-L043 (SKY-L044–SKY-L047 are not yet released); older installed versions do not emit these findings.

Quality scans include eight bounded checks for selected Python pytest and unittest tests. They emit LOW review findings, which enter the cleanup task queue for manual review:

RuleEvidence to review
SKY-L040A literal-only assertion is always true and cannot check a failure
SKY-L041A test has only a docstring, pass, or ellipsis, without known fixture/setup backing
SKY-L042Adjacent identical assertions repeat a check of unchanged, proven builtin values
SKY-L043A fixed sleep immediately precedes a local Event completion assertion
SKY-L044A test reads only values it builds itself, so no project code can change its result
SKY-L045An assertion is true for every value, such as len(x) >= 0 or assert (x == 1, "message")
SKY-L046A test stores a result it never checks and has no assertion
SKY-L047A test repeats an earlier test's decorators, parameters and body
skylos . --quality
skylos . --quality --format json
skylos cleanup . --top 5 --context

These commands inspect source without running tests or requesting model review. The selector respects configured pytest collection, skipped/xfail scopes and test opt-outs. Unknown wrappers, helper scopes and golden fixtures do not become test subjects. Fixture arguments, local hooks, known autouse/usefixtures marks, and possible ancestor conftest.py checks prevent empty-body findings. Proven loop jumps and returns keep unreachable statements out of test-quality advice. Collection metadata changes apply to the affected test while preserving eligible sibling tests.

Review the intended behavior and make any change manually, then rescan the same scope. These checks do not establish AI authorship, general assertion coverage, or passing runtime behavior, and have no supported automatic cleanup edit.

Preview and apply one task​

Use an ID from the report. Human output shows unique prefixes; JSON contains the full IDs.

skylos cleanup . --task TASK_ID
skylos cleanup . --task TASK_ID --apply
skylos cleanup . --task TASK_ID --apply --test-cmd "pytest -q test/test_orders.py"

--task previews a deterministic patch. --apply writes the selected patch and rescans the same target. Choose a test command for the affected behavior; it runs without shell interpretation. Check callers, entry points and dynamic use before accepting dead-code removal.

Pytest test runs produce fresh JUnit evidence automatically. For another runner, have the authorized command write a report and supply its relative path:

skylos cleanup . --task TASK_ID --apply \
--test-cmd "YOUR_RUNNER_WITH_JUNIT_OUTPUT" --junit-report reports/tests.xml

Supported edits are limited to these cases:

RuleSupported changeCases requiring manual review
SKY-U001 in PythonDelete a conservatively matched unused functionDecorators, defaults, annotations, ambiguous source anchors or uncertain use
SKY-U002 in PythonDelete an unused import statement from an allowlist of standard-library modulesLocal or third-party imports, from imports, possible project shadowing or other import effects
SKY-L038 in PythonSimplify a proven f-string conversion, such as str(value) to !sA rewrite the detector cannot freshly prove, including shadowed builtins and debug fields whose expression text contributes to output
SKY-U002 in TypeScript/TSXRemove one explicit unused named import type binding from a same-directory local providerValue or mixed imports, ambient declarations, ambiguous providers and unsupported module resolution

The patch is bound to the exact scanned source and is revalidated before writing. A stale or unsupported task must be rescanned or changed manually. This command does not provide general automatic refactoring.

The TypeScript subset requires a supported local tsconfig, another module marker and a self-contained structural type provider. Provider/configuration hashes and resolution alternatives are checked again before application and after checks. Other TypeScript tasks remain review work. No compiler, runtime or package script runs by default.

Read verification receipts​

An edit has separate tests and rescan receipts in JSON. Inspect them even when the command completes successfully.

Execution statusMeaning
verifiedFresh observed tests passed and a complete comparable rescan removed the target without new defects or high-severity review findings
applied_unverifiedThe patch remains applied, but the required verification evidence is missing, such as skipped tests
incompleteA requested check or comparable rescan could not complete; inspect the receipt and current file
failedA check failed; inspect the rollback receipt to see whether the original source was restored

verified describes the recorded checks, not universal behavioral proof. Rollback only replaces a file that still matches the applied patch, so an intervening edit is preserved. A finding disappearing by itself is not a passing test result.

An opaque command exiting zero is insufficient for verified: passing tests must be observed through fresh JUnit results. Test count, evidence type and whether changed Python lines were exercised remain separate. A Python replacement stays applied_unverified when tracing shows that its changed lines were not exercised. Unknown exercise requires a completed bounded source-effect proof before the replacement can be verified. An affirmative tracing miss is never overridden by that model. Deletion-only edits have no replacement lines to trace; their verification is limited to observed tests and the comparable rescan, and the receipt records that limitation.

Apply checks include static security and secrets analysis before and after the edit, alongside quality, AI-code and dead-code checks. They do not enable dependency registry checks. Receipts record the categories checked. A bounded Python source-effect model can report equivalence, differences or unknowns; it does not execute the program or establish general runtime equivalence.

Keep local work history​

skylos cleanup . --defer TASK_ID --reason "Review public callers first"
skylos cleanup . --restore TASK_ID
skylos cleanup . --history --format json
skylos cleanup . --no-state

History lives in .skylos/cache/cleanup.json and is scoped to the scan target, scanner version and project configuration. An incomplete or differently scoped scan cannot close earlier work. A task absent from a complete comparable scan becomes not_reported; this does not mean its behavior was verified.

IDs can survive line-only shifts when the syntax anchor stays unchanged. Substantive source, evidence or path changes can change them. Deferring a task changes the local work queue without suppressing the finding or changing gate policy. --no-state disables history reads and writes; it cannot be combined with history actions.

On platforms without the guarded filesystem operations needed for history, use --no-state to build the queue. Deterministic edits also require those operations and remain unavailable there.

Organize an ordered local plan​

skylos cleanup . --create-plan imports --plan-task FIRST_ID --plan-task SECOND_ID \
--prerequisite "Review public callers" --acceptance-check "pytest -q"
skylos cleanup . --plan imports
skylos cleanup . --plan imports --move-task SECOND_ID --before FIRST_ID
skylos cleanup . --plan imports --complete-task FIRST_ID --note "Reviewed manually"
skylos cleanup . --plans

A plan stores explicitly selected anchored tasks in your chosen order and scope. Named plans currently require Python syntax anchors; supported TypeScript import edits can be selected directly with --task. Source changes can make a step stale. A missing finding never completes it, and manual completion stays unverified. Stale completion requires a note.

Prerequisites and acceptance checks are recorded text. Adding a command there does not execute or authorize it.

Add source context or model review​

skylos cleanup . --context --format json
skylos cleanup . --review --provider anthropic --model YOUR_MODEL
skylos cleanup . --reviews
skylos cleanup . --plan imports --promote-review REVIEW_ID

--context includes bounded Python and TypeScript/JavaScript excerpts, static graph impact, candidate callers and suggested test files while respecting scan exclusions. Human output marks the reported line among nearby source lines. Source-resolved relationships and simple-name candidates stay distinct; neither proves runtime reachability. Suggested tests do not authorize execution. Graph coverage and budget limits remain visible. Other languages retain their scanner evidence.

--review sends the bounded context to the configured model and returns separately labeled subjective advice with source citations. It requires the LLM extra and provider configuration; hosted providers may charge for calls. Use --model, --provider and --base-url to select the model setup. Model review is separate from patch application and does not authorize source edits.

Completed reviews persist locally with citations, model/provider details and source/context hashes unless --no-state is set. --reviews distinguishes current and stale advice. Explicit promotion adds current advice to a named plan as review_advice; it cannot create a scanner defect, authorize an edit or count as verification evidence. Freshness covers the cited excerpts and bounded context dependencies, not an entire Git revision. Newly added or unexamined files can require a fresh review.

Reuse a saved report​

skylos cleanup . --from-report findings.json --format json

--from-report accepts existing Skylos analyzer JSON. Supply the original scan root as the path so locations stay meaningful. Output records source: saved_report; analyzers are not rerun. Missing analyzers or coverage information make the queue incomplete. Saved reports cannot authorize edits, model review or history changes; those operations require a live scan.

Read the result​

StatusExitMeaning
ready0Visible review work is available
clear0No visible work in the recorded cleanup scope
incomplete2Analysis, coverage or requested verification is incomplete; inspect the available evidence

Invalid input also exits 2. An explicit edit whose checks fail exits 1. Exit 0 alone does not establish that tests ran. These statuses describe the operation and recorded scope, not a security verdict. Language coverage follows the underlying analyzers, while deterministic edits have the narrower limits above.

The separate skylos clean command previews or applies Python unused-import and unused-function edits. See CLI Reference.

Cloud Cleanup workspace​

Upload through the existing scan flow:

skylos . --quality --ai-defects --upload

The Cloud Cleanup workspace projects tasks from a selected native code scan, defaulting to the latest available source. Choose a branch/source scan and an optional comparison independently of an active removal PR's original source. Choose a current task or move to the next one. Related work uses the existing issue group, or the same rule and folder when no shared issue is recorded. Review whether a shared fix actually applies.

Each task shows recorded evidence and source context, including the scan, branch, revision and completeness limits. Copy task includes those identifiers and a bounded source excerpt for an agent. Partial loading or incomplete analysis remains visible rather than becoming an empty complete queue.

Where a shared issue exists, the workspace uses its existing assignment, work status and comments for ownership and outcome notes. Available actions follow the workspace role. Record the commit or PR, checks run, and reasons for deferral there. Changing work status does not resolve scanner findings; comparable follow-up scans determine whether the issue is still reported.

Existing constrained removal-PR eligibility remains separate from task visibility. The broader workspace does not automatically rewrite every task. CLI observation IDs do not authorize Cloud resolutions.

Explicit scan uploads can also include up to 20 valid local cleanup outcome receipts from the Git root and selected upload root. If cleanup ran in a subdirectory, upload that same path to include its receipts. This metadata contains allowlisted IDs, relative paths, hashes and check outcomes; it excludes test commands, logs and source excerpts. Normal uploaded findings retain their own evidence policy.

Cloud displays these as client claims, including recorded test counts, changed-code exercise and actual checked categories. A working-tree result remains unbound; committing later does not rebind its old test evidence. Even a reported clean outcome head matching the upload does not independently prove test execution, coverage or behavior preservation. CI identity identifies the uploader, not whether those checks ran. Receipts alone never pass a gate or resolve an issue.

Comparable progress uses complete raw inventories, including optional and suppressed findings, and requires compatible recorded scope, root, version, check profile, analyzer configuration claims and trusted source scans. Missing evidence shows Progress not checked, with unknown counts. A Done check-policy digest does not establish analyzer configuration equivalence. Covered disappearance is not reported, separate from behavior verification and shared issue resolution. These Cloud source changes require the normal application deployment before they appear on the hosted site.

Check skylos cleanup --help after installing a release that includes this command.