Commit Graph
543 Commits
Author SHA1 Message Date
Eric WagonerandClaude Opus 5.5 9500b8062a Safari's masked extension frames stay out of Sentry
Safari reports an extension's scripts as webkit-masked-url://hidden/, so the
extension filter never matched them; WIZWAR-17 was one such failure.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-11-03 17:17:02 -05:00
Eric WagonerandClaude Opus 5.5 e3681cd703 The family list welcomes Wyrm, and Dip seats as many as its map allows
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-11-03 15:57:07 -05:00
Eric WagonerandClaude Opus 5.5 e2194a49e7 Table talk replayed from the chronicle wears its speaker's color
A rejoin rebuilds chat from tableTalk events, whose player was not counted
as the actor, so those lines took the turn owner's mark instead.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-11-03 15:49:39 -05:00
Eric WagonerandClaude Opus 5.5 b0993032f7 Chaos asks for your answer in a modal, as the other out-of-turn choices do
The shield-or-surrender question was a slip in the sidebar, below the
board on a phone, and a player who missed it left the table waiting.
It now takes the centre of the screen like a Ward or a giant's push:
who cast it, what it does, a Full Shield button when you hold one, and
the way through.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-31 22:56:32 -04:00
Eric WagonerandClaude Opus 5.5 f372b0a3ca A fire imp asks for no orders, and Chaos asks for no shield you do not hold
The creature slip offered "attack ready" for every creature you control,
but only trolls, skeletons and shadows strike on command; a fire imp
neither moves nor takes orders, so it no longer awaits any. The Chaos
slip told every player to tap a Full Shield; a hand without one is now
told so and offered only the way through.

The duel skill gains game fifteen's lessons.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-31 22:54:00 -04:00
Eric WagonerandClaude Opus 5.5 3a9f39780b A wallet that lost the seat last sat in takes it back on load
The cap that dropped the newest seat left wallets without the very seat
their browser was sitting in, so a reload landed in the Peanut Gallery.
That seat is also kept on its own; loading the wallet now restores it
from there when it is missing.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-31 12:07:13 -04:00
Eric WagonerandClaude Opus 5.5 bca4d5eba7 The seat wallet's cap of fifty drops the oldest seats, not the newest
Seats are kept newest first, but the cap kept the tail, so a browser
holding more than fifty threw away the seat it had just taken. Sitting
in that room hid it (each room message remembers the seat again); the
first games poll after moving to another table lost it for good.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-30 18:13:09 -04:00
Eric WagonerandClaude Opus 5.5 29025f2ccb A rejoin's replayed chronicle replaces the one the table already holds
When a socket dropped and came back, the server sent the whole chronicle
again and the client appended it, so every turn was counted twice and
the instant-replay eyes asked for turns the server had not reached ("no
such turn yet"). The talk count doubled the same way and never reset
between rooms; it now resets with the chronicle.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-30 18:01:04 -04:00
Eric WagonerandClaude Opus 5.5 0ced49ca6c A wall beyond the door you stand at and have unlocked is in sight for wall-aimed spells
Edge casts judged sight on the bare board, where every door hangs shut,
so the threshold peek (an unlocked, held, removed or pickable door at
your elbow) reached only square-aimed spells. Ramses (BDFS) unlocked a
door with MASTER KEY and could not STONE TO WATER the wall beyond it
until he stepped through. Edge casts now see with the caster's eye.
Widening only: refused casts never entered ledgers.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-21 20:10:56 -04:00
Eric WagonerandClaude Opus 5.5 8dcdfd2415 Mist shields its wizard from creatures; a glued square turns with its sector; Waterbolt splits the power it is cast with
Three of Ramses's reports from KFJL:
- Rev 28: MIST-BODY's "may not attack or be attacked" holds against
  creatures. A wraith's or democratic monster's touch, a fire imp's
  scorch, and an ordered troll/skeleton/shadow blow all pass the mist by;
  older games keep the strike their ledgers recorded. The automaton no
  longer orders its creatures at a misted wizard.
- ROTATE and RELOCATE SECTOR threw while GLUE was down: GLUE keeps its
  cell's key in the sustained effect's edge slot, and the remap read it
  as an edge. It maps as a cell now (the throw never reached a ledger,
  so this ships ungated).
- WATERBOLT's damage/knockback split was sized by the NUMBER's face; the
  engine weighs POWERSTONE's +1 and AMPLIFY's doubling, so a 5 behind a
  powerstone was refused for not totalling 6.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-21 19:54:43 -04:00
Eric WagonerandClaude Opus 5.5 3368a92cf5 A seat link is cut from a report to the end of its string, so a name with a quote, an ampersand or a hash in it cannot end the cut before the token
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0141G6xqLeNRYEtviLWSB5Up
2026-10-17 20:14:41 -04:00
Eric WagonerandClaude Opus 5.5 6606853332 A seat link's token is cut from an error report and its breadcrumbs before it goes to Sentry, since the history breadcrumb for taking the link out of the address bar still names it
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0141G6xqLeNRYEtviLWSB5Up
2026-10-17 20:12:49 -04:00
Eric WagonerandClaude Opus 5.5 c984bb4b56 A crash report's strings reach the log on one line: anyone may post one, and a line break could otherwise forge another log line
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0141G6xqLeNRYEtviLWSB5Up
2026-10-16 17:06:24 -04:00
Eric WagonerandClaude Opus 5.5 956c908867 Chromium's crash reports reach the server, which logs each and files it in Sentry as a warning, and the page's own errors name the room and seat and leave extensions' failures out
A tab that crashes takes the page's error reporting down with it, so the
page never says so. Every page now names a default Reporting API endpoint,
/api/reports, where Chromium sends a crash report after the fact; the
server logs the room, the reason when one is given, and the browser, and
files a warning that rings no bell. Other report types are ignored, and an
address may send ten an hour.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0141G6xqLeNRYEtviLWSB5Up
2026-10-16 17:03:14 -04:00
Eric WagonerandClaude Opus 5.5 9a1c98ca55 The host's phrase button says it makes a transfer phrase, and its tooltip says who it is for and how the player uses it
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0141G6xqLeNRYEtviLWSB5Up
2026-10-16 15:54:54 -04:00
Eric WagonerandClaude Opus 5.5 4b7e05713d The host can give a stuck player's seat to the clockwork and make a phrase that brings a seat back, and a socket in a background tab no longer drops every minute
A "seats" button beside "transfer seat" opens the host's panel. In a game
under way, "give to the clockwork" lets an automaton play a person's seat
from the next beat, with their hand, treasures and place untouched; a
standIn line on the ledger records it, the chronicle says so, the
stand-in never talks under the person's name, and the person's token
opens nothing after. "Make a phrase" mints the four-word phrase for any
person's seat; claiming it re-seats on a new token, and a seat the
clockwork stood in for goes back to its person mid-turn. A rematch holds
a stood-in seat for its person. The gallery now has its own claim box,
for a player who opens the invite link in a fresh browser.

The client's watchdog pinged and then closed a socket quiet for 45
seconds. A background tab's timers run about once a minute, so the last
pong was always a minute old when it looked, and idle tabs reconnected
every 58 seconds. It now closes only when its own ping went unanswered.
The server pings every socket at the protocol level every 30 seconds and
drops one that left the last ping unanswered, so a crashed browser's
socket no longer lingers until TCP gives up.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0141G6xqLeNRYEtviLWSB5Up
2026-10-16 15:43:24 -04:00
Eric WagonerandClaude Opus 5.5 7ef0c1bc14 On a phone, the table fits the screen and another wizard's turn says whose it is
The masthead's links never wrapped, so a game widened a phone's page to
nearly 500px: the page scrolled sideways and the opening roll-off sat off
its centre. And while an automaton's opening turn played back, the rail
that says "Automaton is taking their turn" sat below the fold, leaving a
board that moved on its own. Of 132 bot-first games, 13 humans never made
a move. Now the links wrap, and a caption over the board names the wizard
whose turn it is, and says when yours is next.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-14 17:35:39 -04:00
Eric WagonerandClaude Opus 5.5 5ea0d4fdec The keeper can bring back a seat a browser lost: a reseat line on the ledger gives that wizard's seat a new token and the old one opens nothing after, wizwar-reseat.sh on the host asks for it through a keeper door that listens on the loopback alone and opens only to a key the deploy makes once, and the link it prints carries the seat in the fragment, which leaves the address bar at once and is kept only when no seat held in this browser still opens and the server takes it; a gallery watching a game in play is told both ways back, the front page asks before forgetting a game not yet finished, and the server's tests now run with the rest
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01MbtUPJ24P6vc6tE1x6RS3m
2026-10-13 18:33:04 -04:00
Eric WagonerandClaude Opus 5.5 1b9acfd7c4 The family list carries the kit's current pitches
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01MbtUPJ24P6vc6tE1x6RS3m
2026-10-13 09:29:58 -04:00
Eric WagonerandClaude Opus 5.5 6f86076712 The hosting line says what it promises: chipping in unlocks nothing, and nothing is held back without it
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01MbtUPJ24P6vc6tE1x6RS3m
2026-10-13 09:23:44 -04:00
Eric WagonerandClaude Opus 5.5 c64ff70ed4 The table speaks plainer, and keeps its whimsy
Wording throughout the app, the server's messages and the engine's
refusals trades its stacked dashes for sentences, while the maze still
trusts you to honor its curses, the gallery still listens, and the
clockwork still learns its best tricks from the humans at the table.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-11 11:29:07 -04:00
Eric WagonerandClaude Opus 5.5 aeb58bdf4a A treasure carried home says so, and a turn out of steps points at End turn
A first-time player banked a stolen chest, stepped off with no moves left,
and left (NQ6S): the score changed only in the turn bar's quiet tally, and
a still board with no word read as a game that had stopped. Now a slip
announces the score for the rest of the turn, and once the steps are
spent the turn bar says to cast or end the turn while End turn beckons.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-03 20:36:27 -04:00
Eric WagonerandClaude Opus 5.5 ceb22a9898 A stale tab's reload no longer throws: a retired chunk resolves to nothing, and nothing is mounted
The preload-error handler claims the failed import and reloads; the import
then resolves empty, and destructuring its default threw (WIZWAR-X).

Fixes WIZWAR-X

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_016ZtFMp1AtjXPBY4Z69Tx81
2026-09-30 12:06:34 -04:00
Eric WagonerandClaude Opus 5.5 cbf897ff13 Pages show the hall-wide notice, when there is one, at the top
The keeper's hall-announce writes one file on the shared host; the site
serves it at /hall/announcement.json, and the banner shows it with the time
in the reader's own clock, dismissable one notice at a time.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-29 13:03:37 -04:00
Eric WagonerandClaude Opus 5.5 d5b92d9a63 The about panel no longer credits its making
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-27 20:58:56 -04:00
Eric WagonerandClaude Opus 5.5 a4196480ce A socket's own error closes that socket, not the server
A message over the size limit or a malformed frame raised an error on
the socket, which had no listener, and Node ended the process: one
message from anyone could take the server down until systemd restarted
it. The socket is terminated instead.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-27 01:21:45 -04:00
Eric WagonerandClaude Opus 5.5 3a6b0ff43e Credibility pass: the illusion tests roll both ways, and the seams from the last batch are sanded
Scope: 66b5c06..HEAD.

- The rev-27 illusion tests search seeds for a believed and a doubted
  roll and assert fixed life totals; seed 42 alone never believed, so
  the BLUNT pricing went unchecked.
- Three docblocks stranded above newly inserted functions are back on
  their own (openCreatureStack, resolvedBlow, castTrace).
- POWER ATTACK's life trade is one helper instead of three copies; the
  goat's charge distance is one helper for its validator, its ram and
  its pricing.
- The family list loads once into a shared store; the lobby and gallery
  share one talk filter; Board uses the engine's neighbor().
- A creature's blow shows the card that summoned it by the creature's
  kind, not by matching the blow's display name.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-26 00:22:20 -04:00
Eric WagonerandClaude Fable 5.1 e97deb8d6f A commanded troll lights only the walls and doors beside it, and so does a punching wizard
Every interior line lit whenever an edge was wanted; the troll can strike
only the four sides of its own square, so only those light now.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-24 21:37:13 -04:00
Eric WagonerandClaude Fable 5.1 7a0a972452 A creature's blow is named on the stack: the counter is played against the fire imp's scorch, not a punch (SC59)
The caster whose creature is countered now sees "your attack, answered"
and the name of their own blow, instead of an incoming punch with the
opponent's counter card standing in the attack slot.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-24 21:32:34 -04:00
Eric WagonerandClaude Fable 5.1 c3f63d4eb7 Rev 27: an ILLUSIONARY ATTACK is priced as the spell it fakes, so BLUNT and the rest meet it (UPJE)
The believed illusion was dealt after the counter trail had already
spoken over a zero, so a BLUNT trailed for nothing and the full points
landed. Now the fake carries its spell's points through the pipeline and
the belief roll decides whether the weighed blow lands. Games dealt under
rev 26 and before replay as they were.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-24 20:40:47 -04:00
Eric WagonerandClaude Fable 5.1 991a6a0443 ROTATE SECTOR asks which way: the tap marks the sector, a button turns it (UPJE)
The clockwise checkbox sat in the hint strip and defaulted on, so a
sector could spin the way nobody meant. The turn is now its own decision,
in the dock beside the board like the teleport confirm.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-24 20:30:37 -04:00
Eric WagonerandClaude Fable 5.1 6c29f750fc A waterwall tapped onto a slime washes it: the tap picks the face across the caster's approach (B8G9)
The flash for a corridor-line card no longer names wizards, bushes and
slimes as its targets; it gives the card's own line hint.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-23 22:59:14 -04:00
Eric WagonerandClaude Fable 5.1 0244cffb4b The family list knows the hall: about panels link to gamehall.kestrelsnest.social, and a new game gets a card there
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-23 21:04:31 -04:00
Eric WagonerandClaude Fable 5.1 9f1358496d The about panel says the games are free and where the hosting tip jar is
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-23 20:25:05 -04:00
Eric WagonerandClaude Fable 5.1 c79fdb4adb The collection is Kestrel's Hall
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-23 19:51:06 -04:00
Eric WagonerandClaude Fable 5.1 9d087ccaa1 The front page and the about page point to the other games of the Kestrel's Nest
The list is the kit's family.json, shipped as /family.json and refreshed
at deploy when the kit is beside this checkout.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-23 12:26:49 -04:00
Eric WagonerandClaude Fable 5.1 13a6fc2603 The host may let the Peanut Gallery talk
A gallery line wears the eye and a name that no wizard at the table
holds; the host opens or hushes it from the lobby or the mast, on the
ledger, and the gallery is reined per address.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-23 09:47:26 -04:00
Eric WagonerandClaude Fable 5.1 35d805fda3 The lobby tells a caller what hour it is where the keeper lives, and that other games can go on in another tab
WIZWAR_KEEPER_TZ names the zone (Eastern by default); the room carries it
and the client words the hour by the minute.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-23 08:49:37 -04:00
Eric WagonerandClaude Fable 5.1 31bfcf7bc0 Rev 26: BUTT-HEAD's ram is priced into the blow, so STRENGTH, AMPLIFY, and the counters weigh it (KWUZ)
Ramses cast STRENGTH, then an amplified BUTT-HEAD three squares off, and
the goat dealt three: the ram was applied in onResolved, past the pipe
that doubles, soaks, and adds. Older games keep the bare distance.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-23 08:16:30 -04:00
Eric WagonerandClaude Fable 5.1 5193b12b8e Rev 25: a bush or the ooze is attacked like a wall — POWER ATTACK counts, thrown weapons land at its foot
Older games took neither; both sides pinned.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-22 12:19:15 -04:00
Eric WagonerandClaude Fable 5.1 66b5c06f17 Credibility pass: one teleport step, one bell, one step type, and the comments that argued are gone
Since 6e49fc9. Engine: the teleport BFS in the view and the engine's
wallIgnoringDistance share teleportStep; the counter trail is weighed
between steps instead of on six arms; the bush attack takes its
adjacency from SIDES like the wall does; a dead redirected clause, a
one-member set, an identity ternary, and a stray try/catch are gone;
two tests now assert what their names promise. Server: KEEPER and
MAX_SEATS live in rooms.ts, the three Sentry bells ring through one
helper, the unread reply field is dropped, actingSeat comes from the
engine, and the protocol header names every message. Web: ReplayStep
is one type, cardName one helper, the say box and the reference section
one snippet each, the keeper's name arrives from the server rather than
the source, and the lifesaver ruling that ruled nothing is out.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-22 09:56:49 -04:00
Eric WagonerandClaude Fable 5.1 c4a555f8df Fuller banter pools, and the blow's own names decide who dealt pain and who killed
Damage lands on the defender's step, so a trigger keyed to the actor
never credited the attacker: across thirty three-bot games the kill line
fired zero times and the dealt-pain line five, against 328 takes. Both
now read the attackResolved, punched, and died events themselves.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-22 09:39:05 -04:00
Eric WagonerandClaude Fable 5.1 be96dd6047 The archmage cuts off a winning delivery and aims at the leader when no kill is on the table
Reuben's three wins today were walked home unseen: the clockwork
fought whoever stood in front of it. Now a delivery that would end the
game pulls every automaton toward that wizard's home (where the banked
gold is lifted off the doorstep) or the road to it, and among visible
targets the thief still dies first, a kill is still taken, and only then
does the aim shift to whoever has more treasures banked. Measured with
deploy/brain-trial.mjs, which seats the working tree's brain against an
older checkout's at one table.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-22 09:11:34 -04:00
Eric WagonerandClaude Fable 5.1 11e9f950c6 Reports are threads, and every turn of one rings the desk's bell
A player answers the desk under its reply from their lobby, proven by
the seat the report was filed from; the lobby shows the exchange in
order and says whose word is pending. A new report, a player's answer,
and a desk reply each raise a Sentry issue on the keeper's phone — the
first two from the server, the last from the reply script itself,
straight to Sentry from the droplet. The Desktop digest lists the
answers, and the desk's rule reads a report as reopened when the last
word is the player's.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-21 12:08:55 -04:00
Eric WagonerandClaude Fable 5.1 071e7ce988 A permanent spell settles 'for good' in the chronicle and the receipt, not for a billion turns
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-21 11:09:01 -04:00
Eric WagonerandClaude Fable 5.1 48350a3686 A report may carry a screenshot
The 🐞 form takes a picture beside its words — PNG, JPEG, or WebP, under
2.5 MB, previewed before sending. The socket's message cap is far too
small for one, so the picture goes through a plain HTTP door after the
report is filed, addressed to the report's id, one per report within
the hour, checked by its own first bytes, and kept in feedback-images/
beside the reports with a line on the report saying so. The desk's
skill knows where to look.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-21 11:02:59 -04:00
Eric WagonerandClaude Fable 5.1 d76a18d5e6 A seated wizard leaves the room's expected list, live and on rebuild
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-17 23:45:36 -04:00
Eric WagonerandClaude Fable 5.1 1ebd6dbe47 A refused seat is logged, and the wallet drops a seat only on the second refusal in a row
A lost seat mid-game is the costliest quiet failure this table has: one
refusal around a restart cost Kestrel PRPM's seat with nothing in the
journal to say why.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-17 23:22:00 -04:00
Eric WagonerandClaude Fable 5.1 f738957100 Rev 24: a REFLECTION against a permanent curse afflicts both wizards
"If this spell is REFLECTed, both players take 1/2 point of damage per
space moved" (WALKING DEAD); "In case of REFLECTION, both players are
affected" (IDIOT); SLOW DEATH follows REFLECTION's own rule that a
spell works for both parties. A permanent curse has no duration for
the reflection's split to halve, so the caster went untouched; the
curse is now laid on them as well, as if cast back. Older games replay
as they were; PRPM, reflected at seq 108 with no move since, was
re-stamped to 24 at its table's request.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-17 23:07:41 -04:00
Eric WagonerandClaude Fable 5.1 f26893f45b The reel measures its padding inside its width, so it stays within the share page on a phone
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG
2026-09-17 21:18:35 -04:00