Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 4 additions & 6 deletions .github/fork-features.yml
Original file line number Diff line number Diff line change
Expand Up @@ -3114,16 +3114,16 @@ features:
retire_when: Upstream preserves project scope across sidebar state and every new-thread entry point.

- id: provider-auto-default
title: Start new threads in Auto where the provider reviews actions
title: Apply an Auto default only where the provider reviews actions
status: maintained
prs: [928, 930]
invariants:
- The built-in default permission mode for new threads is Auto. Configs that never chose a mode, including those that kept the old Full access default, use it.
- The built-in default permission mode for new threads stays Full access, as upstream; Auto as the default is the user's choice.
- With Auto as the default, a new thread on a provider whose snapshot does not report its own Auto reviewer (reviewsAutoMode) starts in Full access; Claude, Codex, and Grok report one. An unloaded snapshot or an older server counts as no reviewer.
- Web and mobile drafts follow their selected provider until the user picks a mode; the server's bootstrap thread uses the same resolution. Picking Auto for one thread keeps Auto on every provider.
- The provider canary's auto scenario fails a release whose Auto turn asks for approval of a routine workspace write, or whose provider does not report applying Auto; providers without reviewsAutoMode skip it.
- provider.turn.completed reports approvalRequests, the command, file, and permission approvals the turn raised, alongside its runtimeMode.
rationale: Auto is the safer default where a reviewer approves routine actions, but on a provider without one Auto asks about every action, which would stall threads nobody is watching.
rationale: Auto is the safer default where a reviewer approves routine actions, but on a provider without one Auto asks about every action, which would stall threads nobody is watching. Making Auto the built-in default for everyone was withdrawn before release; approval counts from opted-in users are meant to inform that decision.
implementation_paths:
- apps/mobile/src/features/threads/new-task-flow-provider.tsx
- apps/server/scripts/verify-provider-live.ts
Expand All @@ -3134,22 +3134,20 @@ features:
- apps/web/src/components/ChatView.tsx
- packages/contracts/src/providerPolicy.ts
- packages/contracts/src/server.ts
- packages/contracts/src/settings.ts
- packages/provider-core/src/server/snapshotProbe.ts
- packages/provider-grok/src/server/status.ts
upstream_paths:
- apps/mobile/src/features/threads/new-task-flow-provider.tsx
- apps/server/src/orchestration-v2/ProviderEventIngestor.ts
- apps/web/src/components/ChatView.tsx
- packages/contracts/src/providerPolicy.ts
- packages/contracts/src/settings.ts
tests:
- apps/server/src/orchestration-v2/ProviderEventIngestor.test.ts
- packages/contracts/src/settings.test.ts
upstream:
status: unassessed
tracking: []
retire_when: Upstream defaults new threads to Auto on providers with their own reviewer, or styal returns to a Full access default.
retire_when: Upstream starts new threads in Full access on providers without their own reviewer when Auto is the default.

- id: provider-auto-updates
title: styal managed updates install canary-verified provider versions
Expand Down
2 changes: 1 addition & 1 deletion docs/user/permission-modes.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ composer; it applies to that thread.

Set the default for new threads in **Settings → General → New threads → Permissions**.
Projects can override the environment default. New threads use this setting rather than the
mode of the thread you were viewing. The initial default is **Auto**. With **Auto** as the
mode of the thread you were viewing. The initial default is **Full access**. With **Auto** as the
default, new threads on a provider without automatic review, such as OpenCode or Antigravity,
start in **Full access** instead of asking about every action; choose **Auto** in the composer to
keep it for one thread. Existing threads and modes you choose in a draft keep their permissions.
Expand Down
8 changes: 4 additions & 4 deletions docs/user/styal-differences.md
Original file line number Diff line number Diff line change
Expand Up @@ -65,10 +65,10 @@ works. This overview focuses on desktop and web; the mobile app is a work in pro
[revision adb0420](https://github.com/pingdotgg/t3code/tree/adb04202b25c1c45255e76be9f03f0b346b9c5c4).
[Send while the agent is working](./composer.md#send-while-the-agent-is-working).

- **New threads default to Auto.** Claude, Codex, and Grok threads start in **Auto**, where the
provider's own reviewer approves routine actions and asks about the rest. Providers without
automatic review start in **Full access**. A default you chose yourself still applies. T3 Code
starts new threads in **Full access** as of
- **An Auto default fits each provider.** With **Auto** as the default for new threads, Claude,
Codex, and Grok threads start in **Auto**, where the provider's own reviewer approves routine
actions, and providers without automatic review start in **Full access** instead of asking about
every action. In T3 Code an Auto default makes those providers ask, as of
[revision 30afc56](https://github.com/pingdotgg/t3code/tree/30afc56076c86580d5d913897280bea660d44c79).
[Permission modes](./permission-modes.md).

Expand Down
7 changes: 0 additions & 7 deletions packages/contracts/src/providerPolicy.ts
Original file line number Diff line number Diff line change
Expand Up @@ -31,13 +31,6 @@ export const RuntimeMode = Schema.Literals([
export type RuntimeMode = typeof RuntimeMode.Type;
export const DEFAULT_RUNTIME_MODE: RuntimeMode = "full-access";

/**
* The built-in default for new threads. A provider whose Auto mode has no
* reviewer of its own starts in Full access instead; see
* `resolveNewThreadRuntimeMode`.
*/
export const DEFAULT_NEW_THREAD_RUNTIME_MODE: RuntimeMode = "auto";

/**
* The mode a new thread starts in from the default-permissions setting. Auto
* relies on the provider's own reviewer to approve actions; a provider without
Expand Down
6 changes: 3 additions & 3 deletions packages/contracts/src/settings.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -133,9 +133,9 @@ describe("ClientSettings rich text composer", () => {
});

describe("ServerSettings default permissions", () => {
it("defaults settings that never chose a mode to Auto", () => {
expect(decodeServerSettings({}).defaultRuntimeMode).toBe("auto");
expect(DEFAULT_SERVER_SETTINGS.defaultRuntimeMode).toBe("auto");
it("keeps full access for settings saved before a default was configured", () => {
expect(decodeServerSettings({}).defaultRuntimeMode).toBe("full-access");
expect(DEFAULT_SERVER_SETTINGS.defaultRuntimeMode).toBe("full-access");
});

it("starts a default of Auto in Full access when the provider has no Auto reviewer", () => {
Expand Down
10 changes: 2 additions & 8 deletions packages/contracts/src/settings.ts
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ import {
} from "./model.ts";
import { ModelSelection } from "./modelSelection.ts";
import { ProjectScript, type ProjectMutation } from "./project.ts";
import { DEFAULT_NEW_THREAD_RUNTIME_MODE, RuntimeMode } from "./providerPolicy.ts";
import { DEFAULT_RUNTIME_MODE, RuntimeMode } from "./providerPolicy.ts";
import { BrowserProfile, BrowserProfileId, DEFAULT_BROWSER_PROFILE_ID } from "./browserProfile.ts";
import {
DEFAULT_PREVIEW_APPEARANCE,
Expand Down Expand Up @@ -1195,14 +1195,8 @@ export const ServerSettings = Schema.Struct({
defaultModelSelection: Schema.NullOr(ModelSelection).pipe(
Schema.withDecodingDefault(Effect.succeed(null)),
),
/**
* The mode new threads start in, resolved per provider by
* `resolveNewThreadRuntimeMode`. The old built-in Full access was never
* persisted (defaults are stripped on write), so configs that never chose a
* mode move to the new built-in.
*/
defaultRuntimeMode: RuntimeMode.pipe(
Schema.withDecodingDefault(Effect.succeed(DEFAULT_NEW_THREAD_RUNTIME_MODE)),
Schema.withDecodingDefault(Effect.succeed(DEFAULT_RUNTIME_MODE)),
),
/**
* Per-project overrides of the keys in `PROJECT_SCOPED_SERVER_SETTING_KEYS`.
Expand Down
Loading