Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
25 changes: 25 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,31 @@
Notable changes, written so a person can read them. Pre-1.0, breaking changes
are expected and listed without apology.

## Unreleased

- Four recipes for a public API with habits of its own, asked for on
[#52](https://github.com/shergin/baton/issues/52), each in Swift and
Kotlin and compiled against AniList's schema. None is a new concept.
`docs/recipes/budgeted-transport.md` is a wrapper around the one verb
that holds one request in flight, sends a write before a refresh before
a browse page, meters the sends under the server's limit, pauses every
request for the whole minute after a 429, and turns AniList's outage 403
into an error of the app's, which a handle's fetch carries beside the
data while the view shows a calm line. The built-in transports do not
keep a refused response's headers, so `Retry-After` is not read.
`docs/recipes/json-scalar.md` reads `customLists(asArray: true)`, an
array of objects, as a mapped type, notes that `customScalarTypes` maps
a scalar and not a field, and keeps a map a type of the app's, never a
dictionary on the read path. `docs/recipes/fields-by-path.md` is what a
list fragment selects when a server answers a field differently by the
path that reached it, where path-dependent and viewer-dependent fields
go, and a probe that tells the two apart. `docs/recipes/unpaged-collection.md`
is `MediaListCollection` as one operation with a long
`@cacheExpiration`, grouped on the client from each entry's own fields so
a mutation's response moves the row with no updater, and carried by the
image to the next launch. The README, the docs index and the site link
them.

## 0.17.0 (Kulich) — 2026-10-18

- `@deletes(type:id:)`, the second directive that is not Relay's: a mutation
Expand Down
10 changes: 10 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -388,6 +388,16 @@ graphql-sse but carry a `JSON` scalar, so they update no record. A process
holds one schema family: two environments may share it, and two schemas
in one process must not give two types one name.

A public API's own habits are compositions too, each with a recipe in
both languages: a rate limit and an outage
([a budgeted transport](docs/recipes/budgeted-transport.md)), a JSON
scalar read as a type of the app's
([a `Json` scalar](docs/recipes/json-scalar.md)), a field answered
differently by the path that reached it
([fields a server nulls by path](docs/recipes/fields-by-path.md)), and a
whole list in one request
([an unpaged collection](docs/recipes/unpaged-collection.md)).

Baton strives to support each backend's own features wherever they fit the
design and make sense for a client. If yours does something Baton does not
speak yet, open an issue.
Expand Down
11 changes: 9 additions & 2 deletions docs/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,8 @@ What to read when.
ships. [integrating Baton with a coding agent](recipes/agents.md) is the
page an agent reads first. [the exchange](recipes/exchange.md) is a
challenge, a retry and a deadline over the transport's one verb.
[a budgeted transport](recipes/budgeted-transport.md) is a queue, a
meter and an outage over the same verb.
[`batonc`](recipes/batonc.md) is the compiler's command line for a build
outside SwiftPM. [Bazel](recipes/bazel.md) is the compiler as a toolchain
and one rule over its command. [Gradle](recipes/gradle.md) is the Kotlin
Expand All @@ -49,7 +51,12 @@ What to read when.
[derived state outside views](recipes/derived-state.md) is a model over
`Observations` or `snapshotFlow`.
[discover once, refresh through `nodes(ids:)`](recipes/discover-once.md)
is the pattern for external keys. The rest arrive with the releases that
make them true.
is the pattern for external keys.
[an unpaged collection](recipes/unpaged-collection.md) is a whole list in
one request, grouped on the client and carried by the image.
[fields a server nulls by path](recipes/fields-by-path.md) is what a list
fragment selects. [a `Json` scalar](recipes/json-scalar.md) is a value
with no type of its own, read as a type of the app's. The rest arrive
with the releases that make them true.
- **What did a decision open up?** [openings/](openings/) is written as the
project ships. There are none yet.
Loading
Loading