Skip to content

Commit 441cade

Browse files
committed
docs: RELEASE-NOTES.md for v1.3.1
Replaces the v1.3.0 notes, as each release does. One fix a user feels — the chat no longer slides away when you scroll past the end of the transcript — and, for people who run from source, the dev editor's own identity and the build check that goes with it. Measured, not recalled: 49 suites and 892 cases, counted the way scripts/draft-release-notes.mjs counts them (v1.3.0 that way is 48 and 854, which is what its notes say). The scroll fix's figures are the ones in docs/CHAT-TYPOGRAPHY.md; that the fault dates from v1.1.0 is read off the chat page at each tag, and the new guard fails on v1.3.0's page. The identity check is in this release's build log for both architectures. The draft script could not be used: v1.3.1 was tagged first, so these notes land after the tag, as the last two did. Said plainly in the text, because it is new and follows from the dev scheme being off by default: a source build cannot sign in to LevelCode Cloud.
1 parent f8b6193 commit 441cade

1 file changed

Lines changed: 36 additions & 75 deletions

File tree

‎RELEASE-NOTES.md‎

Lines changed: 36 additions & 75 deletions
Original file line numberDiff line numberDiff line change
@@ -1,107 +1,68 @@
1-
# LevelCode v1.3.0
1+
# LevelCode v1.3.1
22

3-
When a LevelCode Cloud session ended, v1.2.0 said so with `API 401: Signature has expired` in red — beside an account popover that still claimed you were signed in. This release replaces that with one card and a **Sign in** button, shown before you send anything. Mostly you will not see even the card: the session is renewed ahead of time, a lapsed token is renewed wherever a request is sent rather than only in the chat, and thirty days of sign-in now run from the last time you used the editor. GPT-6 Astra and Claude Fable 5 / 5.1 are sized as the models they are, and the agent's browser preview can open for the first time.
3+
One fix you will feel: the chat stays where it is. Past a conversation's first long turn, scrolling beyond the end of the transcript slid the whole chat — transcript, composer and status row — up over a blank page. It has done that since v1.1.0. The rest of this release is for people who run LevelCode from source: the dev editor is now its own app to macOS, so a sign-in started there comes back there.
44

55
## Highlights
66

7-
### An ended session is a Sign in button, not a red error
7+
### The composer stays put
88

9-
The card is headed **Your session has expired**, greets you by name, and says: *Sign in again to keep using LevelCode Cloud — your chat and files here are untouched.* It has two buttons: **Sign in**, and **Use my own key instead**, which opens the provider-mode setting.
9+
The chat is a page exactly one window tall, and the transcript is the only thing in it meant to scroll. The composer and the status row sit under it and should never move. From the second turn of any conversation whose first one was long, they did: reach the end of the transcript, keep scrolling, and the whole chat rode up together with blank space beneath it.
1010

11-
- **It is found before your first message.** The session is checked when the chat opens and every time the window comes back to the front. The check reads the token's own expiry, so a session with hours left costs no request.
12-
- **The popover and the footer stop saying you are signed in** at the same moment. That was the worst part of the old failure: two parts of the same window disagreeing about whether you were signed in.
13-
- **The card stays with the conversation.** New Chat, a resumed session and a checkpoint restore each rewrite the transcript, and each puts the card back while the expiry is unanswered. Signing in, or choosing your own key, takes it away.
14-
- **Inline edit and Agent Sketch say it too.** An ended session reads *Your LevelCode Cloud session has expired. Sign in again to continue.* there — with a **Sign in** button on the inline-edit toast — where v1.2.0 showed the gateway's 401.
11+
The page itself had become scrollable. Since v1.1.0 the speaker label — "You", "LevelCode AI" — is kept for screen readers and taken off the screen, with the usual rule for that: out of flow, one pixel, clipped. Nothing above the label was positioned, so it was laid out against the **page** rather than the transcript, at its unscrolled place in the log, where the log's own scrolling and clipping do not reach. A message that started more than a window down had its label below the fold, the page grew to reach that one pixel, and once the transcript was at its end the wheel scrolled the page.
1512

16-
**Only the server saying no ends a session.** Being offline, a 5xx or a malformed reply means nothing is known yet: you stay signed in, and the request shows its own error. A renewal that hangs is given ten seconds and then treated the same way. Clearing credentials on a network blip would sign you out for closing your laptop on a train.
13+
The transcript is now the anchor for everything inside it. The label is as it was — off screen, and still read out.
1714

18-
If you use LevelCode on your own key with no account, none of this reaches you — no card, no prompt. Gateway mode with no token is what a fresh install is, and it still falls back to your key.
19-
20-
### Thirty days now run from the last time you used it
21-
22-
A cloud sign-in is two credentials: an access token good for 8 hours, and a refresh token good for 30 days that buys the next access token. Through v1.2.0 the editor kept the refresh token it was handed at sign-in for that token's whole life, so the thirty days ran from the day you signed in. Someone who used LevelCode every day was signed out on day thirty all the same.
23-
24-
The cloud now issues a new refresh token with every renewal, and the editor stores it. The thirty days slide: keep using the editor and you do not reach the wall; leave it for a month and you sign in again.
25-
26-
| What | Value |
27-
| --- | --- |
28-
| Access token | 8 hours |
29-
| Sign-in | 30 days, counted from the last renewal |
30-
| Renewed ahead of expiry | when under 5 minutes remain — checked at chat open, and on window focus at most every 10 minutes |
31-
| A renewal that hangs | given up on after 10 seconds — you stay signed in |
32-
33-
### A lapsed token is renewed wherever a request is sent
34-
35-
The chat and the agent already renewed a lapsed access token and sent the request again. Nothing else did. Once the eight hours were up, everything around the chat failed until a chat message happened to renew the token — for a session that was perfectly renewable.
36-
37-
| Where | v1.2.0 | Now |
15+
| Measured in a 1118px window, two turns | v1.3.0 | Now |
3816
| --- | --- | --- |
39-
| Inline edit | *LevelCode AI edit failed: … API 401: Signature has expired* | renewed, and the edit asked once more |
40-
| Agent Sketch — Run, the board command, Generate flow | the gateway's 401 on the nodes that ran | renewed; nodes that fail together share one renewal |
41-
| Inline completion | silently nothing, on every pause in typing | renewed quietly |
42-
| Compact and the session-memory summary | failed | renewed |
17+
| Page height | 1963px | **1118px** — the window |
18+
| Composer after four wheel ticks at the end of the transcript | 400px higher, blank page beneath | **unmoved** |
19+
| Transcript content height | 2919px | 2919px — nothing inside it moved |
4320

44-
What it deliberately will not do:
21+
Scrolling up inside the transcript still pauses auto-scroll and offers "jump to latest".
4522

46-
- **Send anything twice.** One retry, and none once part of an answer has arrived — a second send would repeat it.
47-
- **Outlive a Cancel.** Stop, Cancel or the next keystroke ends the wait at once, and a request nobody is waiting for starts no renewal.
48-
- **Cross accounts or hosts.** A request stays with the account and the cloud host it was sent on. Sign in as someone else while it is out — in this window or another — or point the editor at a different host, and it is not sent again on the new credentials.
49-
- **Turn typing into refreshes.** Ghost text is sent on every pause in typing. It may start one renewal a minute, and waits on one that is already out.
23+
**What it deliberately does not do: lock the page.** `overflow: hidden` on the page would have hidden the symptom and left the cause. It would also have cost something real: in a window too short for the composer and the status row — they need 208px — scrolling the page is the only way to reach the bottom controls.
5024

51-
### One session, every window
25+
**What is proven, and what is not.** The numbers above were measured in Chromium against the shipped chat page, served the way the editor serves it and driven with the editor's own messages. They were not taken from a packaged build.
5226

53-
The session is stored once and every window shares it, but a window only heard about the changes it made itself. One left open in the background kept showing "signed in" after another window had signed out.
27+
### Running from source: the dev editor is its own app
5428

55-
Each window now compares what is stored with what it is showing whenever it comes to the front, and catches up: the card and a signed-out popover if the session ended elsewhere, the popover alone if you signed out there, and the card taken down if you signed back in there.
29+
To macOS, the editor started by `./scripts/run-dev.sh` and the LevelCode in /Applications were the same app: one bundle identifier, one `levelcode://` scheme. Sign-in ends with the browser opening a `levelcode://` link, and macOS decides which app that belongs to. It picked the installed one. The dev editor that had asked never heard back, and the installed editor was handed a sign-in it had not started.
5630

57-
### GPT-6 Astra and Claude Fable 5 / 5.1, sized as they are
31+
`run-dev.sh` now gives the dev run an identity of its own — the scheme `levelcode-dev` **and** the bundle identifier `ai.levelcode.app.dev`. A scheme alone would not have been enough: with one shared identifier macOS can still hand a launch, or a link, to whichever copy is running.
5832

59-
v1.2.0 had no entry for any of them and fell back to a guess: a 200k-token window for all three, and no images for Astra. In gateway mode that meant the model picker offered Astra while the composer refused your screenshot, and the context meter was sized for a fifth of the real window.
33+
- **It is set on every launch,** in the two places it lives: what the editor believes at runtime, and what macOS believes about the dev bundle. Both or neither — the two files change as one change, and a failure half-way is undone.
34+
- **The launch waits for macOS to agree.** After registering the bundle, the script asks macOS which app opens `levelcode-dev://` and stops unless the answer is this bundle. Being told about a bundle is not the same as agreeing to use it: one under a temporary folder is registered and never chosen.
35+
- **The sign-in code did not change.** It already asked to be called back on the editor's own scheme, whatever that is.
36+
- **The installed app is untouched.** Its identity is the product's, and a build is now checked for it (below).
6037

61-
| Model | Context window | Images |
62-
| --- | --- | --- |
63-
| GPT-6 Astra | 1,050,000 tokens | yes |
64-
| Claude Fable 5 and 5.1 | 1,000,000 tokens | yes |
65-
66-
The rows hold under every id the models arrive as: `openai/gpt-6-astra` and `anthropic/claude-fable-5.1` from the gateway and OpenRouter, and Anthropic's own `claude-fable-5-1`.
67-
68-
On LevelCode Cloud, Fable 5 and 5.1 are included from **Pro** and GPT-6 Astra from **Pro+**. They are expensive models, and the pricing page says so in turns rather than leaving you to find out: Pro's 2,000 credits are about 260 turns on Kimi K2.7 and about 20 on Fable 5.1.
69-
70-
### The agent's browser preview opens
38+
**A server has to be told to accept the scheme.** No server does by default — LevelCode Cloud included — so from a source build, a LevelCode Cloud sign-in ends on the account page in the browser and the editor hears nothing. Your own key works as it always has. If you run the backend yourself, set `LEVELCODE_EXTRA_EDITOR_SCHEMES=levelcode-dev` on it; it accepts `levelcode-<variant>` and nothing else.
7139

72-
When the agent starts a web server in the background and it prints a local address, LevelCode opens it in the built-in browser beside the chat — without taking focus, and once per address, so closing the tab is final. That is what `levelcode.ai.preview.autoOpen` has promised since v0.9.2.
40+
On the first run after updating: quit a dev editor that is already open, because a second launch joins the running one and that one still has the old identity. macOS may also ask again for folder access — to it, this is a new app.
7341

74-
It never happened. A logging call on that path referred to a name that was out of scope, and threw before the browser was asked for. Every release from v0.9.2 to v1.2.0 carries it; this is the first that can open the tab.
42+
### A build is checked for the identity it ships with
7543

76-
**What is proven, and what is not.** A test now runs the real chain — the agent, the tool, the command's output — up to the call that opens the browser. The tab itself appearing in a packaged build is the one step no test covers.
44+
`scripts/build-macos.sh` now fails a build that is not `levelcode://` and `ai.levelcode.app`, or that carries the from-source overrides file. The dev identity lives outside the product definition and cannot be picked up by a build; the check says so out loud, before anything else is done to the app. It ran on both architectures in this release's build.
7745

78-
Only local addresses are ever opened: `localhost`, `127.0.0.1` and `[::1]`.
46+
## Also changed
7947

80-
## Also fixed
81-
82-
- **Three icons were printed as words.** Opening the chat in an editor tab showed a banner reading *layout MOVED TO THE EDITOR*; the preview chip and the recall and project-memory chips showed `globe` and `history` as text on ungrouped timeline rows. The glyphs are in, and a test now runs every icon name written down on either side through the real renderer.
83-
- **A sign-in replaces the whole session.** One that arrived without a refresh token kept the previous session's, and the next renewal was made with it: refused, it ended the session you had just started; still valid, it renewed the *previous* account under the new one's name. Latent — the cloud sends a refresh token with every sign-in — and closed.
84-
- **A background command that failed to start** raised an unhandled rejection instead of being logged. Same out-of-scope name as the preview.
48+
- **`run-dev.sh` lost its `pkill`.** It targeted the binary name the app had before it was renamed, so it had been matching nothing. The reason it gave — dev and packaged builds sharing a bundle identifier — is what this release removes.
8549

8650
## Not in this release
8751

88-
**The Sessions panel still does not search.** It was the stated gap in v1.0.5, in v1.1.0 and in v1.2.0, and it is the stated gap again. This cycle went to sign-in.
52+
**The Sessions panel still does not search.** It was the stated gap in v1.0.5, v1.1.0, v1.2.0 and v1.3.0, and it is the stated gap again.
8953

90-
**A session with no refresh token cannot be renewed, and is not ended either.** When its access token lapses, the request still shows the gateway's 401. The cloud issues a refresh token with every sign-in, so reaching this takes a sign-in that arrives without one — but it is the one path left where that error can appear.
54+
**A source build cannot sign in to LevelCode Cloud.** That follows from the scheme being off by default, and it is new: on a Mac with no installed LevelCode, a source build could complete that sign-in, being the only app that claimed `levelcode://`.
9155

92-
**Nothing renews the token in a window that simply stays in front.** The check runs when the chat opens and when the window regains focus. A window you never leave finds a lapsed token on its next request, which is renewed and sent again — a moment's delay rather than an error, but not the same as never lapsing.
56+
**The website's IDE link still opens the installed app.** It is written with the shipped scheme, so in a development setup it does not reach the dev editor.
9357

94-
**"Use my own key instead" is only on the chat's card.** The inline-edit toast offers **Sign in** alone, and Agent Sketch shows the sentence with no button at all.
58+
**The editor still acts on a callback it did not ask for.** Ignoring a sign-in callback when no sign-in is in flight would make a misrouted one harmless; today it is merely unlikely.
9559

96-
## Test coverage
60+
**Off macOS, the dev scheme is not registered with the system.** The script says so and sets the runtime half alone.
9761

98-
- **48 suites**, **854 cases** across the bundled extensions — all green. v1.2.0 measured the same way was 40 suites and 599 cases.
99-
- `test/sessionExpiredHost.test.js` (70 cases) — the host's own functions, sliced out of `extension.js` and run against stores that answer a turn late: the expiry found at open and on focus, late answers that must not touch a newer session, a sign-out in the middle of a request, and what other windows do to the store.
100-
- `test/authRetryCallers.test.js` (76 cases) — the real inline edit, Agent Sketch and completion modules, driven as the editor drives them against a gateway that answers 401 to a lapsed token.
101-
- `test/authRetry.test.js` (45 cases) — the renew-and-retry rules on their own: one retry, one renewal at a time, and a request that stays with its account and host.
102-
- `test/session.test.js` (19 cases), `test/sessionExpiredUi.test.js` (17) and `test/sessionExpiredCallers.test.js` (16) — the token arithmetic, the card's routing in the webview, and what inline edit and Agent Sketch say.
103-
- `test/chatIcons.test.js` (6 cases) and `test/agentRunCommand.test.js` (4) — the icon guard, and the preview chain.
62+
## Test coverage
10463

105-
**The suites now run on every pull request.** Until this release they ran in CI at one moment only — when a tag was pushed — so a new suite's first run on Linux was the release gate, after the merge. The first v1.3.0 tag failed its gate that way: a new test counted turns of the event loop across a real timer, which holds on a Mac and not on the runner. The test waits by the clock now, and the gate is one script, `scripts/test-extensions.sh`, shared by the release workflow and a pull-request check.
64+
- **49 suites**, **892 cases** across the bundled extensions — all green. v1.3.0 measured the same way was 48 suites and 854 cases.
65+
- `test/editorIdentity.test.js` (37 cases, new) — the two identities and the shape a server accepts; the dev bundle changing in two lines and nowhere else; the two files changing as one, with the undo; a registration that fails, or that macOS does not act on; the release check; and the real sign-in function run under each scheme. It runs on fixtures and cannot reach LaunchServices: the script's macOS object is replaced with one that throws.
66+
- `test/webviewCss.test.js` (36 cases, one new) — the transcript is positioned and stays positioned, with the page's one-window premise pinned beside it. No DOM test can see this bug, since a fake DOM lays nothing out; the guard fails on v1.3.0's chat page.
10667

107-
**Full changelog:** https://github.com/levelcodeai/levelcode/compare/v1.2.0...v1.3.0
68+
**Full changelog:** https://github.com/levelcodeai/levelcode/compare/v1.3.0...v1.3.1

0 commit comments

Comments
 (0)