Skip to content

release: 0.5.0 - #51

Merged
efim0v merged 105 commits into
mainfrom
release/0.5.0
Oct 21, 2026
Merged

efim0v merged 105 commits into
mainfrom
release/0.5.0

Conversation

@efim0v

@efim0v efim0v commented Oct 21, 2026

Copy link
Copy Markdown
Owner

Workspaces moves into the notch panel, next to the limits: Projects with each session's last exchange and what needs you, Agents with who talks to whom, and no menu-bar item. Glim gets two new moods, and Brow refreshes tokens again while Claude Code sessions sit open. The changelog has the details. Merged with a merge commit, like 0.4.0, so the history of each change stays readable.

efim0v added 30 commits October 19, 2026 03:51
The runner sent SIGKILL half a second after SIGTERM. On its way out
Claude Code waits up to two seconds for a token refresh in flight to be
saved, and the refresh token changes with every refresh, so a kill in
that wait could leave the account without a refresh token that works.
The keeper now gives both commands five seconds; every other command
keeps the half second. The cycle watchdog grows from 270 s to 280 s to
cover the longer grace.
…n help

Claude Code renews a token only inside its last five minutes: every
refresh it makes, short of answering a 401, first checks
now + 5 min >= expiresAt (read out of the 2.1.290 to 2.1.302 binaries).
The keeper ran claude doctor from 30 minutes before the expiry, so the
first doctor of every token did nothing, counted as a failure, and the
claude -p after it spent limit and started the account's 5-hour window
for nothing. The keeper now acts 4 min 30 s before the expiry, inside
the CLI's window with half a minute to spare.
Claude Code's native binary runs itself as other tools: as rg, its
bundled ripgrep, and as ugrep and bfs for the grep and find of its Bash
tool's shell, under that name (ARGV0= in zsh, exec -a in bash). Such a
process inherits its session's CLAUDE_CONFIG_DIR, and one left behind
in an old tail -F | grep pipeline ran for days after the session had
gone. Brow took it for a session holding the account and never
refreshed that account's token. A process whose argv[0] is rg, ugrep,
bfs or apply-seccomp is no longer counted.
…g its token

Since 0.3.1 an account with a live claude process for its folder was
left to that session, however long it had sat idle, with nothing to
fall back on as the token ran out, and the refresh button could not
override it. A session renews its token only when it sends a request
in the token's last five minutes, so with sessions left open for days
nothing renewed any token: eight hours after its last refresh each
account read "Token in use by Claude Code", then "Rate limited", and
signing in again only restarted the clock.

The 0.3.1 worry, a refresh by Brow racing the session's own, no longer
holds: Claude Code takes a lock in the config dir around every refresh
and re-reads the token under it. A session now holds the keeper off
only while the token has more than two minutes left. After that, after
a 401, and when a refresh is asked for (the refresh button, a wake, a
sign-in), the keeper runs whoever holds the account. Each stretch of
either is logged once, at the default level, so it is kept.
The usage client sent a token whatever its expiry. The endpoint can
only refuse a dead token, the client retried every 401 once, and with
Brow polling every 30 s the account's row went from "Token in use by
Claude Code" to "Rate limited". A token past its expiry now stays
home. The panel says "Token expired 12 min ago", and adds "— Claude
Code hasn't refreshed it" while a session holds the account. When the
keeper's attempt floor is what holds the refresh back, the dead token
gets the one forced attempt a 401 would have bought it.
The key lit for any 401, and the token line read "sign-in revoked",
so a token a refresh would have fixed sent you to sign in again; with
an idle session holding the account that only restarted its eight-hour
clock. A 401 now reads "Anthropic rejected the token" and buys the
keeper's forced attempt. The key lights when the keeper says the login
is dead, because claude doctor or claude -p printed "Please run
/login" or three attempts in a row did not renew the token, and, as
before, when an account has no token at all. The keeper keeps that
verdict with the token it was reached on, through its attempt floor
and a relaunch, until a new sign-in replaces the token or a refresh
lands, and spends no claude -p on a login the CLI says is dead.
Brow's 30 s poll keeps firing in the dark wakes of a sleeping Mac
(Power Nap, maintenance), and the keeper ran claude doctor and
claude -p in them. A doctor frozen mid-refresh when the Mac goes back
to sleep can lose the refresh token that still works, and -p spends
limit with nobody there. From macOS saying it is going to sleep until
the wake that follows, while the main display is asleep, the keeper
now runs nothing; the usage reading still goes out. The display check
keeps a sleep that never ended in a wake notification from holding
the keeper off for someone at the screen.
The changelog's Unreleased section says what changed and why the 0.3.1
reasoning no longer holds: Claude Code locks around every refresh, and
an idle session renews nothing. docs/brow.md and the three READMEs
said Brow never refreshes a token a session is using and that the
fallback runs from 30 minutes out; they now say a session gets the
first go while the token has more than two minutes left, and that
claude doctor runs in the token's last 4½ minutes.
Two moods at the ends of the meter, judged like the others on H plus the
food still on the plate, with 5 points of hysteresis: Stuffed from -35
coming down until above -30, and Famished from 90 until below 85. Stuffed
takes about six points from 0 or a feast from 13 or below and wears off
within an hour of hunger time from the floor; Famished comes 4 h 30 min
after 0 at an even pace and is left only by food.

A meal carries the mood it was planned in. A full meal that leaves the
pet stuffed is followed by `brim`, a full meal or a feast eaten famished
by `grateful`; a nibble is a lick as before. The words are Stuffed and
Famished. pet.json is unchanged: a restored pet takes the mood its H
gives. Until they get their own look, the two ends wear their
neighbours' faces.
…f the panel

The outline's bottom corners are Apple's continuous corners: the quadratic ones turned at once, with the control point on the corner, which read as a plain radius. The open panel's radius goes from 18 to 24 pt, where a continuous corner reads as one soft curve; the strip keeps 14. The flares are drawn beside the body, so the two never overlap and no seam can show. NotchGeometry.frames takes the open panel's width, so a screen of the one window can ask for its own.
maxDayCards shows that many accounts beside the month and then "+N more on this day", so a day on which every account resets cannot make the column taller than the panel was sized for. nil keeps every account, as before.
The keeper's "sign in again" came only from the -p leg, and a token past
its expiry reached the keeper flagged as rejected (the store flags it so
the attempt floor lets one attempt through), which skips -p. So once a
dead login's token had expired, every attempt stopped at claude doctor,
the breaker was never reached, and the key stayed grey for good: doctor
prints a report, not "Please run /login".

A token past its expiry is now renewed like a due one: -p and the
breaker apply to it. Only a token Anthropic refused while it still had
life left stays at doctor, as before. The breaker's verdict no longer
needs the -p leg either, so it also reaches people who turned the
fallback off.
claude -p is not interactive, and there the CLI words a dead login
"Failed to authenticate: OAuth session expired and could not be
refreshed", "Failed to authenticate: OAuth token revoked. …" or
"Failed to authenticate. API Error: …"; "Please run /login" is what an
interactive session says (2.1.290 to 2.1.303). The keeper looked only
for the latter, so a dead refresh token, the commonest dead login, went
unheard. It now takes either, and the key lights on the first attempt
after the token expired instead of three attempts later. The changelog
and docs/brow.md say which words count.
With the network down nothing can renew a token, and the usage request
that used to say "Offline" is no longer sent for one past its expiry.
So on a long flight every account read "Token expired 2 h ago — Claude
Code hasn't refreshed it", which points at the session and at signing
in again, while the account comes back on its own with the network.
The row and the footer say "Offline" again, and the token is still not
sent.
The changelog and docs/brow.md say a token past its expiry is not sent
to Anthropic, but only the usage request held to that: the daily
api/oauth/profile request still went out with a dead token, about once
an hour per account while the token stayed dead. It now throws the same
"expired" error the usage client does, without a request.
…session

Two of the rules that let the keeper run past a session holding the
account were pinned only by the table test of holderRule: with the 401
rule or the dead-login rule taken out, every cycle test still passed.
The 401 test used a token with five hours left, which no session holds
the keeper off for anyway, and no test had a dead login with a session
open on it.

Now a 401 with three and a half minutes left still gets its forced
doctor, and a dead login with a session open on it keeps the sign-in
key lit and the keeper's word in the token line.
docs/brow.md said the fallback is never used after a 401/403. Since a
token past its expiry is no longer sent, nothing refuses it, and the
keeper gives it claude doctor and then claude -p like a token that is
due; only a token Anthropic refused while it had time left stays at
doctor.
ScreenMetrics carries the screen's visible frame, and NotchGeometry gains the height the open panel may have: from the screen's top edge down to 12 pt above the visible frame's bottom (the Dock, or the screen's edge), and a 480 pt floor for a panel with sections. panelHeight takes the content's own height between the two.
… at the month

The grid always reserves six week rows, so walking from a five-week month to a six-week one never changes the panel's height. The day's cards are drawn over the space beside the grid and are cut at its height: as many as fit, at most the number the panel asks for, then "+N more on this day" with the other accounts' dots. A day on which every account resets can no longer grow the panel and push its bottom row out of the outline.

The tests run on made-up accounts (MadeUpLimits: the README's three and five more), for a four-, five- and six-week month and every hovered day.
claude -p ends any 401/403 that its own one forced refresh did not
clear with "Failed to authenticate. API Error: …", and that refresh
also fails when the token endpoint errors or does not answer, or when
another process is in the middle of a refresh (read out of 2.1.303).
The keeper took the line for a dead login, so an outage at the token
endpoint would light the sign-in key on every account whose token ran
out during it, and send people to sign in again for nothing.

A dead refresh token reads "Failed to authenticate: OAuth session
expired and could not be refreshed", and the CLI clears it from the
Keychain, which the next scan sees as no token. That line and "OAuth
token revoked" still count.
…I's own deadline

On SIGTERM Claude Code cleans up first (up to 2 s), runs the SessionEnd
hooks (1.5 s unless configured otherwise), and only then waits up to
2 s for a token refresh in flight to be saved. Its own deadline for
all of that is 6.5 s, and 8.5 s while a refresh is in flight (2.1.290
to 2.1.303). The five seconds Brow gave it could end in the last of
that wait, which is the kill the grace exists to avoid.

Nine seconds outlast the CLI's deadline. The cycle's worst case becomes
267 s, still inside the 280 s watchdog, and the test that recomputes it
from the constants passes unchanged.
Stuffed sits round and low, leaning back from the number belly out, the
nubs on its belly, eyes shut in bliss over a wide smile and rosy cheeks,
its light over the brim. The belly is the meter's: it bulges the lower
sides and sets the feet wider from -26 down, so the bite that makes the
pet stuffed rounds it as the light lands and it goes down by itself as
hunger returns; curled up asleep there is none.

The eyes open out of their bliss every 6 to 18 s for a couple of
seconds. Its beats take the place of the habits that do not suit it, one
gesture at a time: a pat-pat on the belly, a contented sigh with a puff
of breath, a peek at the number and a lick, a hiccup, and about every
three minutes a thumbs-up with a wink and a sparkle, the arm away from
the readout coming up with a little thumb. The thumbs-up's rise and the
hiccup's hop are drawn in the fast class.

It still eats, leaning for the food rather than leaping, its belly
bouncing as the bite lands, and the swallowed light carries no tint at a
stuffed mouth. A full meal that leaves it stuffed ends in pats, a
thumbs-up and a sigh; a feast that does the same in the stuffed face.
Out of stuffed it settles into Full over 2 s. Eyes open and shut on a
quick clock of their own wherever a posture blend takes them across the
drawings' cross-fade. The old heavy-lidded face is now `heavy`, the
start of the yawn at the 5-hour limit.

The body's box, which the zone clamp keeps inside the zone, is now
measured on the points the outline is drawn through and counts the arms'
and the thumb's stroked edge: the round belly bulged between the coarser
points it was measured on, and under the notch at 100 % a stuffed meal's
belly and cheeks came within the readout's 4 pt.
launchCommand takes the environment a session starts with from the app that hosts the engine, already quoted, in place of the CLAUDE_CONFIG_DIR and BROWSER it would build. Brow passes env -u CLAUDE_CONFIG_DIR for the default account, so a shell that exports another account cannot make the session run as that one. A blank one is none.
…vironment

Workspaces' screens learn where they are drawn: a window of their own, or a section of a host's panel (groveHost), and in which accent (groveAccent: Grove's blue by default). Stats, Graph, the stats settings and the notices draw their controls, links and glyphs in it; the repositories keep their own chart colours. Cards in a host's panel are its own: white at 5.5 % with a 7 % edge.

FadingScrollView is the screens' scroll: a fade at the top once scrolled and at the bottom while there is more. Offscreen, where ImageRenderer draws no ScrollView, it clips the content to the room it is given at a render offset that never runs past the end, and draws the indicator; given no height it is as tall as its content. isSnapshotRender is public, with a snapshotRender() modifier, so a host renders the screens too. Graph's repositories sit in one row that scrolls sideways and never wraps a name. ScopeHeader takes the screen's own actions and a subtitle under the title.
Famished stands up on its toes, leaning in at the number and a step
closer to it, the near nub reaching for it, with shining eyes (bigger
catchlights and a third pin of light, never at the lower rim), brows
high and level, an eager open smile and rosy cheeks. Its light is the
meter's; the face carries the hope: never a raised inner brow, a frown,
a lower body, a tear or a tongue resting out.

Its tummy grumbles every 25 to 43 s on a schedule of its own: it looks
down at it, surprised, pats it with both nubs and goes back to the
number with a hopeful smile and a lick. Coming up from hungry, the first
grumble comes at once, or 8 s after a rumble it has just had, and the
schedule's own start 20 s after it. It reaches on tiptoe with grabby
little circles, and about every three minutes asks please: the shining
eyes on the viewer, both nubs at its cheeks, two quick happy squints.
Blinks keep out of the grumble and the please. Settled, it only rumbles,
at half strength.

Its meal starts with a hop of joy and sways through the chews; a full
meal or a feast eaten famished ends in the grateful beat, a self-hug with
sparkles and a bounce, then shining eyes back on the number for more. A
nibble gets a quick happy squint.

Leaning in, it turns its whole face to the number: the head takes part
of the eyes' travel, so the big eyes stay over the smile instead of
sliding across the face onto it, and its look down at a grumble is a
little slower, so that face never sweeps across the body faster than
the idle's half a point a frame. The readout guard now renders both
ends of the meter and every gesture of theirs.
Opening the panel is a new event for the brain, `panel(open:)`, sent at
the instant the outline starts to spring. When the pet rests at an end of
the meter, Reduce Motion is off and no greeting came in the last three
minutes, the brain cues `greet` once the hop into the header has landed,
0.6 s later. The rig plays it as the mood's own gesture, a thumbs-up
stuffed and please famished, waiting up to 1.5 s for a gesture already
playing to end or letting it go, and nothing if the mood has changed by
then. The pointer coming close greets nobody: near the notch it is often
on its way to the menu bar.

The greeting's leap is drawn in the fast class like the others, and the
controller wakes at both ends of it. A beat under way when the mood
changes plays on into the next idle, and one an action cuts short fades
with it rather than vanish.
…e-eyes

Between the bean eye and the happy arc the drawing cross-fades, and an
eye held in the cross-fade for more than a couple of frames shows both:
the idle lick peaked there for about nine frames at its half pace. The
lick's and the squish's squints now go all the way to the arc in the
same time, and the scratch's squint and the celebrations' joy open and
shut on the eyes' quick clock.

A blink took the lids down with their slant, so the half-shut frames of
a hungry blink read as a side-eye; the slant now goes down with the lid
and the middle of a blink is level.

A new scan walks the eyes frame by frame at 30 fps through every idle
mood, settled, eager and the ten-minute script, which now visits both
ends of the meter.

Stuffed, eyes opened out of their bliss that would shut just as a
gesture opens them on its own (the thumbs-up, room for more, the hiccup,
a mote) stay open for it: shut and opened again at once, they stopped
half way for three frames. The ten-minute script also greets at both
ends.
Asleep at the limit the brows pressed down onto the shut eyes over a
dark open dash, which drew "=_=", the face of someone bored or put out.
The brows now rest easy above the shut eyes, the mouth is a small closed
smile and the cheeks are warm: full, cozy and content. The loaf, the
light, the Zzz, the yawn into it, drowsy and hibernation are unchanged.
…footer

The panel is a shell installed once, which a publish of the limits never rebuilds: the band at the top, a switch between sections while there is more than one (Limits, and the sections a host registers), the section's content, and one footer that is never part of a scroll. One width and one height for every section — the Limits section's own laid-out height, measured offscreen rather than read back from the window's frame, at least 480 pt while there are sections and at most 12 pt above the Dock — so switching sections never moves the outline, and the bottom row is always inside it. On Limits, Glim's row and the Overall line are a fixed header and the accounts and the month scroll under them; the month's day column shows three accounts at most.

The footer is the same on every section: the section's status line, its own button (Limits' share), the pin, ⟳ and ⚙ with the version, Settings… and Quit Brow. Hovered, the panel opens and closes with the pointer, on the section it last closed on for 15 minutes. Any click inside pins it: only then may the non-activating panel become key, so its fields take the keyboard without activating Brow, and the pointer leaving no longer closes it. It closes on Esc at a section's root, a click outside, the pin or a hand-off, and every close latches the hover until the pointer has left. While pinned, ⌘1–⌘3 and ⌃Tab switch sections, holding ⌘ shows the keys, ⌘R refreshes the section in front, ⌘, opens Settings and ⌘Q quits. It can open pinned with the notch off, at the top centre, for as long as it is open.

Off Limits the band keeps the strip's readouts and Glim stays on its ledge; switching to and from Limits hops it with today's hop. The shell stays in the tree while the panel is closed, so what a section holds is there when it opens again. Cream is the one accent. The Workspaces button leaves the footer: Workspaces becomes a section of this panel. The README's panel renders draw the controller's own outline at the height it measures.
PetMoodsPreviewTests renders the two ends of the meter through Brow's
real window on the cream desktop of Brow's pictures, every number made
up: the six moods side by side at 4x and at real size, stuffed and
famished pose by pose, both under the notch and on the pill, the panel's
header, films of the strip at 60 fps (a 4x zoom over the real strip) of
each end at rest, eating, coming in and going out, the panel's greeting
played by the real controller, the sleep at the 5-hour limit, and one
day through the brain that passes through both ends. Skipped unless
PET_MOODS_DIR names an output folder; each test is best run in a
process of its own.
efim0v added 29 commits October 20, 2026 05:35
…gents

Every opening of the panel, a pass of the pointer on its way to the menu bar
included, started the agents' watch, and after half a minute closed its cold
start: a look through every account's projects folder and the end of each
transcript written in the last half hour. The watch now starts once the panel
has been open for a quarter of a second, the rule Projects already scans by,
and not at all if it closed before.
…ever under a running session

Confirmed in the row, Delete did nothing, without a word, when no account was
the canonical one (every account outside ~/.claude): the guard came from the
safety net, which the delete only cleans as well. And the row asks before it
deletes, so a session could start running between the two: its process would
go on writing a file no longer there. The delete now looks at what runs first,
as Share and Resume as do, and says why it will not.
The item opens the panel pinned on Projects, and a second click should close
it. But the pinned panel took the item's mouse-down for a click outside and
closed, so the item's action, on the mouse-up, found it closed and opened it
again. A click on Brow's own status-bar window is now left to the item.
With "Show Brow in the notch" off the panel opens pinned from the menu-bar
item, the menu or a reopen. Pressing the pin then unpinned it, which took
away Esc and the click outside, and with no strip there was no pointer to
leave it either: nothing closed the panel short of pinning it again. Now the
pointer leaving closes it, as it does with the notch on; nothing hovers it
open.
…d state

The session index reads what runs, then lists transcripts for a while; a
session record written meanwhile (a turn ending) is read again and shown at
once. When the index finished after that, its older read went back up: a
session gone idle showed "Working" again until the next read, up to the next
15 s refresh. Every read is now numbered as it starts and only the newest
started is shown; the index's rows take their states from it.
The shell stayed in the tree while the panel was closed, invisible, so every
publish of what its sections read and every frame of the strip evaluated it
again: a third of a core and more with a large project open. It now leaves
the tree once the closing spring has settled. Where Projects is lives in
AppState's route, so the panel opens where it was; a section holding
something a rebuild would lose (a form, a creation's log) keeps it in.
A project can hold a hundred loose worktrees that agents and scripts left
behind, and each was a row with its own "New session" menu, which read every
account and its limits again on every publish, and git ran for each on every
refresh. Worktrees with no session, process or cmux workspace now count on
one line, listed when it is opened or a search finds them, with no git run
for them. The menu's accounts are read once for all rows.
Each project listed every session under its folder or its workspaces folder,
so two projects whose folders overlap, one inside the other or two of one
name sharing a workspaces folder, both showed it: one session counted as two
at work. A session now belongs to the project whose folder holds it most
closely. A folder that is a project's, lies in one, holds one, or shares a
project's name is not added as a second project.
A session run in ~/Projects offered all of ~/Projects as a project, every
repository in it included. A folder right in the home folder, or one holding
more than twelve repositories, is where projects are kept, not one.
Transcripts written by claude -p and the Agent SDK (entrypoint sdk-*) were
listed and counted with the sessions someone typed in. The entrypoint is read
from the same first record as the folder and kept with it.
Projects opens from the notch, the Brow menu and opening Brow again. Settings
keeps the old switch's value for older builds, as it keeps 0.4's panel material.
DemoScreenshotTests renders the panel's Projects and Agents sides and the
screens Workspaces pushes in it from the made-up world of the review
renders, and renders the notch, the panel and Settings › Workspaces again.
Each changed picture has a new name, since GitHub and browsers cache an
image by its name. Workspaces' renders as a window of its own go: the
window is gone.
The workspace pictures are the panel's: a project with a workspace open and
Resume with options with each account's limits, and a new section shows
Projects and Agents side by side. The menu-bar item is gone from Coming from
Grove and the FAQ, which says how to open Projects instead. Glim's new moods,
tokens renewed while sessions sit open, and the test count are brought up to
date.
Both show Projects and Agents in the notch panel with the new pictures, name
the session menu's Resume as, Copy to account and Share with all accounts,
say how to open Projects now that there is no menu-bar item, and quit from
the ⚙ menu. Glim's new moods, tokens renewed while sessions sit open, the
test count and the screenshot command match the English README.
docs/workspaces.md says how to open Projects and Agents now that Brow has no
item in the menu bar, and shows the panel's own screens in place of the
Workspaces window: a project, New Workspace, a project's settings, Projects,
Agents, Resume with options, Graph and Stats, and Projects while Grove.app
runs. It adds that a session shows under one project, which folders are not
suggested, that sessions a program started are not listed, and the one line
for loose worktrees nobody works in. Troubleshooting says where Projects
opens, architecture.md drops the menu-bar item, docs/brow.md shows the
collapsed notch and the open panel, and the pictures nothing shows any more
are deleted.
The English, Russian and Chinese pages say version 0.5.0 and link its
release notes. Workspaces is the Projects and Agents sides of the notch
panel rather than an item in the menu bar: the section shows the panel's own
screens, a project with a workspace open and Resume with options with each
account's limits, and gains two rows, what each session said last and who
talks to whom. The session menu's actions take their new names, Resume as,
Copy to account and Share with all accounts. The questions say how to open
Projects, that Brow has no menu-bar item, and when the claude -p fallback
runs. Tokens renewed while sessions sit open, Glim's new moods, and what
Projects and Agents read are brought up to date, as are the structured data's
screenshots and features.
Continue a Claude Code session on another account opens Projects from the
notch and moves a session from its menu, with Resume as, Copy to account and
Share with all accounts; Resume with options takes Terminal.app, a copy is
resumed as its account from a terminal, and Settings › Accounts shows which
accounts are linked. Run Claude Code across multiple repositories adds a
project and a workspace from the panel and starts a session with New session.
The accounts guide names the new actions. Pictures nothing shows any more go,
and the sitemap dates every page 21 October.
Brow has no menu-bar item; the development build's own identifier keeps
rebuilds away from what macOS keeps for the installed app, its permissions
included.
Copy to account in place of Migrate to…, the New session form in place of the
launch sheet, Projects and Agents among the parts of Brow, and no menu-bar
item.
The panel on the right is 0.5.0's, rendered from the app's own views: its
footer has share, the pin, refresh and the gear, and its bottom corners
are continuous. The text and the cream icon with its shadow are as they
were.
The hero, the calendar and the sign-in are rendered again from the app's
own views, with the same story, timing and made-up accounts: the panel
now has 0.5.0's footer (share, the pin, refresh, the gear) and its
continuous bottom corners. As in 0.5.0, the click on a button pins the
panel, so the pointer closes it with a click on the desktop, and Team's
row reads "Anthropic rejected the token" with its key lit. Glim's film is
drawn by 0.5.0's pet, which smiles in its sleep. New file names, so no
cached copy of the old ones is shown.
The hero, calendar, sign-in and Glim loops on every page, their stills
for reduced motion and the stills the structured data names, at the
site's 1280 x 800, from the same renders as the README's. New file names,
so no cached copy of the 0.4.0 ones is shown.
The collapsed strip with its 5-HOUR, GLIM and WEEKLY labels is rendered
again from 0.5.0's views, with the same composition and numbers (54 % and
72 %): the strip's bottom corners are now continuous. A new file name, so
no cached copy of the 0.4.0 one is shown.
@efim0v
efim0v merged commit 032daf4 into main Oct 21, 2026
2 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant