Ship log · v0.7.0 → v0.9.2

Changelog.

Every ship, signed by who shipped it. Features, fixes, policy, and infrastructure for HumanDeploy — in the order they landed.


Spaces and realtime threads

Renamed Areas to Spaces with a new spaces_projects join table. Projects now live inside a Space with scoped brand and context. Thread orchestration moved off a 5-second poll onto Supabase realtime on postgres replication; Slack mutations land on web surfaces sub-second. Migration ran online behind a feature flag with no downtime.


Inflow becomes HumanDeploy

Inflow is now HumanDeploy. Same codebase, new domain (humandeploy.ai), new name, new story. No data migration. Existing tenants kept their workspace, memory, and billing. Founding-tier pricing holds at $2,500/mo.


Credit operations

Added credit-operations with three primitives: reserve, consume, release. Each call runs inside a SELECT FOR UPDATE transaction with an idempotency key, so a retried network call never double-spends. A scope approval reserves against client balance; delivery consumes; cancellation releases. Failed debits write to a recovery table the admin dashboard reads from. Unlimited-credit allowlist accounts bypass reservation.


Expert Slack app

Shipped a second Slack app for experts with separate install, separate OAuth, and shared workspace memory. When a handoff moves into assigned, the expert receives a DM with scope, deadline, and a link to the brand profile. Accept flips state to in_progress; decline routes to next-best-fit via the assignment engine. Assignments with no response in 2 hours expire on a cron and re-route to the next expert in rank. Experts see a kanban of the work they own.


Integrations framework

integration-oauth now handles the full OAuth lifecycle for any provider listed in providerConfigs.ts. Tokens are AES-encrypted before persistence. Connectors extend BaseConnector and inherit per-provider rate limiting (10 req/s default) and circuit breaking on every outbound call (opens at 5 failures, cools for 60s). A health runner scans active connections every 15 minutes. Notion and Google Drive are live on the new path; adding the next provider is a pull request against registry.ts plus two env vars. Slack and Stripe remain on legacy.


Scope generation

Added generate-handoff-scope. A Slack DM from a client is read alongside the workspace brand guardrails and any prior project context, and returns a HandoffScope validated against a Zod schema: deliverables, exclusions, timeline, credit cost. The scope renders back into the thread via Block Kit with Approve and Adjust actions. Approve writes a row into work_requests on the new slack_conversation intake path and moves the handoff to approved. Adjust opens a modal.


Message classifier

Every inbound Slack message now runs through classifyAndRoute() before reaching a handler. It reads thread history and the workspace brand profile, then returns one of eight intent types with a confidence score. Confidence above 0.7 routes to the owning handler; below that triggers a clarifying question. Runs under 400ms p95. Model: GPT-4.1-mini, temperature 0.2, structured JSON output.


Handoffs table

Added the handoffs table with eight states: draft, approved, assigned, in_progress, delivered, revision, complete, cancelled, plus paused. A Postgres trigger validates every transition against an allowed-edges map, so an invalid write fails at the database. Requester-allowed transitions are separated from admin-only ones via RLS. Each state writes its own timestamp column. Downstream surfaces read this row as the source of truth: the client's confirmation, the expert kanban, the admin dashboard.