---
title: Changelog
built: 2026-10-30
source: api/CHANGELOG.md
html: https://insurgently.com/projects/topic-map/technical/agents/CHANGELOG
---
# Changelog

> Index of these files: https://insurgently.com/projects/topic-map/technical/agents/llms.txt

The API package's versions. The package version is the API version, and each is published after the Topic Map release that serves it. Before 1.0, a minor version may break the API; breaking changes are marked **Breaking**.

## 0.5.0

Not yet released.

- The catalog calls `catalogNames`, `catalogNodeName` and `renameCatalogNode` (`TopicMapCatalogApi`), offered on `TopicMapApi` as optional: feature-detect each with `hasMethod`. A domain's tree file is the one source of its nodes' names; a rename writes it and the pages Topic Map made from it, is undone by `undoRun` (which fires the event again with the restored name), and fires `topic-map:catalog-renamed` (`TOPIC_MAP_CATALOG_RENAMED`, carrying a `CatalogRenamed`).
- `moveCatalogNode(domain, id, newParentId)`: a type under another sub-family, a sub-family under another family, ids kept. One run that `undoRun` takes back; fires `topic-map:catalog-moved` (`TOPIC_MAP_CATALOG_MOVED`, carrying a `CatalogMoved` with the parent ids `from` and `to`), and again with them swapped when undone. Refusals: `catalog-missing`, `catalog-node-missing`, `invalid-request`.
- `catalogRedraftReport(domain)`: what the catalog's last redraft couldn't keep (`CatalogRedraftReport`: `at`, and `items` of `{ id, name, parent, reason }`), or null when there was none. Refuses `catalog-missing` and `invalid-request`.
- New `TopicMapErrorCode`s: `catalog-missing` and `catalog-node-missing`.

## 0.4.0

- `openMap` is offered (feature-detect with `hasMethod`); `registerMapLayer` and the map layer types are new; in the library map a book's card id is `calibre:<id>`.
- `openMap` rejects with a coded `TopicMapError`: `invalid-request`, `not-indexed`, `collection-missing`, `hub-missing`, or `canceled` (the layout stopped, or another map opened in the map view first). Other failures are a plain `Error` naming the cause. No new error code.
- A layer's `legend` is read at registration and again on each `refresh()`; a legend the map can't draw is refused there (`invalid-request`) and the last one stays. In a layer with the id `shelves`, a legend entry may name its shelf (`shelf`), which selecting it in the library map chooses.
- `MapPoint` has an optional `collection` (the map it is on), and its `book` is typed as `BookRef`.
- **Breaking:** `estimate()`'s `cost_usd` is now money that would be charged only: a reading that a subscription covers, or that a model on this computer runs, counts nothing (a subscription's price at API rates isn't a charge). `startIndex` checks its `maxSpendUsd` cap against it, and the run's spend limit counts charged money the same way.

## 0.3.0

The first published version.

- `getTopicMap(app, wanted, { by, for })` and `onTopicMapReady` find Topic Map and check its version. `opts.by` and `opts.for` put your plugin's name, and what it needs Topic Map for, into the message given when Topic Map is missing or too old.
- `hasMethod(api, name)` checks for a call newer than your version gate, or one still to be implemented.
- Collections, search, neighbors, cards, passages, dry runs, index jobs, undo, quote checks and `ensureCollection`.
- The group calls (`similar`, `nearest`, `rankGroups`, `place`, `groupHealth`, `overlaps`, `findGroups`, the library collection) and `openMap`, as types only: no installed Topic Map offers them yet, so check each with `hasMethod`. (`openMap` is offered from 0.4.0.)
- Events: `topic-map:ready`, `topic-map:unload` and `topic-map:index-changed`.
- Every refusal rejects with a `TopicMapError` whose `code` is always set.
