I Built a Naming MCP Server for Claude Code and Codex
I built NamingSignal so Claude Code and Codex can turn a README into a naming brief, check domains, and return a source-backed shortlist through MCP.

Ask a chat model whether a domain is free and you get a confident sentence.
Run an actual registry lookup and you get this:
{
"domain": "zorbulant.com",
"status": "likely_available",
"checkedAt": "2026-08-27T16:26:39.688Z",
"provider": "Registry RDAP (rdap.verisign.com)",
"sourceUrl": "https://rdap.verisign.com/com/v1/domain/zorbulant.com",
"evidenceStatus": "inferred",
"confidence": "high",
"detail": "Registry returned 404 after its known-registered canary passed. The domain is likely unregistered, not guaranteed purchasable."
}
That is a real response, from a real check I ran while writing this. Look at what it refuses to say. Not "available." Not "you can buy this." It says a specific registry returned a 404 at a specific second, after a control domain that is definitely registered came back correctly, so the 404 probably means what it looks like it means.
The difference between those two answers is the entire reason I built NamingSignal, and it is why I ended up putting an MCP server in front of it.
Naming is a workflow, and I kept doing it badly#
Every tool on this site started the same way: a dead afternoon spent naming it.
The loop went like this. Ask a model for names. Get twenty variations on one root word. Pick five. Open a registrar in another tab. Check them one at a time. Find that three are taken. Go back for more names. Forget which ones I already rejected and why. Paste survivors into a spreadsheet. Come back two days later and re-check the same names because I no longer trust the spreadsheet.
The busywork was annoying. The part that actually bothered me was the trust problem. Somewhere in that loop, "a model told me this was free" and "a registry told me this was free" got mixed together, and by the time I was down to three finalists I could not tell which claims came from where.
So I stopped treating naming like a question with an answer and started treating it like a workflow with steps:
- Compile a brief from what the thing actually is, and look at it before generating anything.
- Generate a wide field of candidates in genuinely different directions, not one idea in fifty outfits.
- Check the domain endings you would really launch on, in bulk.
- Check developer namespaces on whatever survives.
- Research one to three finalists, properly.
- Keep the record: sources, timestamps, rejections, reasons.
Written out like that, it is obvious what kind of software this is. It is not a generator. It is a pipeline with evidence at each stage.
It is also, once you look at it, exactly the shape of thing an agent is good at.
Why this became an MCP server#
I already had a REST API and a CLI. Both work. But I noticed I never used them the way I designed them, because the interesting context was always in a repository I had open in Claude Code anyway.
The agent had the README. It knew what the project did. It knew who it was for, because it had been writing the thing with me for a week. That is true whether the session is building and deploying a whole site or fixing one route. And I was manually summarizing all of that into a form field, badly, so a naming tool could infer it back out.
That is the problem the Model Context Protocol solves. MCP is a standard way to hand an agent a set of tools it can call, with a schema, so it does not have to guess. I have written before about connecting Zapier's MCP server so Claude can work inside Google Drive, and the shape here is the same: the agent stops being a text box you paste things into and starts being the thing that runs the job.
So NamingSignal exposes five tools:
| Tool | What it does |
|---|---|
compile_project_brief | Turns a sentence, a prompt, or a README into an editable brief, with the gaps named |
create_naming_sprint | Generates the candidate field, checks the domain endings you chose, returns registry survivors first |
check_names | Exact domain checks, plus optional npm, PyPI, GitHub and Apple checks, for names you already have |
analyze_candidates | Source-backed research on one to three finalists |
get_purchase_links | Registrar search links for the manual final check |
Every one of them is annotated read-only. None of them spends money, registers anything, or contacts anyone. I will come back to why that matters.
Connect it in about a minute#
The server runs remotely at https://namingsignal.com/mcp over Streamable HTTP, so there is nothing to install.
You need a free API key first. Sign in at namingsignal.com, then create one in the developer console. Keys are user-owned and individually revocable, so make one per client: one for Claude Code, one for CI, one for a teammate's machine. Revoking one does not sign the others out.
Claude Code, one command:
claude mcp add --transport http naming-signal https://namingsignal.com/mcp \
--header "Authorization: Bearer YOUR_NAMINGSIGNAL_KEY"
Add --scope user if you want it available in every project instead of just this one.
Codex, four lines in ~/.codex/config.toml:
[mcp_servers.naming_signal]
url = "https://namingsignal.com/mcp"
bearer_token_env_var = "NAMING_SIGNAL_API_KEY"
startup_timeout_sec = 20
tool_timeout_sec = 360
bearer_token_env_var names the environment variable that holds the key, so the key itself never sits in a config file you might commit.
The timeout line is not decoration. Codex defaults to 60 seconds per tool call, and a large sprint runs for minutes in a single call. Claude Code has the same trap: set the per-server timeout in .mcp.json to 60000 or higher, or it stops waiting after 60 seconds. The full setup, including both timeout settings, is in the Claude Code quickstart.
Then paste something like this:
Use the naming-signal MCP server. Compile a naming brief from this
description: "<one sentence about the product, its user, and the painful
job it solves>". Show me the brief and wait for my corrections. Then run
create_naming_sprint with count 40 and TLDs com and dev, and summarize the
registry survivors with their evidence states, sources, and check dates.
Treat unknown as unknown, never as available.
The pause is the point#
Notice what that prompt does before it generates anything: it shows you the brief and stops.
I fought this for a while. It felt like friction. Every version I tested that skipped straight to names produced worse names, and the reason turned out to be boring: a wrong brief is invisible in the output. If the compiled brief thinks your product is for agencies when it is for solo founders, you do not see "wrong audience" in the list. You see a hundred perfectly reasonable names that are all slightly off, and you blame the generator.
So the brief is editable and it is shown first. Product, audience, the pain, the outcome, the mechanism, tone, what to avoid, and, importantly, what it could not work out from what you gave it. Unknowns stay marked as unknowns instead of being quietly invented.
That is the most valuable thirty seconds in the whole run. Read it. Fix the two things that are wrong. Then generate.
This is also the part where an agent beats a form. Correcting a brief in a chat turn is one sentence. Correcting it in a web form is eight fields.
Why a failed check has to stay unknown#
Here is the rule the whole product is built on, and the one I would keep if I had to throw everything else away.
A check that did not succeed is not good news.
A timeout is unknown. A rate limit is unknown. A domain ending with no usable lookup is unknown. A calibration that failed is unknown. None of them are "available."
This sounds obvious written down. It is surprisingly hard to hold onto, because every incentive in software points the other way. Unknown looks like a bug in your UI. Available looks like a result. When you are three hours into naming something and you want to be finished, "we could not check this one" is exactly the answer you are motivated to round up.
NamingSignal separates four states and never lets one become another:
- Confirmed. A direct source returned decisive evidence. The npm package exists. Here is the response.
- Inferred. A calibrated registry not-found. Likely unregistered at the time of the check, and nothing stronger.
- Unknown. A timeout, a block, an unsupported source, a conflict. Unresolved, and it stays that way.
- Manual. A human has to look. Here is the link.
The "calibrated" in inferred is doing real work. Before trusting a 404, the check confirms that the same registry correctly reports a domain that is definitely registered. If that control fails, the registry is having a bad day and the 404 means nothing, so the result drops to unknown. That is the known-registered canary passed line in the JSON at the top of this post. NamingSignal has a longer write-up on the reasoning in why domain availability is not a boolean.
You can use this rule without using my tool, by the way. Next time any AI tells you a name is free, ask it which source said so and when. If it cannot answer, it did not check.
What a real run costs#
Everything metered is priced in Naming Credits, and the free plan includes 15,000 of them per calendar month. No card.
| Operation | Credits |
|---|---|
| One name checked on one domain ending | 1 |
| Generation batch, up to 50 names | 500 |
| Ranking batch, up to 30 names | 500 |
| Researched finalist | 250 |
| Public URL import for the brief | 50 |
A 40-name sprint across two endings is one generation batch plus 80 domain combinations: about 580 credits. Add ranking and three researched finalists and you are near 1,830. So the free month covers several complete naming runs, which is roughly the right amount, because you should not need to name things every week.
The live schedule is published at https://namingsignal.com/api/v1/health, unauthenticated, so an agent can read the same numbers the meter uses instead of trusting a number in a blog post that might be stale. Including this one.
What it will not do, on purpose#
The agent cannot buy the domain.
It cannot reserve a name, contact an owner, negotiate, file a trademark, or tell you a name is legally clear. It returns a registrar search link and an explicit list of the manual actions still open.
People occasionally read that as a missing feature. I think it is the opposite. There is a real difference between a tool that gathers evidence and a tool that spends your money, and collapsing the two is how you end up with an agent that bought .com variations of a name you had already rejected. Read-only is a boundary I want, not one I am waiting to remove.
The same logic covers trademarks. The research output gives you namesakes, same-category collisions and preliminary starting points. It is a better first hour than you would do yourself. It is not clearance, and a tool that told you it was would be doing something worse than useless.
Where you still have to do the work#
An honest list, because the fun of this stuff is watching an agent run twelve steps and it is easy to forget which steps it cannot run:
- Does it sound right out loud? Say the finalists in a sentence. "Hi, this is Moe from ___." Half of a shortlist dies right there and no amount of evidence predicts it.
- Does it mean something bad somewhere? Automated checks do not cover a word that is fine in English and unfortunate in another language your users speak.
- Is the domain actually purchasable, and at what price? Likely unregistered and available at a normal price are different claims. Go and look.
- Does it still fit in three years? A name that describes exactly what version one does can become a cage. Worth thinking about before you love it.
- Legal. If you are serious, this is a professional's job, not an API's.
The agent gets you from a blank page to three defensible finalists with receipts. The last mile is judgment, and it should be.
When a manual process is still fine#
If you are naming one internal script, open a registrar, type a word, and get on with your day. This is over-engineering for that.
The workflow earns its keep when at least two of these are true: the name is going on something you will have to live with for years, there is a domain you actually need, there is a crowded namespace to survive (npm and the app stores are brutal), or more than one person has an opinion and you need the reasoning written down so the argument only happens once.
That last one surprised me. The most useful output is not the name. It is the record of why the other 147 names lost.
Try it#
If you already have Claude Code or Codex open, the setup above takes about a minute and the first sprint costs a few hundred of your free monthly credits.
The full breakdown of the evidence model, the four access surfaces, and what the product deliberately does not do is on the NamingSignal project page. If you would rather just use it in a browser, start at namingsignal.com, and if you are wiring it into something else, the REST contract, CLI reference and MCP setup all live in the developer documentation.
And if you take one thing from this and never touch my tool: when something tells you a name is free, ask it who said so, and when.