Official

tabs

The tabbed detail pane beside the chat: opened files and diffs (JavaScript UI plugin).

The app opens the listing; nothing installs until an agent in your Plugins workspace has read the files and you enable the plugin. In a terminal: cvg install convergence/tabs@0.2.0

Permissions in 0.2.0

  • Read files fs.readMediumReads files in the listed places.Open workspace files in tabsPlaces: the open workspace
  • Read chats chats.readMediumReads your transcripts and chat lists.Reload the open file when an agent finishes a turn
  • Show panels ui.slotsLowShows views in the listed parts of the window.Draw the tabbed pane beside the chatSlots: detail

Files

contract.ts1.2 KB
// The convergence/tabs service: other plugins open and close tabs in the
// detail pane and follow which tab is visible. Zod is the contract; the host
// derives JSON Schema from it and checks every call, result and event.
import * as z from "zod";
import { defineService } from "convergence/services";

export const TabKind = z.enum(["file", "diff", "terminal", "view"]);

// Which tab: tabs are known by kind and path (a terminal's path is its id).
export const TabRef = z.object({ kind: TabKind, path: z.string() });

export const OpenTab = z.object({
  kind: TabKind,
  workspaceId: z.string(),
  path: z.string(),
  // A diff tab shows this unified diff; a view tab draws this view id.
  diff: z.string().optional(),
  view: z.number().optional(),
  title: z.string().optional(),
  icon: z.string().optional(),
});

export const Tabs = defineService("convergence/tabs", "1.0.0", {
  methods: {
    open: { params: OpenTab, result: z.object({ id: z.string() }) },
    close: { params: TabRef, result: z.null() },
    active: { params: z.object({}), result: TabRef.nullable() },
  },
  events: {
    activeChanged: TabRef.nullable(),
  },
});
export type Tabs = typeof Tabs;

Versions

VersionPublishedPlugin APISizePermissionsStatus
0.2.0latestOct 5, 2026>=2 <318.8 KB3 permissionsListed

Reviews and comments

0 threads · 0 reviews

No comments yet.