Every catalog provider can now drive agent execution:
- Azure OpenAI -> Chat Completions at the deployment URL with api-key
- AWS Bedrock -> Converse API signed natively with SigV4 (node:crypto)
- Vertex AI -> Gemini generateContent with a service-account JWT (RS256)
exchanged for a cached access token
The credential resolver maps each cloud profile to the turn's needs; the router
covers all 16 providers. Pure encoders, the SigV4 signer and the GCP auth are
unit-tested; no AWS/GCP SDK dependency.
New 'Custom OpenAI-compatible' and 'Custom Anthropic-compatible' providers let
an agent run against any compatible endpoint by base URL + key: the turn posts
Chat Completions (/chat/completions) or Anthropic Messages (/v1/messages) at the
configured base URL. Backfilled into existing orgs by migration 037.
The loop was gated to API-key providers, so a GPT-account (Codex) CEO failed
with 'requires an API-key provider'. Port Pi's actual request handlers natively
so every agent-capable provider runs:
- chat-completions turn for xAI, Groq, Mistral, Cerebras, OpenRouter
- Codex SSE Responses for GPT account
- Anthropic-OAuth (Claude Code system + beta headers) for Claude Pro/Max
- Copilot proxy (baseUrl from the token) for GitHub Copilot
- Gemini Code Assist for Google Antigravity
A credential resolver refreshes expired OAuth access tokens at request time and
persists the rotation; the runner routes by provider key and passes the resolved
credential. The heartbeat now retries failed tasks (bounded to 3 attempts) so a
run that failed on the old gate recovers automatically. Cloud providers
(Azure/Bedrock/Vertex) still report a clear unsupported message.
The queue worker now also enqueues one run per actionable assigned task of a
heartbeat-enabled agent with an enabled provider and no run yet, so after the
CEO hires and delegates, its reports start their tasks on their own. Each task
is enqueued at most once. The team-building prompt is now scoped to managers
(no manager) with an empty team, so reports execute their task instead.
The new app reached a real LLM but never ran an agent: the kickoff task_run
sat queued forever and runTask was a single text completion with no tools.
This adds the missing runtime:
- provider-tool-turn: OpenAI Responses + Anthropic Messages tool-use turns
- agent-tools + deliverable-writer: hire_agent, create_task,
update_task_status, write_deliverable (workspace-scoped, traversal-safe)
- agent-run-loop: real tool-use loop, capped iterations
- task-queue-worker: claims queued runs in a transaction and executes them
task-execution now drives the loop; a background worker auto-runs the
bootstrap CEO run so it hires its team, delegates tasks, and writes the first
deliverable into the bound workspace. Autonomy is gated by AGENTCOMPANY_NEW_AUTORUN
(tests run with it off to stay hermetic).
Closes the Anthropic OAuth gap with a native Claude Pro/Max device sign-in
(reusing the OAuth engine) and adds three OpenAI-compatible API-key
providers. Model lists are sourced from the provider registry. A backfill
migration seeds the new providers into existing organizations idempotently.
Implement the official OAuth login flows natively (ported from pi-ai's
reference): GitHub Copilot device-code, GPT account (ChatGPT Codex) and
Google Antigravity authorization-code + PKCE via a loopback callback server.
Obtained credentials are stored as JSON through the existing secret vault.
Onboarding and Settings now run the real sign-in instead of pasting an
access token.
The browser-platform governance data (account grants, social audit records,
browser actions with policy decisions) was recorded but never shown. Add a
read-only Access & activity section to the Social page that lists who is
authorized on each account with what scope, and a merged, policy-tagged
timeline of recent social and agent browser actions.
Onboarding only accepted a typed workspace path, which is error-prone and
diverged from the original wizard. Add a pickDirectory IPC backed by Electron's
open-directory dialog and a Choose button beside the path field, so the founder
can select a real folder for agent artifacts.
The editMessage/deleteMessage IPC and their audit events existed but had no UI.
Add an inline editor and delete control on a member's own, non-deleted
messages; show an edited marker and render deleted messages as a muted
placeholder. Thread the handlers from ChatPage through the timeline.
The conversation header search button was inert. Toggle a search field that
filters the channel's root messages by body text; clearing or pressing Escape
restores the full timeline. Search stays scoped to the open space, so results
respect the membership the user already has.
social-service.ts exceeded 500 lines and mixed the Electron browser-login
window concern with the social domain logic. Move openSocialLoginWindow and its
navigation policy into social-login-window.ts and re-export the public types.
Behaviour unchanged; unit and e2e suites remain green.
chat-service.ts exceeded 500 lines. Move the row-shape interfaces, slash-command
parsing/validation and the small standalone helpers into chat-service-internal.ts
and import them back. Pure relocation with no behaviour change; the chat
governance suite (82 tests) and e2e remain green.
FilesPage had grown past 500 lines by carrying the tree, table, grid, card
visuals and all pure helpers inline. Extract file-helpers.ts, FileVisuals,
FilesTree, FilesTable and FilesGrid under pages/files/, leaving FilesPage as the
orchestrator. Behaviour is unchanged; the pinned-card radius is corrected to 10
to match the design.
The Work board used auto-fit columns that reflowed and clustered at the left;
pin it to four equal columns (minmax(0,1fr) so they shrink rather than
overflow). On Home, render approval kind and risk as humanized labels instead
of raw enum strings.
Attachments rendered identically regardless of how they were transferred. When
an agent sends a file through the handoff path, mark its attachment card with an
AI-to-AI badge so the design's handoff indicator is present.
chat_presence was recorded (active, waiting_approval, thinking) but never
surfaced. Map each status to a colour and render a presence dot on the
counterpart's avatar in the direct-message list, matching the design.
The PRD calls for company, division, department, project, pod and ad-hoc
spaces, but only company, department, project and direct were accepted. Add
division, pod and ad_hoc to the command contract, the service whitelist and the
new-space dialog. The space_type column is free text, so no migration is
needed.
Any employee in the org could send a message as the board (freeze, takeover,
force-approval), because requireSender only checked that the board sender was a
valid employee. Enforce the approval_decider role (org_admin inherits it) via
IdentityAccessService, which also records an access decision for denied
attempts, and only render the thread board-control form for principals who hold
that authority — others get a read-only view of past interventions.
The Home budget card invented a cap of 4x the allocated total and listed agent
counts under a money heading; the Members table hardcoded every human's
department as Executive with a blank budget. Source the cap from the real
per-department monthly budget envelope (hiring policies), show real allocated
dollars per provider, and render humans (which carry no department or budget)
as not-applicable instead of a fabricated department.
Chat and Settings escaped the content padding with a hardcoded
calc(100vh - 44px) height and negative margins, while Files and Social let the
whole page scroll, so secondary panes (channel list, settings nav, file tree)
scrolled away. Add a .content.flush modifier the Shell applies to the chat,
settings, files and social routes, plus a reusable .pane-scroll region, and
rework those pages to fill the content area with each pane scrolling on its
own. Removes the magic-number coupling to the topbar height.
Each page rendered its primary actions inside the scrolling body, so they
drifted away on scroll and diverged from the design, which places them in the
topbar next to the breadcrumbs. Introduce a TopbarSlotContext that the Shell
publishes from its topbar action area, and a TopbarActions portal that Home,
Team, Work, Files, Social and Approvals use to render their controls there.