The trash button and its hotkey open a confirm dialog instead of a
dropdown. Its Don't ask again checkbox saves a preference that Settings
turns back on under Traffic, as Confirm before clearing.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The shared Tree reset its selection to the last focused row after every
render, so several selected rows collapsed to one whenever the tree rendered
again, as new traffic changing the counts makes it. It now leaves the
selection alone while that row is still in view and selected.
The proxy's sidebar sync also makes All traffic exclusive, groups a saved
search's own OR in parentheses beside other rows, applies System's heading
query, and on Back or Forward selects the rows whose queries make up the
restored filter, compared by shape so AND and OR stay apart.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The actions row moves out of the code editor into ActionsBar, a plain
component a wrapper places over its content. FormatAction reformats an
editor through its ref, and BodyViewModeSwitch names its first state for
the body's format (Pretty, Table, Parts, Preview, Form) next to Raw.
Yaak Proxy's request and response body tabs now share one viewer
choice, with the switch in each tab's bar beside the text viewer's
filter. The choice is remembered for both panes; bodies over the large
size open raw. "Response (Raw)" leaves the proxy's tab menu, while
Yaak's response pane keeps it until the remaining sites move.
SegmentedControl moves from the client into packages/ui.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Filters can hold captured values, so neither the reload's places nor the
launch's last filter go into web view storage: the engine holds the places in
memory while the app runs, and proxy.db's last_filter row keeps the last
filter. A read of a selected flow that answers after the window shows a newer
copy no longer replaces it. The pane and stream harnesses select through
goToPlace, so switching a tab no longer empties their card.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The search box now composes a filter and Enter applies it. The main window's
view (filter, selected flow, card tabs) is a place: a session stack of them
backs Back and Forward (⌘[ ⌘], mouse buttons, a Go menu), the current one
survives a reload, and the last filter comes back at launch. Filters applied
with Enter go into a new filter_history table, listed from the magnifier and
recalled with Up in the empty box.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
While a column is dragged it hides where it is and the columns between it and
where it would land slide by its width, header and cells together, so the gap
shows the drop. One style element carries a rule a column and changes only when
the target does; the rows don't render. On drop the rules go as the order
changes, in the same task, so nothing animates; on Escape the columns slide
home and the column shows again. The drop line and its code are gone.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The ghost of a dragged column is now its header and the cells of the rows in
view, copied once when the drag starts and moved sideways by a transform,
kept within the list; the column dims in place, its cells by one style rule
so no row renders. A built-in column turned on before any reordering takes
its default place again; once the person has an order, a newly shown column
goes at the end.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The line was hidden while a drop would leave the column where it is, so a drag
showed nothing until it crossed a neighbour's middle. It now shows from the
first movement, on the nearer edge of the column's own slot when the drop
would change nothing, and at the first boundary over the mark column. The
choice of boundary moves to a tested function in the columns module.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
A column's label drags it: a lifted ghost follows the pointer, a line marks the
boundary it would drop at, down the header and the rows in view, and the list
scrolls sideways near its edges. A press that doesn't move still sorts, the
resize handles still resize, and Escape cancels. The order is kept with the
other column preferences as a list of ids, and the header menu gains Move Left
and Move Right, the columns menu Reset Column Order.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
A sort key can now name a header or query parameter column (`field:header.x-cache`). The
database sorts it by the value the column shows, read from the stored headers or URL with the
name bound as a parameter, and the app's in-memory sort places live flows the same way. Custom
column headers sort on click and Option-click and their menus' sort items work; the sort is
kept with the columns and removing a column drops it from the sort.
The Add Column field completes `@` and the paths a column accepts, with no colon and no values,
opens its menu on focus, normalises a pasted term, and says why a path cannot be added.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Captured traffic is now cleared as the app launches by default, with a
"Keep between launches" choice that brings the size limit with it. An
install that had a size limit set keeps its traffic. The Proxy settings
tab is regrouped into Proxy, Decryption, Traffic and Terminal, and the
per-body limit row is gone.
The app now watches macOS proxy settings and follows them: when another
app or the user points the system proxy elsewhere, the override shows as
off and the settings saved for restoring are dropped, so quitting puts
back nothing the app didn't set.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Search actions keep the editor focused so a wrapped box does not collapse
under the click. Header scrolls from focus move the rows too. Timeline
details always show their tooltip. A sidebar row shared by same-named
folders or programs in different places offers no path rather than an
arbitrary one.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Columns keep fixed widths, Path included, and the list scrolls sideways
with the header in step instead of dropping columns or capping Host.
Resize handles sit on every column boundary, a double-click resets one,
and a third click on a sorted header goes back to start time, with empty
values sorting lowest. The search box takes up to 44rem and wraps over
the list while focused, its completions as wide as it. The list/detail
handle fills the gutter. Native title tooltips become Yaak's tooltip,
shared buttons gain an opt-in for it, and folder and program rows in the
sidebar get Reveal in Finder and Copy path.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The shared tree treats every node with a children list as a folder and
collapses an empty one before the left arrow moves to its parent. Left
out of the collapsed map, a leaf path never read as collapsed, so the
left arrow kept trying to collapse it and never moved up.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Every domain and path node starts collapsed, so paths stay hidden until
a host is expanded. The nodes the user expands are kept by id in local
storage, so they stay open across launches; hosts seen later start
collapsed. The Domains folder, selection and counts are as before. The
shared tree is unchanged: the proxy hands it its own collapsed atom.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
- Send a flow's write event inside its transaction, so a clear's event,
sent after its own commit, always comes after it.
- Record a saved request only on a flow that still exists, so a save
that finishes after a clear does not bring the flow back.
- Count the total again from the database a second after new flows,
so a flow both in a page and in the events around it settles to the
right count.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
- Replay live changes over a page of older flows, so a slow flow that
ends while the page loads is not lost from the window.
- Read list_flows' page and total from one snapshot, so a flow written
between them is not counted twice.
- Commit a clear's flow deletion only after its bodies' deletion, so a
failure leaves the flows to clear again rather than orphaned bodies.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The app held every flow in memory and redid all of its work for each new
one: the sidebar mounted every domain and path node (its tree scrolled
inside a container that never bounded it), every tree row looked up its
atoms by scanning every atom the family had made, and the layout, detail
pane and list rows re-rendered per flow. At 3,000 flows each new one cost
about 90 ms of main thread, more than the traffic left time for.
The app now holds a window of the newest 2,000 flows, applies new ones in
batches, and loads older ones in pages from the database on scrolling to
the top, through a new list_flows RPC that pages in SQL. The database
keeps every flow.
Also adds clear_flows: an RPC, POST /flows/clear on the control API, and
a Clear button in the header that Cmd+K opens, confirming first.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>