@ai-ecoverse/slicc-spectrum 2.9.0 → 2.9.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -431,10 +431,11 @@ Sessions stay alive while hidden; `exit` closes the tab.
431
431
 
432
432
  What the agents' browser control is doing.
433
433
  It opens on the most recently driven tab (`.focused`), or on the tab overview: cards (`li[data-id]`, `data-controlled` while an agent drives the tab, `data-pulse` when another tab starts being driven, without switching to it) with a thumbnail, the agent and a small **Stop <agent>** (`data-action="stop-agent"`), and an address bar to open a URL.
434
- The focused tab has **All tabs** (`data-action="all-tabs"`), a tab picker (a list of tabs at 720 px and wider), the URL with **Copy** (`data-action="copy-url"`) and **Open** (`data-action="open-tab"`, activates the tab), who's using it (`.driving[data-driving=agent|user|none]`; a controlled tab without an agent reads **In use** and has no Stop) with a small **Stop <agent>** (`data-action="stop-agent"`) in the same row, which keeps its height with or without an agent, a view-only preview (`figure[data-view]`: `live` while watching with a frame under 3 s old, `shot` with "Updated N s ago", `none`) and the recent actions (`li[data-action-id][data-kind][data-status]`, failures with their error inline), the tab's own filtered first, then the latest 50, with **Show more** (`data-action="more-actions"`) adding 50 earlier ones each time up to all the port has ("Showing the latest N of M"); the list scrolls and takes focus.
434
+ The focused tab is preview-first: **All tabs** (`data-action="all-tabs"`) with a tab picker (a list of tabs at 720 px and wider) on one row, the URL with **Copy** (`data-action="copy-url"`) and **Open** (`data-action="open-tab"`, activates the tab) on the next, who's using it (`.driving[data-driving=agent|user|none]`; **Watching <agent>** while an agent drives, **In use** when a controlled tab has no agent and no Stop) with a small **Stop <agent>** (`data-action="stop-agent"`) in the same row, which keeps its height with or without an agent, a watching-only preview (`figure[data-view]`: `live` while watching with a frame under 3 s old, `shot` with "Updated N s ago", `none`; the caption says **Watching only**) that keeps a 16:10 frame, and a **Recent actions** feed (`.feed`) that fills the leftover height.
435
+ Recent actions (`li[data-action-id][data-kind][data-status]`, failures with their error inline) are newest first: the tab's own filtered first, then the latest 50, with **Show more** (`data-action="more-actions"`) adding 50 earlier ones each time up to all the port has ("Showing the latest N of M"); the list scrolls and takes focus.
436
+ Consecutive identical done actions fold into one row (`li[data-group]`) with a count (`×n`).
435
437
  Actions with a URL (`open`, `goto`, `request`) expand (`data-action="action-url"`, `aria-expanded`) to show the full URL, or the request line, under the shortened one.
436
- Below 480 px they fold into **Recent actions (n)**, a chevron disclosure counting all of them, with the last one showing.
437
- The tab the user opened (or **All tabs**), expanded URLs and an open **Recent actions** hold for every view of the panel on the same model, so a layout switch keeps them; a closed tab lets go, and the panel opens on the most recently driven tab again.
438
+ The tab the user opened (or **All tabs**) and expanded URLs hold for every view of the panel on the same model, so a layout switch keeps them; a closed tab lets go, and the panel opens on the most recently driven tab again.
438
439
  Labels, URLs and errors are text only.
439
440
  With no tabs and `browser.via` `null` in the network status, it says browser control isn't connected (`data-browser="none"`) with the extension link and the commands to install and run slicc (`curl -fsSL https://get.sliccy.ai/slicc | sh`, then `slicc`, or `npx sliccy@next` with Node).
440
441
  The Browser rail button carries a dot (`data-driven`) while a tab is in use.
@@ -483,10 +484,10 @@ Values go only to `vault.put` and are never kept on the element or put in an eve
483
484
  The head shows **Locked** or **Unlocked**, then, when `status.policy` marks a file `paused`, a second light (`[data-paused]`) "Paused: {file} is missing" ("Paused: {file} and 1 more are missing" for both), and the lock mode ("Unlocks automatically in this browser", "Unlocks with a passkey" or "Unlocks with a passphrase"); locked, the vault's **Unlock** button (`slicc-vault-button[data-action=unlock]`); unlocked, **Lock** (`data-action="lock"`, with `lock`) and the vault's **Protect with a passkey** (lock `auto`) or **Change protection** button (`data-action="protect"`).
484
485
  A status line (`[data-availability]`) says "Waiting for the vault" while `availability()` is `connecting` or `waiting` (or `status()` is `null` without it), and "Unlock the vault to continue" while `scrub.needed` and not `scrub.ready`.
485
486
  Waiting requests show under **Waiting for you** (`[data-request]`, the agent's `prompt` as plain text under "From the agent, not checked by SLICC:", capped at 200 characters, and "Expires in N min"), with **Enter value** (`data-action="answer"`, which fires `value-request` with `{ id, vault }` for the `<slicc-value-request>` on the same vault) for `value` requests and **Cancel request** (`data-action="cancel-request"`); `oauth`, `jerk-seal`, `jerk` and `unseal` requests say what they ask for and offer Cancel request only.
486
- With `backupReminder: 'due'`, an alert (`[data-backup]`) offers **Export backup** (`data-action="export"`) and **Not now** (`data-action="dismiss-backup"`, with `dismissBackupReminder`).
487
487
  **Add secret** (`data-action="add-secret"`, `[data-form=add]`, a name and a value; a name that exists asks before it replaces the value; with `vault.enter` and `valueFrame`, a name and **Next** (`data-action="enter-value"`), which opens `vault.enter` (with `replace: true` after that question) and shows the vault's own field (`[data-form][data-entry] slicc-vault-value`); **Replace value** opens `vault.enter({ name, kind, provider | server, replace: true })` and that field at once; the frame's `done` closes the form and says it was saved (with the name the form asked for when `done` carries none), and Cancel, Escape, the frame's `escape`, another form and a change of vault cancel the request), **Import…** (`data-action="import"`, `[data-form=import]`: Bundle, KeePass or six, a file, an optional password, then a pick of candidates, all checked but the `refused` ones (disabled, with their reason), marked "Replaces a secret" when they exist, with their suggested rules as untrusted text and a note that the file's rules aren't applied, and **Import N**, which sends `{ name, kind }` for a candidate of another `kind`; then "Imported N" and "Skipped NAME: reason" for each skipped name, from `reasons`) and **Export…** (`data-action="export"`, `[data-form=export]`: a passphrase twice, at least 8 bytes, behind a confirmation, downloaded as `slicc-secrets-<yyyy-mm-dd>.slicc-vault`, with "Last exported" or "Never exported" from `exportedAt`).
488
488
  Saved shows "Saved NAME in the vault" (`[data-said]`).
489
- The secrets, sorted by name (`li[data-secret][data-state]`, with `[data-rules]`, `[data-exits]` only when restricted, `[data-exec]` (any command, the listed commands, every bash) and how often programs were given it today, `[data-source]`, `[data-used]`, `[data-expires]`; a model record or an MCP token no rule names reads “Used for” (`[data-used-for]`, model requests to its provider or requests to its MCP server, by the agent) instead of where it's sent, with its account's state as its light, and shows its Provider (`[data-provider]`, the account's name) or Server (`[data-server]`)) offer **Replace value** (`data-action="replace"`, for `settings`, `process` and `import:*` secrets that aren't sign-ins) and **Remove** (`data-action="remove"`, behind a confirmation, passing the secret's `kind`), and removed ones, under **Removed**, **Restore** (`data-action="restore"`; ENOENT reads "Removed too long ago to restore").
489
+ The secrets, sorted by name (`li[data-secret][data-state]`, with `[data-rules]`, `[data-exits]` only when restricted, `[data-exec]` (any command, the listed commands, every bash) and how often programs were given it today — the last argv in that "Revealed to programs…" line is capped at 120 characters with an ellipsis, while Activity keeps the full command; the allow-list and reveal lines are not CSS-clamped, `[data-source]`, `[data-used]`, `[data-expires]`; a model record or an MCP token no rule names reads “Used for” (`[data-used-for]`, model requests to its provider or requests to its MCP server, by the agent) instead of where it's sent, with its account's state as its light in `.aside` beside the row actions, and shows its Provider (`[data-provider]`, the account's name) or Server (`[data-server]`)) offer **Replace value** (`data-action="replace"`, for `settings`, `process` and `import:*` secrets that aren't sign-ins) and **Remove** (`data-action="remove"`, behind a confirmation, passing the secret's `kind`), and removed ones, under **Removed**, **Restore** (`data-action="restore"`; ENOENT reads "Removed too long ago to restore").
490
+ With `backupReminder: 'due'`, an alert below the list (`[data-backup]`) offers **Export backup** (`data-action="export"`) and **Not now** (`data-action="dismiss-backup"`, with `dismissBackupReminder`).
490
491
  Locked, every form (Add secret and Replace value without `vault.enter`, Import, Export; with it, the vault's field unlocks itself) says "Unlock the vault first" (`p[data-locked]`) next to the vault's own small **Unlock** button (`slicc-vault-button[data-action=unlock]`) and disables its submit; once unlocked, the form stays open with what was typed and its submit enables.
491
492
  Vault errors show their message, EACCES as "Unlock the vault first", an EACCES with `cause: 'policy-paused'` as "Secrets are paused until the missing policy file is back", and ENOTSUP as "This arrives with a later vault version".
492
493
  Each action shows only when the port has its method.
@@ -721,10 +721,15 @@ var DummyBrowser = class extends Emitter {
721
721
  this.finish(action.id, "Stopped");
722
722
  if (changed) this.emit("tabs", this.list());
723
723
  }
724
- watch(tabId) {
724
+ #watch = null;
725
+ lastWatch() {
726
+ return this.#watch;
727
+ }
728
+ watch(tabId, size) {
725
729
  const tab = () => this.#tabs.find((candidate) => candidate.id === tabId);
726
730
  if (!tab()?.controlled) return () => {
727
731
  };
732
+ this.#watch = { tabId, size: size ? { ...size } : void 0 };
728
733
  const send = () => {
729
734
  const now2 = tab();
730
735
  if (!now2?.controlled) return;
@@ -732,7 +737,10 @@ var DummyBrowser = class extends Emitter {
732
737
  };
733
738
  const timer = setInterval(send, 500);
734
739
  void this.#clock.sleep(0).then(send);
735
- return () => clearInterval(timer);
740
+ return () => {
741
+ clearInterval(timer);
742
+ if (this.#watch?.tabId === tabId) this.#watch = null;
743
+ };
736
744
  }
737
745
  #changed() {
738
746
  this.emit("tabs", this.list());