deprecation radar for code

Your vendor's changelog just became a deadline.

Changelogs are prose. Your repo is code. Nothing connects the sentence to the line. Sunset matches a curated claim's surface tokens against your files and tells you which call sites break, and how many days you have left — then fails the policy when the answer is “not enough”.

live demo

Edit the code. Watch the findings move.

The sample repo has four files and five call sites: three matching surfaces, one stale pinned API version, and one unrelated service that should not be flagged. Everything below is computed by the same POST /api/scan you can call.

— lexical scan · no LLM · no network
policy SCANNING
30 days

Any finding with fewer days left than this fails the policy.

findings — claims — files — violations — in comments —

Findings

sorted by urgency

report.md

scanning…
the claim ledger

Claims only exist if the quote is in the document.

Each claim carries the verbatim sentence it was cut from. On load, Sunset re-checks that the quoted span literally appears in the stored vendor excerpt — the anchored chip is that check, not a promise. No quoted span, no claim. These ten are curated examples written for this demo, not a live vendor feed.

Why anchoring matters: a deprecation tool without a source quote is just a vibes-based linter. Every finding below can be traced back to a sentence someone can read.

why this exists

Three sentences, zero links to your code.

01 / prose

Changelogs don't know your repo

“The legacy endpoint stops accepting requests on 31 March 2027” is true and useless until someone greps for it. Grep doesn't know which of 40 matches matter.

02 / syntax

Call sites are syntactic

A call site is an identifier, a method chain, a pinned version string. Those are matchable without an LLM, reproducibly, in CI, on every pull request.

03 / policy

Deadlines are policy

“Fail if any match has fewer than 30 days left” turns a blog post into a merge gate. The number is yours; the enforcement is the product.

method

Lexical, deterministic, boring on purpose.

No model call, no embeddings, no “AI-powered” asterisk. The same input produces the same findings, which is what a merge gate needs.

1

Extract

Read each file, strip line and block comments (keeping string state), and keep the remaining code text with line numbers.

2

Match

For each claim, require all of its surface tokens to appear with word-ish boundaries. Tokens are identifiers, method chains, paths, and pinned version strings.

3

Score

Days left = effective date − today, in whole UTC days. Severity comes from the claim, not from the match.

4

Enforce

Every match with days left below the policy threshold becomes a policy violation and flips the verdict to FAIL.

// one claim, one file match = all(tokens).found_in(code_without_comments) days = ceil((effective_date - today) / 1d) verdict = any(days < policy_days) ? FAIL : PASS // claims are anchored: quote must exist in vendor_doc_text claim.exists = vendor_doc_text.includes(quote) // else no claim
api

Three endpoints. That's the whole surface.

# the ledger, with anchor status
GET /api/claims

# four files + default policy
GET /api/sample-repo

# scan a snippet or a whole repo
POST /api/scan
{ "code": "stripe.charges.create({...})",
  "file": "payments.ts",
  "policyDays": 30 }
// response shape
{
  "matches": [{
    "file": "payments.ts", "line": 9,
    "claimId": "stripe-charges", "vendor": "Stripe",
    "daysLeft": 147, "severity": "critical",
    "quote": "The legacy charges.create…",
    "migration": "Replace with paymentIntents…"
  }],
  "counts": { "matches": 4, "policyViolations": 2 },
  "policyViolations": [ ... ],
  "reportMarkdown": "# Sunset scan report…"
}
honest limits

What this does not do.

A tool that hides its edges is a demo. These are the edges.

Matching is lexical

A wrapper like charge() that calls charges.create elsewhere hides the usage. Dynamic construction, aliases, and generated clients defeat token matching. Findings are candidates, not proof.

Vendor docs change

Quotes, dates, and URLs drift. The ten claims here are curated examples with plausible prose, not a live feed. Re-anchor claims against the vendor page before trusting a date.

Free report ≠ paid policy

The scan is advisory. Making it a merge gate — scheduled re-scans, per-repo policy files, ownership routing, audit history — is the part that costs money. This page deliberately stops at the report.