342 lines
11 KiB
Protocol Buffer
342 lines
11 KiB
Protocol Buffer
syntax = "proto3";
|
|
|
|
package iop;
|
|
|
|
import "google/protobuf/struct.proto";
|
|
|
|
option go_package = "iop/proto/gen/iop";
|
|
|
|
enum RunSessionMode {
|
|
RUN_SESSION_MODE_UNSPECIFIED = 0; // default: create if missing
|
|
RUN_SESSION_MODE_CREATE_IF_MISSING = 1;
|
|
RUN_SESSION_MODE_REQUIRE_EXISTING = 2;
|
|
}
|
|
|
|
enum CancelAction {
|
|
CANCEL_ACTION_UNSPECIFIED = 0; // default: cancel run only
|
|
CANCEL_ACTION_CANCEL_RUN = 1;
|
|
CANCEL_ACTION_TERMINATE_SESSION = 2;
|
|
}
|
|
|
|
// RunRequest initiates an adapter execution on a node.
|
|
message RunRequest {
|
|
string run_id = 1;
|
|
string adapter = 2;
|
|
string target = 3;
|
|
string workspace = 4;
|
|
google.protobuf.Struct policy = 5;
|
|
google.protobuf.Struct input = 6;
|
|
int32 timeout_sec = 7;
|
|
map<string, string> metadata = 8;
|
|
string session_id = 9;
|
|
RunSessionMode session_mode = 10;
|
|
bool background = 11;
|
|
}
|
|
|
|
// RunEvent is a streaming execution event.
|
|
message RunEvent {
|
|
string run_id = 1;
|
|
string type = 2; // start | delta | complete | error | cancelled
|
|
string delta = 3;
|
|
string message = 4;
|
|
string error = 5;
|
|
Usage usage = 6;
|
|
map<string, string> metadata = 7;
|
|
int64 timestamp = 8; // unix nano
|
|
string session_id = 9;
|
|
bool background = 10;
|
|
string node_id = 11;
|
|
string node_alias = 12;
|
|
}
|
|
|
|
enum ProviderTunnelFrameKind {
|
|
PROVIDER_TUNNEL_FRAME_KIND_UNSPECIFIED = 0;
|
|
PROVIDER_TUNNEL_FRAME_KIND_RESPONSE_START = 1;
|
|
PROVIDER_TUNNEL_FRAME_KIND_BODY = 2;
|
|
PROVIDER_TUNNEL_FRAME_KIND_END = 3;
|
|
PROVIDER_TUNNEL_FRAME_KIND_ERROR = 4;
|
|
PROVIDER_TUNNEL_FRAME_KIND_USAGE = 5;
|
|
}
|
|
|
|
// ProviderTunnelRequest asks a node to open a provider HTTP request and relay
|
|
// the raw provider response over ProviderTunnelFrame messages on the existing
|
|
// Edge-Node socket. It is separate from RunRequest, which remains the
|
|
// normalized adapter execution path.
|
|
message ProviderTunnelRequest {
|
|
string run_id = 1;
|
|
string tunnel_id = 2;
|
|
string adapter = 3;
|
|
string target = 4;
|
|
string method = 5;
|
|
string path = 6;
|
|
map<string, string> headers = 7;
|
|
bytes body = 8;
|
|
bool stream = 9;
|
|
int32 timeout_sec = 10;
|
|
map<string, string> metadata = 11;
|
|
string session_id = 12;
|
|
}
|
|
|
|
// ProviderTunnelFrame carries ordered raw provider response data back to Edge.
|
|
// Body bytes are the passthrough source of truth and must not be routed through
|
|
// RunEvent.delta or the lossy event bus fanout.
|
|
message ProviderTunnelFrame {
|
|
string run_id = 1;
|
|
string tunnel_id = 2;
|
|
int64 sequence = 3;
|
|
ProviderTunnelFrameKind kind = 4;
|
|
int32 status_code = 5;
|
|
map<string, string> headers = 6;
|
|
bytes body = 7;
|
|
bool end = 8;
|
|
string error = 9;
|
|
Usage usage = 10;
|
|
map<string, string> metadata = 11;
|
|
int64 timestamp = 12; // unix nano
|
|
string node_id = 13;
|
|
string node_alias = 14;
|
|
}
|
|
|
|
// EdgeNodeEvent is a general edge-node lifecycle/control event envelope.
|
|
// It is separate from RunEvent, which is reserved for adapter execution streams.
|
|
message EdgeNodeEvent {
|
|
string event_id = 1;
|
|
string type = 2; // node.connected | node.disconnected | edge.disconnected | ...
|
|
string source = 3; // edge | node
|
|
string node_id = 4;
|
|
string alias = 5;
|
|
string reason = 6;
|
|
map<string, string> metadata = 7;
|
|
int64 timestamp = 8; // unix nano
|
|
}
|
|
|
|
message Usage {
|
|
int32 input_tokens = 1;
|
|
int32 output_tokens = 2;
|
|
// reasoning_tokens and cached_input_tokens are populated only when the
|
|
// provider reports them. A zero value means "not reported"; downstream metric
|
|
// emit never estimates reasoning tokens from observed reasoning text.
|
|
int32 reasoning_tokens = 3;
|
|
int32 cached_input_tokens = 4;
|
|
}
|
|
|
|
// Heartbeat is sent by both sides to keep the connection alive.
|
|
message Heartbeat {
|
|
int64 timestamp = 1;
|
|
}
|
|
|
|
// CancelRequest asks the node to cancel a running execution.
|
|
message CancelRequest {
|
|
string run_id = 1;
|
|
string adapter = 2;
|
|
string target = 3;
|
|
string session_id = 4;
|
|
CancelAction action = 5;
|
|
}
|
|
|
|
enum NodeCommandType {
|
|
NODE_COMMAND_TYPE_UNSPECIFIED = 0;
|
|
NODE_COMMAND_TYPE_USAGE_STATUS = 1;
|
|
NODE_COMMAND_TYPE_CAPABILITIES = 2;
|
|
NODE_COMMAND_TYPE_SESSION_LIST = 3;
|
|
NODE_COMMAND_TYPE_TRANSPORT_STATUS = 4;
|
|
NODE_COMMAND_TYPE_OLLAMA_API = 5;
|
|
}
|
|
|
|
message NodeCommandRequest {
|
|
string request_id = 1;
|
|
NodeCommandType type = 2;
|
|
string adapter = 3;
|
|
string target = 4;
|
|
string session_id = 5;
|
|
int32 timeout_sec = 6;
|
|
map<string, string> metadata = 7;
|
|
}
|
|
|
|
message NodeCommandResponse {
|
|
string request_id = 1;
|
|
NodeCommandType type = 2;
|
|
string adapter = 3;
|
|
string target = 4;
|
|
string session_id = 5;
|
|
AgentUsageStatus usage_status = 6;
|
|
string error = 7;
|
|
// result carries free-form key/value data for non-usage-status command types
|
|
// (capabilities, session_list, transport_status). usage_status keeps its
|
|
// dedicated typed payload.
|
|
map<string, string> result = 8;
|
|
repeated ProviderSnapshot provider_snapshots = 9;
|
|
}
|
|
|
|
// ProviderSnapshot is the legacy wire name for a node resource/provider status
|
|
// snapshot. category identifies whether the resource is API, CLI, or local
|
|
// inference; provider-pool dispatch is limited to catalog resources referenced
|
|
// by models[].providers.
|
|
message ProviderSnapshot {
|
|
string adapter = 1;
|
|
string status = 2; // unknown|available|unavailable
|
|
int32 capacity = 3;
|
|
int32 in_flight = 4;
|
|
int32 queued = 5;
|
|
|
|
// Provider catalog fields (MVP).
|
|
// id uniquely identifies this provider within its node.
|
|
string id = 6;
|
|
// type is the runtime type (e.g. "ollama", "vllm", "lemonade", "sglang", "openai_api", "cli").
|
|
string type = 7;
|
|
// category classifies the provider; MVP values: api, cli, local_inference.
|
|
string category = 8;
|
|
// served_models lists the model names this provider can actually serve.
|
|
repeated string served_models = 9;
|
|
// health is the observed provider health state (e.g. "healthy", "degraded", "unhealthy").
|
|
string health = 10;
|
|
// load_ratio is the computed in_flight / capacity value. When capacity is 0
|
|
// or unknown the provider is treated as unavailable for selection.
|
|
float load_ratio = 11;
|
|
// lifecycle_capabilities lists coarse lifecycle capability flags (e.g.
|
|
// "list_models", "load_model", "unload_model", "pull_model", "delete_model").
|
|
repeated string lifecycle_capabilities = 12;
|
|
|
|
// Long-context fields.
|
|
int32 long_context_capacity = 13;
|
|
int32 long_in_flight = 14;
|
|
int32 long_queued = 15;
|
|
}
|
|
|
|
message AgentUsageStatus {
|
|
string raw_output = 1;
|
|
string daily_limit = 2;
|
|
string daily_reset_time = 3;
|
|
string weekly_limit = 4;
|
|
string weekly_reset_time = 5;
|
|
map<string, string> metadata = 6;
|
|
}
|
|
|
|
|
|
// Error is returned when a request fails at the transport layer.
|
|
message Error {
|
|
string code = 1;
|
|
string message = 2;
|
|
}
|
|
|
|
// RegisterRequest is sent by node to edge immediately on connect.
|
|
message RegisterRequest {
|
|
string token = 1;
|
|
}
|
|
|
|
// RegisterResponse is sent by edge to node in response to RegisterRequest.
|
|
message RegisterResponse {
|
|
bool accepted = 1;
|
|
string node_id = 2;
|
|
string alias = 3;
|
|
string reason = 4; // rejection reason
|
|
NodeConfigPayload config = 5;
|
|
}
|
|
|
|
// NodeConfigPayload carries all configuration edge pushes to the node.
|
|
message NodeConfigPayload {
|
|
repeated AdapterConfig adapters = 1;
|
|
NodeRuntimeConfig runtime = 2;
|
|
}
|
|
|
|
// AdapterConfig describes one adapter to enable on the node.
|
|
// name is the stable instance identity within a node; for single-instance
|
|
// adapters it may be empty (equivalent to the type name). When a node carries
|
|
// multiple instances of the same adapter type each must have a unique name.
|
|
message AdapterConfig {
|
|
string type = 1; // "mock" | "ollama" | "vllm" | "cli" | "openai_compat"
|
|
bool enabled = 2;
|
|
google.protobuf.Struct settings = 3; // legacy/compat path; new adapters use oneof
|
|
oneof config {
|
|
CLIAdapterConfig cli = 4;
|
|
OllamaAdapterConfig ollama = 5;
|
|
VllmAdapterConfig vllm = 6;
|
|
MockAdapterConfig mock = 7;
|
|
OpenAICompatAdapterConfig openai_compat = 10;
|
|
}
|
|
string name = 8; // stable instance identity; empty = legacy single-instance
|
|
string target = 9; // optional default target/route hint for this instance
|
|
}
|
|
|
|
message MockAdapterConfig {}
|
|
|
|
message CLIAdapterConfig {
|
|
map<string, CLIProfileConfig> profiles = 1;
|
|
}
|
|
|
|
message CLIProfileConfig {
|
|
string command = 1;
|
|
repeated string args = 2;
|
|
repeated string env = 3;
|
|
bool persistent = 4;
|
|
bool terminal = 5;
|
|
int32 response_idle_timeout_ms = 6;
|
|
int32 startup_idle_timeout_ms = 7;
|
|
string output_format = 8;
|
|
CLICompletionMarker completion_marker = 9;
|
|
string mode = 10;
|
|
repeated string resume_args = 11;
|
|
}
|
|
|
|
message CLICompletionMarker {
|
|
string line = 1;
|
|
string regex = 2;
|
|
}
|
|
|
|
message OllamaAdapterConfig {
|
|
string base_url = 1;
|
|
int32 context_size = 2;
|
|
int32 capacity = 3;
|
|
int32 max_queue = 4;
|
|
int32 queue_timeout_ms = 5;
|
|
int32 request_timeout_ms = 6;
|
|
}
|
|
|
|
message VllmAdapterConfig {
|
|
string endpoint = 1;
|
|
int32 capacity = 2;
|
|
int32 max_queue = 3;
|
|
int32 queue_timeout_ms = 4;
|
|
int32 request_timeout_ms = 5;
|
|
}
|
|
|
|
message OpenAICompatAdapterConfig {
|
|
string provider = 1;
|
|
string endpoint = 2;
|
|
map<string, string> headers = 3;
|
|
int32 capacity = 4;
|
|
int32 max_queue = 5;
|
|
int32 queue_timeout_ms = 6;
|
|
int32 request_timeout_ms = 7;
|
|
}
|
|
|
|
// NodeRuntimeConfig carries legacy node runtime metadata. Execution admission
|
|
// must not use this as a node-wide global gate; provider/resource capacity owns
|
|
// concurrency.
|
|
message NodeRuntimeConfig {
|
|
int32 concurrency = 1; // legacy compatibility, 0/unset means no node-wide limit
|
|
reserved 2;
|
|
}
|
|
|
|
enum NodeConfigRefreshStatus {
|
|
NODE_CONFIG_REFRESH_STATUS_UNSPECIFIED = 0;
|
|
NODE_CONFIG_REFRESH_STATUS_APPLIED = 1;
|
|
NODE_CONFIG_REFRESH_STATUS_RESTART_REQUIRED = 2;
|
|
NODE_CONFIG_REFRESH_STATUS_FAILED = 3;
|
|
NODE_CONFIG_REFRESH_STATUS_SKIPPED = 4;
|
|
}
|
|
|
|
// NodeConfigRefreshRequest is sent by edge to a connected node to push a new config payload.
|
|
message NodeConfigRefreshRequest {
|
|
string request_id = 1;
|
|
NodeConfigPayload config = 2;
|
|
repeated string changed_paths = 3;
|
|
}
|
|
|
|
// NodeConfigRefreshResponse is returned by the node to acknowledge or report failure.
|
|
message NodeConfigRefreshResponse {
|
|
string request_id = 1;
|
|
NodeConfigRefreshStatus status = 2;
|
|
repeated string restart_required_paths = 3;
|
|
string error = 4;
|
|
}
|