Books

Growth 365

Tomas Laurinavicius

ChaptersThe Ghost-Product Radar

The Ghost-Product Radar

Find unshipped products in public certificate logs.

A company can keep a product secret right up until the moment its engineers request an HTTPS certificate for it. The instant that happens, the certificate authority logs it in a public, append-only ledger that anyone can query, because the browser industry made Certificate Transparency mandatory after a run of trust failures. Nobody thinks about the log when they spin up qa-newthing.company.com to test a feature nobody has announced. You should. It is sitting there in plain text, timestamped, forever.

What to do: curl -s "https://crt.sh/?q=%25.site.com&output=json", then filter the hostnames for dev, staging, preprod, qa, sandbox, and admin. Or run the same search directly at crt.sh.

Why it works: Every public certificate authority streams every certificate it issues into a public log the moment it issues it. A subdomain exists in that log whether or not the product behind it ever ships.

Example: Stripe's certificate-transparency history for *.stripe.com holds 2,246 logged cert rows, covering 173 distinct non-wildcard hostnames by the SAN method described below. Sixty-six of those match a ghost-project keyword, including qa-pandora-v2-test.stripe.com and preprod-public-goods.stripe.com.

Walk it through

I ran this against stripe.com in July 2026. Here is exactly what came back.

1. Pull every certificate ever logged for the domain.

curl -s -o stripe_crt.json -w "%{http_code}\n" "https://crt.sh/?q=%25.stripe.com&output=json" --max-time 20

Terminal showing a curl request to crt.sh timing out with status 000, a retry succeeding with 200, and the resulting file at 977603 bytes holding 2246 cert rows

First request timed out at 20 seconds. crt.sh runs on a slow Postgres box and a chunk of requests just hang or come back 502. Second attempt came back clean: 200, 977,603 bytes, 2,246 cert rows logged for *.stripe.com. Budget for at least one retry every time you run this, it is not your connection.

2. Or skip the terminal and run the same search in a browser.

crt.sh's identity-search results for stripe.com, listing common names including jss.qa.corp.stripe.com and jira.corp.stripe.com alongside public hosts like dashboard.stripe.com and api.stripe.com

crt.sh's own identity-search page lists every logged cert with issue date, expiry, and common name. No login, no API key, no rate limit warning on casual use. Scan the Common Name column and internal-looking hosts are already sitting right next to the public ones, jss.qa.corp.stripe.com and jira.corp.stripe.com a few rows from dashboard.stripe.com and api.stripe.com.

3. Count subdomains two ways, then filter for the ghost words.

Terminal showing subdomain counts by two methods, 99 unique common names versus 199 unique SAN entries, then a grep for dev, staging, preprod, qa, admin, and sandbox turning up 66 matches out of 173

One cert row carries one common_name, but its name_value field packs every SAN on that same cert into a newline-joined string. Split it and the count changes: 99 unique common_name values (87 once you strip *.stripe.com wildcards) versus 199 unique SAN entries (173 non-wildcard). State which method you used or the number means nothing to anyone checking your work. I'm reporting the SAN method here, 173 real hostnames. Grep those 173 for dev, staging, preprod, qa, admin, and sandbox and 66 match, including qa-donate.stripe.com, qa-pandora-v2-test.stripe.com, preprod-public-goods.stripe.com, qa-book.stripe.com, and connections-sandbox.stripe.com.

The read

Three things to check before you draw a conclusion from a cert log.

  • The count depends on the method, always say which one. Common-name counting and SAN counting gave 99 and 199 off the identical dataset. Neither is wrong, they are answering slightly different questions, so state your method next to any number you quote.
  • The name is a hint, not a confirmation. qa-pandora-v2-test and preprod-public-goods read like internal project codenames for something not yet public. A cert existing only proves someone provisioned HTTPS for a host, not that a product is coming or still alive behind it.
  • Change over time is the real signal. Re-run the same query next month. A ghost host that disappears from the log got decommissioned. One that flips from preprod- to a bare production name just shipped.

Steal it

Run this against your own domain before you run it against anyone else's. If your qa-, staging-, or preprod- hosts are getting certs from a public CA, they are already in the log, named exactly what your team calls the project internally. Put internal tooling behind a private CA or an internal-only cert authority, or at minimum stop naming test infrastructure after the product.

Against a competitor, treat a ghost hostname as a lead, not a headline. preprod-public-goods.stripe.com tells you Stripe has something called "public goods" in a pre-production environment. It does not tell you what it does or when it ships. Log it, check back monthly, and watch for the host to either vanish or go live. That cadence is the actual intelligence, one snapshot is just a rumor.

Gotchas

  • crt.sh is genuinely flaky. Expect 502s and hung connections under load, not just on this domain. Retry with backoff and don't treat a bad response as "no data."
  • Wildcard entries inflate raw counts fast. *.corp.stripe.com and its siblings show up as single cert rows but represent unlimited hosts. Always strip the *. entries before quoting a subdomain figure.
  • This is a lookup tool, not a scraper target. Querying a handful of domains by hand is exactly what crt.sh is for. Scripting thousands of automated queries against it is the kind of load that gets the public good rate-limited for everyone. Don't do that.