Skip to content

Epic: v1alpha1 API updates (Profile, Workspace, Task, Gateway) #563

Open
0 of 2 issues completed
Open

Description

@yongruilin

Summary

Track the ax.io/v1alpha1 API updates across Profile, Workspace, Task, and Gateway on top of Agent Substrate v1.0.0 (#561). Where Agent Substrate already defines the underlying schema (e.g. EgressRule), AX imports api/ateapi/v1/ateapi.proto directly rather than duplicating types, with pkg/apis/v1alpha1/ organized into per-domain .proto files (#564, #565).

Checklist & Sub-issues

Reference Proto Sketch (pkg/apis/v1alpha1/)

Note: Reference MVP target schema; minor field names, numbers, or comments may be refined in individual PRs.

ax.proto — Control-plane gRPC service
syntax = "proto3";

package ax.v1alpha1;

import "pkg/apis/v1alpha1/gateway.proto";
import "pkg/apis/v1alpha1/model.proto";
import "pkg/apis/v1alpha1/task.proto";
import "pkg/apis/v1alpha1/workspace.proto";

option go_package = "github.com/google/ax/pkg/apis/v1alpha1";

service AX {
  // Tasks
  rpc GetTask(GetTaskRequest) returns (Task);
  rpc ListTasks(ListTasksRequest) returns (ListTasksResponse);
  rpc CreateTask(CreateTaskRequest) returns (Task);
  rpc DeleteTask(DeleteTaskRequest) returns (DeleteTaskResponse);
  rpc SuspendTask(SuspendTaskRequest) returns (Task);
  rpc ResumeTask(ResumeTaskRequest) returns (Task);

  // Workspaces
  rpc GetWorkspace(GetWorkspaceRequest) returns (Workspace);
  rpc ListWorkspaces(ListWorkspacesRequest) returns (ListWorkspacesResponse);
  rpc CreateWorkspace(CreateWorkspaceRequest) returns (Workspace);
  rpc DeleteWorkspace(DeleteWorkspaceRequest) returns (DeleteWorkspaceResponse);

  // Gateways
  rpc GetGateway(GetGatewayRequest) returns (Gateway);
  rpc ListGateways(ListGatewaysRequest) returns (ListGatewaysResponse);
  rpc CreateGateway(CreateGatewayRequest) returns (Gateway);
  rpc UpdateGateway(UpdateGatewayRequest) returns (Gateway);
  rpc DeleteGateway(DeleteGatewayRequest) returns (DeleteGatewayResponse);

  // Models (unchanged for MVP)
  rpc GetModel(GetModelRequest) returns (Model);
  rpc ListModels(ListModelsRequest) returns (ListModelsResponse);
  rpc UpdateModel(UpdateModelRequest) returns (Model);
  rpc DeleteModel(DeleteModelRequest) returns (DeleteModelResponse);
}
common.proto — Shared metadata & compute Profile
syntax = "proto3";

package ax.v1alpha1;

import "google/protobuf/timestamp.proto";

option go_package = "github.com/google/ax/pkg/apis/v1alpha1";

message ObjectMeta {
  string name = 1;
  string atespace = 2;
  google.protobuf.Timestamp create_time = 3;
  string uid = 4;
  map<string, string> labels = 5;
  string owner = 6;
  google.protobuf.Timestamp update_time = 7;
  google.protobuf.Timestamp delete_time = 8;
}

message Condition {
  string type = 1;
  string status = 2;
  google.protobuf.Timestamp update_time = 3;
  string reason = 4;
  string message = 5;
}

message ResourceList {
  string cpu = 1;
  string memory = 2;
}

message ResourcesSpec {
  ResourceList limits = 2;
}

// Profile maps 1:1 to a shared, content-addressed Substrate ActorTemplate
// (ax-<sha256[:16]>) within an atespace.
message Profile {
  string image = 1;
  ResourcesSpec resources = 2;
  // Optional Substrate ActorTemplate in the same atespace used to seed omitted fields.
  string ate_actor_template = 5;
}

message SecretKeyRef {
  string name = 1;
  string key = 2;
}
gateway.proto — Reusable Gateway & outbound L7 credential injection (#549)
syntax = "proto3";

package ax.v1alpha1;

import "api/ateapi/v1/ateapi.proto";
import "pkg/apis/v1alpha1/common.proto";

option go_package = "github.com/google/ax/pkg/apis/v1alpha1";

message GatewayRef {
  string name = 1;
}

message Gateway {
  string api_version = 1;
  string kind = 2;
  ObjectMeta metadata = 3;
  GatewaySpec spec = 4;
}

message GatewaySpec {
  // Outbound allowlist rules imported directly from Agent Substrate ateapi.v1
  // (http, https with effects.replace_headers, tls_passthrough).
  // Copied onto the actor's EgressPolicy at creation time.
  repeated substrate.ateapi.v1.EgressRule egress = 1;
}

message GetGatewayRequest {
  string atespace = 1;
  string name = 2;
}
message ListGatewaysRequest {
  string atespace = 1;
}
message ListGatewaysResponse {
  repeated Gateway gateways = 1;
}
message CreateGatewayRequest {
  Gateway gateway = 1;
}
message UpdateGatewayRequest {
  Gateway gateway = 1;
}
message DeleteGatewayRequest {
  string atespace = 1;
  string name = 2;
}
message DeleteGatewayResponse {}
workspace.proto — Pre-warmed Workspace & WorkspaceSetup
syntax = "proto3";

package ax.v1alpha1;

import "pkg/apis/v1alpha1/common.proto";
import "pkg/apis/v1alpha1/gateway.proto";

option go_package = "github.com/google/ax/pkg/apis/v1alpha1";

message Workspace {
  string api_version = 1;
  string kind = 2;
  ObjectMeta metadata = 3;
  WorkspaceSpec spec = 4;
  WorkspaceStatus status = 5;
}

message WorkspaceRef {
  string name = 1;
  string path = 2;
}

message WorkspaceSpec {
  repeated GitRepo git = 1 [deprecated = true];
  repeated File files = 2 [deprecated = true];
  MCPConfig mcp = 3;
  SkillsConfig skills = 4 [deprecated = true];
  Profile profile = 5;
  WorkspaceSetup setup = 6;
}

message WorkspaceSetup {
  repeated GitRepo git = 1;
  repeated File files = 2;
  SkillsConfig skills = 3;
  repeated string commands = 4;
  // Granted ONLY to the temporary setup actor during pre-warm; never inherited by Tasks.
  GatewayRef gateway = 5;
}

message GitRepo {
  string name = 1;
  string repo = 2;
  string branch = 3 [deprecated = true];
  string dir = 4;
  int32 depth = 5;
  string ref = 6;
}

message File {
  string path = 1;
  string content = 2;
}

message SkillsConfig {
  repeated SkillRegistry registries = 1;
  string path = 2;
}

message SkillRegistry {
  string provider = 1;
  string project = 2;
  string query = 3;
}

message MCPConfig {
  repeated MCPRegistry registries = 1;
  repeated MCPServer servers = 2;
}

message MCPRegistry {
  string provider = 1;
  string project = 2;
  string query = 3;
  repeated MCPServer servers = 4;
}

message MCPServer {
  string name = 1;
  string endpoint = 2;
  string command = 3;
  repeated string args = 4;
  string transport = 5;
}

message WorkspaceStatus {
  string phase = 1;
  repeated Condition conditions = 4;
  string last_setup_error = 5;
}

message GetWorkspaceRequest {
  string atespace = 1;
  string name = 2;
}
message ListWorkspacesRequest {
  string atespace = 1;
  int64 limit = 2;
  int64 offset = 3;
}
message ListWorkspacesResponse {
  repeated Workspace workspaces = 1;
}
message CreateWorkspaceRequest {
  Workspace workspace = 1;
}
message DeleteWorkspaceRequest {
  string atespace = 1;
  string name = 2;
}
message DeleteWorkspaceResponse {}
task.proto — TaskSpec & lifecycle TaskStatus (#542)
syntax = "proto3";

package ax.v1alpha1;

import "google/protobuf/duration.proto";
import "google/protobuf/struct.proto";
import "google/protobuf/timestamp.proto";
import "google/rpc/status.proto";
import "pkg/apis/v1alpha1/common.proto";
import "pkg/apis/v1alpha1/gateway.proto";
import "pkg/apis/v1alpha1/workspace.proto";

option go_package = "github.com/google/ax/pkg/apis/v1alpha1";

message Task {
  string api_version = 1;
  string kind = 2;
  ObjectMeta metadata = 3;
  TaskSpec spec = 4;
  TaskStatus status = 5;
}

message TaskSpec {
  repeated string commands = 2;
  repeated EnvVar env = 3;
  WorkspaceRef workspace = 5;
  bool debug = 6;
  google.protobuf.Struct config = 7;
  Goal goal = 8;
  RetryConfig retry = 9;
  Budget budget = 10;
  TaskRuntimeSpec runtime = 11;
  // Copied onto the actor at creation; tasks without a Gateway have no external egress.
  GatewayRef gateway = 12;
  string session_id = 13;
  Profile profile = 17;
}

message EnvVar {
  string name = 1;
  string value = 2;
}

message TaskRuntimeSpec {
  reserved 1, 2;
  optional int32 uid = 3;
  google.protobuf.Duration idle_timeout = 4;
}

message RetryConfig {
  int32 max_retries = 1;
  google.protobuf.Duration initial_backoff = 2;
  google.protobuf.Duration max_backoff = 3;
  double backoff_multiplier = 4;
}

message Goal {
  string spec = 3;
}

message Budget {
  int64 max_total_tokens = 1;
  int64 max_tool_calls = 2;
  google.protobuf.Duration max_wallclock = 3;
}

enum TaskState {
  TASK_STATE_UNSPECIFIED = 0;
  TASK_STATE_IDLE = 1;
  TASK_STATE_WORKING = 2;
  TASK_STATE_REQUIRES_ACTION = 3;
  TASK_STATE_COMPLETED = 4;
  TASK_STATE_FAILED = 5;
  TASK_STATE_CANCELLED = 6;
  TASK_STATE_QUEUED = 7;
  TASK_STATE_SUSPENDED = 8;
  TASK_STATE_SUSPENDING = 9;
}

enum TaskResult {
  TASK_RESULT_UNSPECIFIED = 0;
  TASK_RESULT_SUCCEEDED = 1;
  TASK_RESULT_FAILED = 2;
  TASK_RESULT_CANCELLED = 3;
  TASK_RESULT_UNVERIFIED = 4;
}

message TaskOutcome {
  TaskResult result = 1;
  google.rpc.Status status = 3;
  int32 exit_code = 10;
  string output = 11;
  google.protobuf.Struct structured_output = 12;
}

message StatusDetail {
  string reason = 1;
  string detail = 2;
}

message TaskStatus {
  reserved 5, 6;
  string phase = 1 [deprecated = true];
  string id = 2 [deprecated = true];
  string actor = 3;
  string worker_ip = 4 [json_name = "workerIP", deprecated = true];
  repeated Condition conditions = 7;
  TaskState state = 8;
  StatusDetail status_detail = 9;
  TaskOutcome outcome = 10;
  int32 attempt = 11;
  string ate_actor_template = 12;
  int64 generation = 15;
  repeated string resolved_argv = 17;
  google.protobuf.Timestamp init_start_time = 18;
  google.protobuf.Timestamp current_start_time = 19;
  google.protobuf.Timestamp end_time = 20;
  google.protobuf.Duration working_duration = 21;
  string previous_failure = 22;
}

message GetTaskRequest {
  string atespace = 1;
  string name = 2;
}
message ListTasksRequest {
  string atespace = 1;
  int64 limit = 2;
  int64 offset = 3;
}
message ListTasksResponse {
  repeated Task tasks = 1;
}
message CreateTaskRequest {
  Task task = 1;
}
message DeleteTaskRequest {
  string atespace = 1;
  string name = 2;
}
message DeleteTaskResponse {}
message SuspendTaskRequest {
  string atespace = 1;
  string name = 2;
}
message ResumeTaskRequest {
  string atespace = 1;
  string name = 2;
}

Deferred Past MVP

  • Model API redesign and internal runner wire-protocol (runner.proto) changes
  • Goal verifiers and explicit Profile snapshot_fidelity / worker_selector fields (seeded via Profile.ate_actor_template for MVP)
  • Gateway ingress rules (agent-substrate/substrate#431) and automatic egress rule expansion
  • ForkTask, CancelTask, UpdateTask, TaskSpec.suspend, parent_task_id cascading, and shared workspace volumes (agent-substrate/substrate#1637)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Labels

Type

No type

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions