Every change Wellknown observed on this MCP server, newest first, with what it was before and what it became. Tool-surface changes carry the definition diff. Nothing here is edited after the fact.
Changed the definition of "get_grid" and "put_item"
GET /: the grid the API key opens: its name,and its limit on items, `max_items` (queries included; null:nono limit), and the `embedder` it embeds content with..
⟨56 unchanged words⟩ emb a list of floats from the grid'sembedder.model. DNA embeds the rest itself and keeps it ⟨62 unchanged words⟩
Certificate changed, valid to 2027-01-28
Added "delete_grade", "delete_grid", "delete_item" and 5 more; removed "delete_node", "get_node", "grade" and 2 more; changed the definition of "create_grid", "create_query", "get_grid" and 2 more (12 tools before, 15 now)
POST /: create a grid, your own store ofnodes;items; no API key needed. Returns its `api_key`, ⟨17 unchanged words⟩ `Authorization: Bearer hg-…`. It holds up to`max_nodes``max_items`nodes.items, queries included. Each address may create only a few grids a day.
POST /queries: store a question to ask of the Added "create_query", "delete_query", "get_query" and 4 more; removed "create_edge", "create_node", "delete_edge" and 5 more; changed the definition of "create_grid", "delete_node", "get_grid" and 2 more (13 tools before, 12 now)
POST /: create a grid, your ownspacestore ofnodes and scores;nodes; no API key needed. Returns its `api_key`, shownonly now:pass it as `api_key` to every other tool, or send it as the header `Authorization: Bearer hg-…`.It holds upto `max_nodes` nodes. Each address may create only ⟨5 unchanged words⟩
Certificate recorded, valid to 2026-11-28
Authorization not required
Added "create_grid"; changed the definition of "create_edge", "create_node", "delete_edge" and 9 more (12 tools before, 13 now)
{"properties":{"api_key":{"anyOf":[{"type":"string"},{"type":"null"}],"default":null,"title":"Api Key"},"nid":{"title":"Nid","type": ⟨13 unchanged words⟩
{"properties":{"api_key":{"anyOf":[{"type":"string"},{"type":"null"}],"default":null,"title":"Api Key"},"emb":{"items":{"type":"number" ⟨20 unchanged words⟩
Unknown → Live
First tool surface recorded: 12 tools (server version 1.1.0)
https://dna.hashgrid.ai/mcp (mcp_streamable_http) — from mcp_registry, with the record
Showing the latest 10 events. The API returns up to 500 and filters by kind: ?kind=tool_surface_changed
⟨25 unchanged words⟩ ,"title":"Content"},"type":{"defaultanyOf":[{"text/plaintype":"string"},{"titletype":"Typenull"}],"typedefault":null,"stringtitle":"Type"}},"required":["content"],"title ⟨3 unchanged words⟩
GET /: the grid the API key opens: its name,the mostitsnodeslimititonholdsitems,`max_nodes``max_items` (queries included; null: nolimit), and the`embedder`its`embedder`nodesitareembedsembeddedcontent with.
GET /queries/id/results: `results`, the query's bestnodesitems under any of `prefixes` (e.g. ["/items/tools/"]; allnodesitems bydefault), best first, each with its `score`,theDNA'spredictedestimate of the gradefromyou-1wouldtogive1it (on the grades' scale once the grid has some; before,andonlyitsthe`preview`order means anything), aslist_nodeslist_items shows it,it.without content. `ungraded`: leave out thenodesitemsityougraded.already graded for this query. Grade what you judged,andwith put_grade: thenextresults learn fromit.it within a few seconds.
{"properties":{"result":{"items":{"additionalProperties":true,"type":"object"},"title":"Result","type":"array"}},"required":["result"],"title":"get_resultsOutputget_resultsDictOutput","type":"object"}
GET /queries/id/grades: `grades`, the query's grades, {"key", "score"}, in path order.
{"properties":{"result":{"items":{"additionalProperties":true,"type":"object"},"title":"Result","type":"array"}},"required":["result"],"title":"list_gradesOutputlist_gradesDictOutput","type":"object"}
DELETE /queries/id/grades/key: forget the query's grade of the item at `key`.
DELETE /: delete the grid and everything in it, items, queries and grades; its key stops working.
DELETE /items/key: delete the item at `key`, and every grade of it.
GET /queries/id/grades/key: the query's grade of the item at `key`.
GET /items/key: the item at `key`, with its `content` as put_item takes it.
GET /items?prefix=: `items`, those whose keys start with `prefix` (e.g. "tools/"; all by default), in key order, without their content (get_item reads one), at most `limit` (1 to 100, 32 by default). `next`: for the next page, pass it as `after` (null: this was the last).
PUT /queries/id/grades/key: grade the item at `key` (as get_results returns it, e.g. "42") for the query `id`. `score` is from -1 (wrong) to 1 (right), anything between for partly right; it trains DNA and replaces the grade before. Grade the results you judged, typically the first few.
PUT /items/key: write the item at `key` (e.g. "42", no leading /), creating it or replacing its content. Text is a string and a record a JSON object, each up to 8 KB; an image its bytes as base64, kept as a WebP of at most 512 px (its width and height come back); an emb a list of floats from the grid's embedder. DNA embeds the rest itself and keeps it only to embed it again; results and listings never return it. `type` is one of text/plain, application/json, image/png, image/jpeg, image/webp, image/gif, application/vnd.hashgrid.emb+json; leave it out for text, a record or an emb, which DNA te…
DELETE /nodes/path: delete the node at `path`, and every grade of it.
GET /nodes/path: the node at `path`, with its `content` as put_node takes it.
PATCH /queries/id/grades: `grades` is a list of {"key": path, "score": s}, for nodes as get_results returns them. A score from -1 (wrong) to 1 (right) trains DNA and replaces the one before; null forgets it.
GET /nodes?prefix=: `nodes`, those whose paths start with `prefix` (e.g. "/items/"), in path order, each with a `preview`: all of its content under 8 KB, else its head (a text's first 8 KB, a record with long values cut, an image's thumbnail), an image as a data: URL, and `truncated`, whether it is less than the content; at most `limit` (1 to 1024). `next`: for the next page, pass it as `after` (null: this was the last).
PUT /nodes/path: write the node at `path` (e.g. "/items/42"), creating it or replacing its content. `type` is one of {TYPES}: text is a string, a record a JSON object, an image its bytes as base64, an emb a list of floats from the grid's embedder. DNA embeds the rest itself. Returns the node: its key, type, size, etag, ctime and mtime.
DELETE/nodes/{nid}/nodes/path: deleteathe nodeand every edge from or toatit;`path`,itsandscoreseverynogradelongeroftrain.it.
⟨8 unchanged words⟩ ":null,"title":"Api Key"},"nidpath":{"title":"NidPath","type":"string"}},"required":["nidpath"],"title":"delete_nodeArguments","type":"object"}
GET /: the grid the API key opens: its name,andthe most nodes it holds, `max_nodes` (null: no limit)., and the `embedder` its nodes are embedded with.
GET/nodes/{nid}/nodes/path:athe node at `path`, with itskey (null if it has none)`content`andasitsput_nodeembeddingtakes`emb`.it.
⟨8 unchanged words⟩ ":null,"title":"Api Key"},"nidpath":{"title":"NidPath","type":"string"}},"required":["nidpath"],"title":"get_nodeArguments","type":"object"}
GET/nodes/nodes?prefix=:the`nodes`,grid'sthosenodeswhose paths start with `prefix` (e.g. "/items/"),eachin path order, each with a `preview`: all of itsidcontent under 8 KB,keyelseanditsembhead (a text's first 8 KB,inaidrecordorder.with`limit`long values cut, an image's thumbnail), an image as a data: URL, and `truncated`, whether it is less than the content; at most `limit` (1 to1024;1024). `next`: for thenext page, passtheitlastasid`after`as(null:`cursor`.this was the last).
{"properties":{"api_keyafter":{"anyOf":[{"type":"string"},{"type":"null"}],"default":null,"title":"Api KeyAfter"},"cursorapi_key":{"anyOf":[{"type":"string"},{"type":"null"}],"default":null,"title":"CursorApi Key"},"limit":{"default":32,"title":"Limit","type":"integer"},"prefix":{"default":"/","title":"Prefix","type":"string"}},"title":"list_nodesArguments","type":"object"}
{"properties":{"result":{"items":{"additionalProperties":true,"type":"object"},"title":"Result","type":"array"}},"required":["result"],"title":"list_nodesOutputlist_nodesDictOutput","type":"object"}
POST /queries: store a question to ask of the nodes, its content as put_node takes it. Returns its `id`, which the other query tools take. It can be searched with get_results at once.
DELETE /queries/id: delete the query `id` and its grades.
GET /queries/id: the query `id`, with its `content` as create_query takes it.
GET /queries/id/results: the query's best nodes under any of `prefixes` (e.g. ["/items/"]; all nodes by default), best first, each with its `score`, the predicted grade from -1 to 1, and its `preview` as list_nodes shows it. `ungraded`: leave out the nodes it graded. Grade what you judged, and the next results learn from it.
PATCH /queries/id/grades: `grades` is a list of {"key": path, "score": s}, for nodes as get_results returns them. A score from -1 (wrong) to 1 (right) trains DNA and replaces the one before; null forgets it.
GET /queries/id/grades: the query's grades, {"key", "score"}, in path order.
PUT /nodes/path: write the node at `path` (e.g. "/items/42"), creating it or replacing its content. `type` is one of {TYPES}: text is a string, a record a JSON object, an image its bytes as base64, an emb a list of floats from the grid's embedder. DNA embeds the rest itself. Returns the node: its key, type, size, etag, ctime and mtime.
POST /nodes/{nid}/edges, the search: from query node `nid`, the best node it has not been shown yet, among those whose key starts with `prefix` ("" for any), stored as a new edge: `id` is the found node's id, `score` is null until you score it (update_edge). Null when nothing is left. Call again for the next.
POST /nodes: add a node. An item gets a `key`, a path unique in the grid (e.g. "/items/42"), so searches can find it; a query gets none. `emb` is its embedding, 1 to 2048 floats from any model; use one model per grid. Returns its id and key (not its emb, to keep replies short; get_node has it).
DELETE /nodes/{nid}/edges/{eid}: forget a result, so it can be suggested again; its score no longer trains.
GET /nodes/{nid}/edges/{eid}: one result of query `nid`, and its score (null if not scored).
GET /nodes/{nid}/edges: a query's results so far, each an edge with the found node's `id` and its `score` (null if not scored), in id order. `limit` is 1 to 1024; for the next page, pass the last id as `cursor`.
PUT /nodes/{nid}/edges/{eid}: score how well node `eid` fits query `nid`, from -1 (wrong) to 1 (perfect), creating the edge if DNA never suggested it, e.g. scores you already have. Only scores train DNA; a new score replaces the last.
PATCH /nodes/{nid}/edges/{eid}: score a result of query `nid` that create_edge returned, from -1 (wrong) to 1 (perfect). Only scores train DNA; a new score replaces the last.
PATCH /nodes/{nid}: change a node. `key`: a new path, or null to remove it, so the node can no longer be found; leave it out to keep it. `emb`: a new embedding; leave it out to keep it. Its scores keep training, on the new embedding. Returns its id and key.
{"properties":{"api_key":{"anyOf":[{"type":"string"},{"type":"null"}],"default":null,"title":"Api Key"},"eid":{"title":"Eid","type": ⟨13 unchanged words⟩
{"properties":{"api_key":{"anyOf":[{"type":"string"},{"type":"null"}],"default":null,"title":"Api Key"},"nid":{"title":"Nid","type": ⟨7 unchanged words⟩
{"properties":{"api_key":{"anyOf":[{"type":"string"},{"type":"null"}],"default":null,"title":"Api Key"},"eid":{"title":"Eid","type": ⟨13 unchanged words⟩
GET /: the grid the API key opens: its name,byandname.the most nodes it holds, `max_nodes` (null: no limit).
{"properties":{"api_key":{"anyOf":[{"type":"string"},{"type":"null"}],"default":null,"title":"Api Key"}},"title":"get_gridArguments","type":"object"}
{"properties":{"api_key":{"anyOf":[{"type":"string"},{"type":"null"}],"default":null,"title":"Api Key"},"nid":{"title":"Nid","type": ⟨7 unchanged words⟩
{"properties":{"api_key":{"anyOf":[{"type":"string"},{"type":"null"}],"default":null,"title":"Api Key"},"cursor":{"anyOf":[{"type":"string ⟨24 unchanged words⟩
{"properties":{"api_key":{"anyOf":[{"type":"string"},{"type":"null"}],"default":null,"title":"Api Key"},"cursor":{"anyOf":[{"type":"string ⟨17 unchanged words⟩
{"properties":{"api_key":{"anyOf":[{"type":"string"},{"type":"null"}],"default":null,"title":"Api Key"},"eid":{"title":"Eid","type": ⟨19 unchanged words⟩
{"properties":{"api_key":{"anyOf":[{"type":"string"},{"type":"null"}],"default":null,"title":"Api Key"},"eid":{"title":"Eid","type": ⟨19 unchanged words⟩
{"properties":{"api_key":{"anyOf":[{"type":"string"},{"type":"null"}],"default":null,"title":"Api Key"},"emb":{"anyOf":[{"items":{" ⟨30 unchanged words⟩
POST /: create a grid, your own space of nodes and scores; no API key needed. Returns its `api_key`, shown only now: pass it as `api_key` to every other tool, or send it as the header `Authorization: Bearer hg-…`. It holds up to `max_nodes` nodes. Each address may create only a few grids a day.