1use schemars::JsonSchema;
9use serde::{Deserialize, Serialize};
10use std::collections::BTreeMap;
11use std::path::PathBuf;
12
13#[derive(Clone, Copy, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
17pub enum ProtocolVersion {
18 #[serde(rename = "7")]
20 V7,
21}
22
23#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
26#[serde(tag = "operation", rename_all = "snake_case", deny_unknown_fields)]
27pub enum AdapterRequest {
28 PlanServe {
31 protocol_version: ProtocolVersion,
32 input: PlanServeInput,
33 },
34 RenderServe {
37 protocol_version: ProtocolVersion,
38 input: RenderServeInput,
39 },
40}
41
42impl AdapterRequest {
43 #[must_use]
45 pub const fn protocol_version(&self) -> ProtocolVersion {
46 match self {
47 Self::PlanServe {
48 protocol_version, ..
49 }
50 | Self::RenderServe {
51 protocol_version, ..
52 } => *protocol_version,
53 }
54 }
55}
56
57#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
59#[serde(deny_unknown_fields)]
60pub struct PlanServeInput {
61 pub model: ServeModelInput,
62 pub topology: ServeTopology,
63 #[serde(default, skip_serializing_if = "Option::is_none")]
64 pub gateway_backend: Option<String>,
65 #[serde(default, skip_serializing_if = "Option::is_none")]
66 pub pd_router_backend: Option<String>,
67 #[serde(default, skip_serializing_if = "Option::is_none")]
68 pub kv_transfer: Option<KvTransferMechanism>,
69 pub roles: Vec<ServeRoleInput>,
70 #[serde(default)]
71 pub profiling: bool,
72}
73
74#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
77#[serde(deny_unknown_fields)]
78pub struct RenderServeInput {
79 pub model: ServeModelInput,
80 pub topology: ServeTopology,
81 #[serde(default, skip_serializing_if = "Option::is_none")]
82 pub gateway_backend: Option<String>,
83 #[serde(default, skip_serializing_if = "Option::is_none")]
84 pub pd_router_backend: Option<String>,
85 #[serde(default, skip_serializing_if = "Option::is_none")]
86 pub kv_transfer: Option<KvTransferMechanism>,
87 pub allocations: Vec<ServeProcessAllocation>,
88 #[serde(default)]
89 pub profiling: bool,
90}
91
92#[derive(Clone, Copy, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
94#[serde(rename_all = "snake_case")]
95pub enum ServeTopology {
96 Single,
98 PrefillDecode,
100}
101
102#[derive(Clone, Copy, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
104#[serde(rename_all = "snake_case")]
105pub enum ServeRoleKind {
106 Serve,
108 Prefill,
110 Decode,
112}
113
114#[derive(Clone, Copy, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
116#[serde(rename_all = "snake_case")]
117pub enum KvTransferMechanism {
118 Mooncake,
120 Nixl,
122}
123
124#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
127#[serde(deny_unknown_fields)]
128pub struct ServeRoleInput {
129 pub id: String,
130 pub kind: ServeRoleKind,
131 pub replica_count: u32,
132 pub parallelism: Parallelism,
133 pub settings: BTreeMap<String, SettingValue>,
134}
135
136#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
139#[serde(deny_unknown_fields)]
140pub struct ServeRoleResult {
141 pub id: String,
142 pub kind: ServeRoleKind,
143 pub declared_replica_count: u32,
144 pub effective_replica_count: u32,
145 pub effective_settings: BTreeMap<String, SettingValue>,
146 pub effective_parallelism: Parallelism,
147 #[serde(default, skip_serializing_if = "Option::is_none")]
150 pub public_endpoint: Option<EndpointRequirement>,
151 #[serde(default)]
152 pub render_inputs: Vec<RenderInputDeclaration>,
153}
154
155#[derive(Clone, Debug, Default, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
160#[serde(default, deny_unknown_fields)]
161pub struct Parallelism {
162 #[serde(skip_serializing_if = "Option::is_none")]
164 pub outer: Option<ParallelismOuter>,
165 #[serde(skip_serializing_if = "Option::is_none")]
167 pub attention: Option<ParallelismAttention>,
168 #[serde(skip_serializing_if = "Option::is_none")]
170 pub experts: Option<ParallelismExperts>,
171}
172
173impl Parallelism {
174 pub fn merge_from(&mut self, other: &Self) {
177 if let Some(other) = &other.outer {
178 self.outer.get_or_insert_default().merge_from(other);
179 }
180 if let Some(other) = &other.attention {
181 self.attention.get_or_insert_default().merge_from(other);
182 }
183 if let Some(other) = &other.experts {
184 self.experts.get_or_insert_default().merge_from(other);
185 }
186 }
187}
188
189#[derive(Clone, Debug, Default, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
191#[serde(default, deny_unknown_fields)]
192pub struct ParallelismOuter {
193 #[schemars(range(min = 1))]
194 #[serde(skip_serializing_if = "Option::is_none")]
195 pub tensor_parallel_size: Option<u32>,
196 #[schemars(range(min = 1))]
197 #[serde(skip_serializing_if = "Option::is_none")]
198 pub pipeline_parallel_size: Option<u32>,
199}
200
201impl ParallelismOuter {
202 fn merge_from(&mut self, other: &Self) {
203 if other.tensor_parallel_size.is_some() {
204 self.tensor_parallel_size = other.tensor_parallel_size;
205 }
206 if other.pipeline_parallel_size.is_some() {
207 self.pipeline_parallel_size = other.pipeline_parallel_size;
208 }
209 }
210}
211
212#[derive(Clone, Debug, Default, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
214#[serde(default, deny_unknown_fields)]
215pub struct ParallelismAttention {
216 #[schemars(range(min = 1))]
217 #[serde(skip_serializing_if = "Option::is_none")]
218 pub tensor_parallel_size: Option<u32>,
219 #[schemars(range(min = 1))]
220 #[serde(skip_serializing_if = "Option::is_none")]
221 pub data_parallel_size: Option<u32>,
222 #[schemars(range(min = 1))]
223 #[serde(skip_serializing_if = "Option::is_none")]
224 pub context_parallel_size: Option<u32>,
225}
226
227impl ParallelismAttention {
228 fn merge_from(&mut self, other: &Self) {
229 if other.tensor_parallel_size.is_some() {
230 self.tensor_parallel_size = other.tensor_parallel_size;
231 }
232 if other.data_parallel_size.is_some() {
233 self.data_parallel_size = other.data_parallel_size;
234 }
235 if other.context_parallel_size.is_some() {
236 self.context_parallel_size = other.context_parallel_size;
237 }
238 }
239}
240
241#[derive(Clone, Debug, Default, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
243#[serde(default, deny_unknown_fields)]
244pub struct ParallelismExperts {
245 #[schemars(range(min = 1))]
246 #[serde(skip_serializing_if = "Option::is_none")]
247 pub tensor_parallel_size: Option<u32>,
248 #[schemars(range(min = 1))]
249 #[serde(skip_serializing_if = "Option::is_none")]
250 pub data_parallel_size: Option<u32>,
251 #[schemars(range(min = 1))]
252 #[serde(skip_serializing_if = "Option::is_none")]
253 pub expert_parallel_size: Option<u32>,
254 #[schemars(range(min = 1))]
255 #[serde(skip_serializing_if = "Option::is_none")]
256 pub dense_tensor_parallel_size: Option<u32>,
257}
258
259impl ParallelismExperts {
260 fn merge_from(&mut self, other: &Self) {
261 if other.tensor_parallel_size.is_some() {
262 self.tensor_parallel_size = other.tensor_parallel_size;
263 }
264 if other.data_parallel_size.is_some() {
265 self.data_parallel_size = other.data_parallel_size;
266 }
267 if other.expert_parallel_size.is_some() {
268 self.expert_parallel_size = other.expert_parallel_size;
269 }
270 if other.dense_tensor_parallel_size.is_some() {
271 self.dense_tensor_parallel_size = other.dense_tensor_parallel_size;
272 }
273 }
274}
275
276#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
278#[serde(deny_unknown_fields)]
279pub struct ServeModelInput {
280 pub id: String,
281 pub served_name: String,
282}
283
284#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
288#[serde(deny_unknown_fields)]
289pub struct MeasurementModelInput {
290 pub locator: String,
291 pub served_name: String,
292}
293
294#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
296#[serde(deny_unknown_fields)]
297pub struct EndpointAssignment {
298 pub host: String,
299 pub port: u16,
300}
301
302#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
304#[serde(deny_unknown_fields)]
305pub struct ClientEndpointInput {
306 pub protocol: EndpointProtocol,
307 pub host: String,
308 pub port: u16,
309 pub completions_path: String,
310 pub chat_completions_path: String,
311}
312
313#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
315#[serde(tag = "kind", rename_all = "snake_case", deny_unknown_fields)]
316pub enum EvalDefinitionInput {
317 #[serde(rename = "openai_smoke")]
319 OpenAiSmoke {
320 prompt: String,
321 max_tokens: u32,
322 timeout_seconds: u64,
323 },
324 LmEval {
326 task: Box<EvalTaskSourceInput>,
327 #[serde(default)]
328 request_body: BTreeMap<String, SettingValue>,
329 limit: Option<u32>,
330 few_shot: Option<u32>,
331 seed: Option<u64>,
332 trials: u32,
333 max_tokens: Option<u32>,
334 concurrency: Option<u32>,
335 metric: String,
336 #[serde(default)]
337 metric_filter: Option<String>,
338 threshold: f64,
339 timeout_seconds: u64,
340 },
341}
342
343#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
345#[serde(tag = "kind", rename_all = "snake_case", deny_unknown_fields)]
346pub enum EvalTaskSourceInput {
347 BuiltIn { name: String },
349 Bundled {
351 name: String,
352 task_identity: String,
353 path: PathBuf,
354 task_closure_sha256: String,
355 task_definition_sha256: String,
356 prompt_asset_sha256: String,
357 dataset_asset_sha256: String,
358 scorer_sha256: String,
359 },
360 WorkspaceYaml { path: PathBuf },
362}
363
364#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
366#[serde(deny_unknown_fields)]
367pub struct BenchDefinitionInput {
368 pub request_source: BenchRequestSourceInput,
369 pub seed: u64,
370 #[serde(default)]
371 pub request_body: BTreeMap<String, SettingValue>,
372 #[serde(default)]
373 pub request_slo: Option<BenchRequestSloInput>,
374 pub timeout_seconds: u64,
375 #[serde(default)]
376 pub reset_prefix_cache: bool,
377}
378
379#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
381#[serde(tag = "kind", rename_all = "snake_case", deny_unknown_fields)]
382pub enum BenchRequestSourceInput {
383 Random {
386 input_tokens: u32,
387 output_tokens: u32,
388 },
389 Dataset {
392 dataset: BenchDatasetInput,
393 max_input_tokens: u32,
394 output_tokens: Option<u32>,
395 catalog: BenchDatasetCatalogInput,
396 },
397}
398
399#[derive(Clone, Copy, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
401#[serde(rename_all = "snake_case")]
402pub enum BenchDatasetInput {
403 Sharegpt,
404}
405
406#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
408#[serde(deny_unknown_fields)]
409pub struct BenchDatasetCatalogInput {
410 pub upstream_identity: String,
411 pub url: String,
412 pub sha256: String,
413 pub source_format: String,
414 pub license: String,
415 pub cache_path: PathBuf,
416 pub cache_state: BenchDatasetCacheState,
417 pub materialization_identity: String,
418}
419
420#[derive(Clone, Copy, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
422#[serde(rename_all = "snake_case")]
423pub enum BenchDatasetCacheState {
424 Missing,
425 Present,
426}
427
428#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
430#[serde(deny_unknown_fields)]
431pub struct BenchPopulationInput {
432 pub path: PathBuf,
433 pub sha256: String,
434 pub entries: u32,
435 pub tpot_applicable: bool,
436}
437
438#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
441#[serde(deny_unknown_fields)]
442pub struct BenchDatasetPreparationRequest {
443 pub protocol_version: ProtocolVersion,
444 pub model: MeasurementModelInput,
445 pub request_source: BenchRequestSourceInput,
446 pub source_path: PathBuf,
447 pub required_entries: u32,
448 pub seed: u64,
449 #[serde(default)]
450 pub request_body: BTreeMap<String, SettingValue>,
451 pub artifact_dir: PathBuf,
452}
453
454#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
457#[serde(deny_unknown_fields)]
458pub struct BenchTokenCountSummary {
459 pub minimum: u32,
460 pub maximum: u32,
461 pub mean: f64,
462}
463
464#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
466#[serde(deny_unknown_fields)]
467pub struct BenchDatasetPreparationResult {
468 pub schema_version: u32,
469 pub status: ClientStatus,
470 pub materialization_identity: String,
471 pub requested_entries: u32,
472 pub candidate_entries: u64,
473 pub admitted_entries: u64,
474 pub ineligible_entries: u64,
475 #[serde(default)]
476 pub ineligible_reasons: BTreeMap<String, u64>,
477 pub population: Option<BenchPopulationInput>,
478 pub input_tokens: Option<BenchTokenCountSummary>,
479 pub output_tokens: Option<BenchTokenCountSummary>,
480 pub evidence_path: Option<PathBuf>,
481 pub error: Option<String>,
482}
483
484#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
486#[serde(deny_unknown_fields)]
487pub struct BenchRequestSloInput {
488 #[serde(default)]
489 pub request_latency_ms: Option<f64>,
490 #[serde(default)]
491 pub ttft_ms: Option<f64>,
492 #[serde(default)]
493 pub tpot_ms: Option<f64>,
494 pub minimum_good_request_ratio: f64,
495}
496
497#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
500#[serde(untagged)]
501pub enum SettingValue {
502 Bool(bool),
504 Integer(i64),
506 Float(f64),
508 String(String),
510 Array(Vec<SettingValue>),
512 Object(BTreeMap<String, SettingValue>),
514}
515
516#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
518#[serde(tag = "status", rename_all = "snake_case", deny_unknown_fields)]
519pub enum AdapterResponse {
520 Ok {
522 protocol_version: ProtocolVersion,
523 result: Box<AdapterResult>,
524 },
525 Error {
527 protocol_version: ProtocolVersion,
528 error: AdapterError,
529 },
530}
531
532impl AdapterResponse {
533 #[must_use]
535 pub const fn protocol_version(&self) -> ProtocolVersion {
536 match self {
537 Self::Ok {
538 protocol_version, ..
539 }
540 | Self::Error {
541 protocol_version, ..
542 } => *protocol_version,
543 }
544 }
545}
546
547#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
550#[serde(tag = "operation", rename_all = "snake_case", deny_unknown_fields)]
551pub enum AdapterResult {
552 PlanServe { output: Box<PlanServeResult> },
554 RenderServe { output: Box<RenderServeResult> },
556}
557
558#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
562#[serde(deny_unknown_fields)]
563pub struct PlanServeResult {
564 pub integration: IntegrationIdentity,
565 pub roles: Vec<ServeRoleResult>,
566 pub replicas: Vec<ServeReplicaRequirement>,
567 pub links: Vec<ServeRoleLink>,
568 #[serde(default, skip_serializing_if = "Option::is_none")]
569 pub gateway: Option<GatewayPlan>,
570 #[serde(default, skip_serializing_if = "Option::is_none")]
571 pub pd_router: Option<PdRouterPlan>,
572}
573
574#[derive(Clone, Copy, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
578#[serde(rename_all = "snake_case")]
579pub enum RenderSource {
580 ControlPlane,
581 Integration,
582}
583
584#[derive(Clone, Copy, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
586#[serde(rename_all = "snake_case")]
587pub enum FrontendProcessRole {
588 Gateway,
589}
590
591#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
593#[serde(deny_unknown_fields)]
594pub struct FrontendCoRendering {
595 pub process_role: FrontendProcessRole,
596}
597
598#[derive(Clone, Copy, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
600#[serde(rename_all = "snake_case")]
601pub enum FrontendGatewayComponent {
602 Gateway,
603}
604
605#[derive(Clone, Copy, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
607#[serde(rename_all = "snake_case")]
608pub enum FrontendPdRouterComponent {
609 PdRouter,
610}
611
612#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
614#[serde(transparent)]
615pub struct GatewayFrontendBinding(pub [FrontendGatewayComponent; 1]);
616
617#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
619#[serde(transparent)]
620pub struct GatewayPdRouterFrontendBinding(
621 pub (FrontendGatewayComponent, FrontendPdRouterComponent),
622);
623
624#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
628#[serde(untagged)]
629pub enum FrontendComponents {
630 Gateway(GatewayFrontendBinding),
631 GatewayPdRouter(GatewayPdRouterFrontendBinding),
632}
633
634impl FrontendComponents {
635 #[must_use]
636 pub const fn gateway() -> Self {
637 Self::Gateway(GatewayFrontendBinding([FrontendGatewayComponent::Gateway]))
638 }
639
640 #[must_use]
641 pub const fn gateway_pd_router() -> Self {
642 Self::GatewayPdRouter(GatewayPdRouterFrontendBinding((
643 FrontendGatewayComponent::Gateway,
644 FrontendPdRouterComponent::PdRouter,
645 )))
646 }
647
648 #[must_use]
649 pub const fn includes_pd_router(&self) -> bool {
650 matches!(self, Self::GatewayPdRouter(_))
651 }
652}
653
654#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
656#[serde(tag = "kind", rename_all = "snake_case", deny_unknown_fields)]
657pub enum GatewayTarget {
658 Engine { role: String },
660 PdRouter,
662}
663
664#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
667#[serde(deny_unknown_fields)]
668pub struct GatewayPlan {
669 pub backend: String,
670 pub implementation: String,
671 pub implementation_version: String,
672 pub effective_settings: BTreeMap<String, SettingValue>,
673 pub endpoint: EndpointRequirement,
674 pub readiness: ReadinessProbe,
675 #[serde(default)]
676 pub ports: Vec<String>,
677 pub targets: Vec<GatewayTarget>,
678 #[serde(default)]
679 pub render_inputs: Vec<RenderInputDeclaration>,
680 pub render_source: RenderSource,
681 pub co_rendering: FrontendCoRendering,
682}
683
684#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
686#[serde(deny_unknown_fields)]
687pub struct PdRoutingPolicies {
688 pub prefill: String,
689 pub decode: String,
690}
691
692#[derive(Clone, Copy, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
695#[serde(rename_all = "snake_case")]
696pub enum FrontendHandoff {
697 InProcess,
698}
699
700#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
703#[serde(deny_unknown_fields)]
704pub struct PdRouterPlan {
705 pub backend: String,
706 pub implementation: String,
707 pub implementation_version: String,
708 pub effective_settings: BTreeMap<String, SettingValue>,
709 pub policies: PdRoutingPolicies,
710 pub prefill_role: String,
711 pub decode_role: String,
712 pub target_scheme: TargetEndpointScheme,
713 #[serde(default)]
714 pub ports: Vec<String>,
715 pub readiness: ReadinessProbe,
716 pub handoff: FrontendHandoff,
717 #[serde(default)]
718 pub render_inputs: Vec<RenderInputDeclaration>,
719 pub render_source: RenderSource,
720 pub co_rendering: FrontendCoRendering,
721}
722
723#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
726#[serde(deny_unknown_fields)]
727pub struct RenderInputDeclaration {
728 pub source_path: String,
729}
730
731#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
734#[serde(deny_unknown_fields)]
735pub struct SuppliedRenderInput {
736 pub source_path: String,
737 pub text: String,
738 pub sha256: String,
739}
740
741#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
744#[serde(deny_unknown_fields)]
745pub struct ServeReplicaRequirement {
746 pub id: String,
747 pub role_id: String,
748 pub replica_index: u32,
749 pub device_count: u32,
750 pub ports: Vec<String>,
751 pub primary_ports: Vec<String>,
752 pub primary_readiness: ReadinessProbe,
753 pub worker_readiness: ReadinessProbe,
754 #[serde(default, skip_serializing_if = "Option::is_none")]
755 pub capture_target: Option<CaptureTargetRequirement>,
756}
757
758#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
762#[serde(tag = "kind", rename_all = "snake_case", deny_unknown_fields)]
763pub enum ServeProcessAllocation {
764 ModelRank {
765 process: String,
766 role: String,
767 role_kind: ServeRoleKind,
768 replica: u32,
769 rank: u32,
770 rank_count: u32,
771 machine: String,
772 devices: Vec<u32>,
773 model_locator: String,
774 #[serde(default, skip_serializing_if = "Option::is_none")]
775 endpoint: Option<EndpointAssignment>,
776 ports: BTreeMap<String, EndpointAssignment>,
777 cache: String,
778 launch: AllocationLaunch,
779 effective_settings: BTreeMap<String, SettingValue>,
780 effective_parallelism: Parallelism,
781 #[serde(default)]
782 links: Vec<ServeRoleLink>,
783 #[serde(default)]
784 dependencies: Vec<String>,
785 #[serde(default)]
786 render_inputs: Vec<SuppliedRenderInput>,
787 },
788 Frontend {
789 process: String,
790 process_role: FrontendProcessRole,
791 components: FrontendComponents,
792 machine: String,
793 devices: Vec<u32>,
794 endpoint: EndpointAssignment,
795 ports: BTreeMap<String, EndpointAssignment>,
796 cache: String,
797 launch: AllocationLaunch,
798 gateway: Box<GatewayPlan>,
799 #[serde(default, skip_serializing_if = "Option::is_none")]
800 pd_router: Option<Box<PdRouterPlan>>,
801 #[serde(default)]
802 links: Vec<ServeRoleLink>,
803 #[serde(default)]
804 dependencies: Vec<String>,
805 #[serde(default)]
806 render_inputs: Vec<SuppliedRenderInput>,
807 },
808}
809
810#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
812#[serde(tag = "kind", rename_all = "snake_case", deny_unknown_fields)]
813pub enum AllocationLaunch {
814 Local,
815 Ssh { target: String },
816}
817
818#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
821#[serde(tag = "kind", rename_all = "snake_case", deny_unknown_fields)]
822pub enum ServeRoleLink {
823 RequestRouting {
825 source: String,
826 targets: Vec<String>,
827 },
828 KvTransfer {
830 source: String,
831 target: String,
832 mechanism: KvTransferMechanism,
833 },
834 Bootstrap {
836 source: String,
837 target: String,
838 port: String,
839 },
840 SideChannel {
842 source: String,
843 target: String,
844 port: String,
845 },
846}
847
848#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
851#[serde(deny_unknown_fields)]
852pub struct CaptureTargetRequirement {
853 pub window_control: CaptureWindowControlRequirement,
854}
855
856#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
859#[serde(deny_unknown_fields)]
860pub struct CaptureWindowControlRequirement {
861 pub endpoint: CaptureWindowControlEndpoint,
862 pub start: HttpActionSpec,
863 pub stop: HttpActionSpec,
864}
865
866#[derive(Clone, Copy, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
869#[serde(rename_all = "snake_case")]
870pub enum CaptureWindowControlEndpoint {
871 ReplicaEntry,
873 Gateway,
875}
876
877#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
880#[serde(deny_unknown_fields)]
881pub struct RenderServeResult {
882 pub integration: IntegrationIdentity,
883 pub processes: Vec<RenderedServeProcess>,
884}
885
886#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
889#[serde(tag = "kind", rename_all = "snake_case", deny_unknown_fields)]
890pub enum RenderedServeProcess {
891 ModelRank {
892 process: String,
893 role: String,
894 replica: u32,
895 rank: u32,
896 rank_count: u32,
897 launch_files: Vec<LaunchFileDeclaration>,
898 command: ProcessSpec,
899 },
900 Frontend {
901 process: String,
902 process_role: FrontendProcessRole,
903 components: FrontendComponents,
904 launch_files: Vec<LaunchFileDeclaration>,
905 command: ProcessSpec,
906 },
907}
908
909#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
911#[serde(deny_unknown_fields)]
912pub struct LaunchFileDeclaration {
913 pub relative_path: String,
914 pub text: String,
915 pub sha256: String,
916}
917
918#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
920#[serde(deny_unknown_fields)]
921pub struct HttpActionSpec {
922 pub method: HttpMethod,
923 pub path: String,
924}
925
926#[derive(Clone, Copy, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
928#[serde(rename_all = "snake_case")]
929pub enum HttpMethod {
930 Post,
932}
933
934#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
937#[serde(deny_unknown_fields)]
938pub struct IntegrationIdentity {
939 pub adapter_id: String,
940 pub adapter_version: String,
941 pub framework: String,
942 pub framework_version: String,
943}
944
945#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
947#[serde(deny_unknown_fields)]
948pub struct ProcessSpec {
949 pub argv: Vec<String>,
950 pub env: BTreeMap<String, String>,
951}
952
953#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
955#[serde(tag = "kind", rename_all = "snake_case", deny_unknown_fields)]
956pub enum ReadinessProbe {
957 Http { path: String },
959 HttpTargetRegistry(Box<HttpTargetRegistryReadiness>),
962 ProcessAlive,
964}
965
966#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
968#[serde(deny_unknown_fields)]
969pub struct HttpTargetRegistryReadiness {
970 pub target_scheme: TargetEndpointScheme,
971 pub readiness_path: String,
972 pub registry_path: String,
973 pub targets_field: String,
974 pub target_url_field: String,
975 pub target_role_field: String,
976 pub target_healthy_field: String,
977 pub target_bootstrap_port_field: String,
978 pub prefill_role_value: String,
979 pub decode_role_value: String,
980 pub prefill_bootstrap_port: String,
981}
982
983#[derive(Clone, Copy, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
985#[serde(rename_all = "snake_case")]
986pub enum TargetEndpointScheme {
987 Http,
989 Grpc,
991}
992
993#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
996#[serde(deny_unknown_fields)]
997pub struct EndpointRequirement {
998 pub protocol: EndpointProtocol,
999 pub completions_path: String,
1000 pub chat_completions_path: String,
1001 #[serde(default, skip_serializing_if = "Option::is_none")]
1002 pub prefix_cache_reset: Option<HttpActionSpec>,
1003}
1004
1005#[derive(Clone, Copy, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
1007#[serde(rename_all = "snake_case")]
1008pub enum EndpointProtocol {
1009 Http,
1011}
1012
1013#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
1015#[serde(deny_unknown_fields)]
1016pub struct AdapterError {
1017 pub code: AdapterErrorCode,
1018 pub message: String,
1019}
1020
1021#[derive(Clone, Copy, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
1023#[serde(rename_all = "snake_case")]
1024pub enum AdapterErrorCode {
1025 InvalidRequest,
1027 UnsupportedProtocolVersion,
1029 InvalidSettings,
1031 Internal,
1033 UnsupportedOperation,
1035}
1036
1037#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
1040#[serde(deny_unknown_fields)]
1041pub struct EvalClientRequest {
1042 pub protocol_version: ProtocolVersion,
1043 pub workspace_root: PathBuf,
1044 pub workspace_source_exclusions: Vec<PathBuf>,
1045 pub endpoint: ClientEndpointInput,
1046 pub model: MeasurementModelInput,
1047 pub definition: EvalDefinitionInput,
1048 pub case_budget_seconds: f64,
1050 pub artifact_dir: PathBuf,
1051}
1052
1053#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
1057#[serde(deny_unknown_fields)]
1058pub struct BenchClientRequest {
1059 pub protocol_version: ProtocolVersion,
1060 pub endpoint: ClientEndpointInput,
1061 pub model: MeasurementModelInput,
1062 pub definition: BenchDefinitionInput,
1063 #[serde(default)]
1064 pub population: Option<BenchPopulationInput>,
1065 pub case: BenchCaseInput,
1066 pub case_budget_seconds: f64,
1068 pub artifact_dir: PathBuf,
1069}
1070
1071#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
1073#[serde(deny_unknown_fields)]
1074pub struct BenchCaseInput {
1075 pub load_shape: BenchLoadInput,
1076 pub request_count: u32,
1077 #[serde(default)]
1078 pub warmup_request_count: u32,
1079}
1080
1081#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
1083#[serde(tag = "kind", rename_all = "snake_case", deny_unknown_fields)]
1084pub enum BenchLoadInput {
1085 ConcurrencyLimited { concurrency: u32 },
1087 RequestRateLimited {
1089 request_rate: f64,
1090 burstiness: Option<f64>,
1091 },
1092 UnboundedRequestRate,
1094}
1095
1096#[derive(Clone, Copy, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
1098#[serde(rename_all = "snake_case")]
1099pub enum ClientStatus {
1100 Succeeded,
1102 Failed,
1104}
1105
1106#[derive(Clone, Copy, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
1108#[serde(rename_all = "snake_case")]
1109pub enum EvalFailureKind {
1110 TaskResolution,
1111 ProbeTokenizer,
1112 ProbeTransport,
1113 ProbeHttp,
1114 ProbeMalformedResponse,
1115 ProbeGeneratedOnlyLogprobs,
1116 ProbeTokenizerAlignment,
1117 MetricNormalization,
1118}
1119
1120#[derive(Clone, Copy, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
1122#[serde(rename_all = "snake_case")]
1123pub enum EvalMetricComparison {
1124 AtLeast,
1125 AtMost,
1126}
1127
1128#[derive(Clone, Copy, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
1130#[serde(rename_all = "snake_case")]
1131pub enum EvalMetricGateConclusion {
1132 Passed,
1133 Failed,
1134}
1135
1136#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
1138#[serde(deny_unknown_fields)]
1139pub struct EvalNormalizedMetric {
1140 pub source_identity: String,
1141 pub metric: String,
1142 pub filter: Option<String>,
1143 pub native_metric_key: String,
1144 pub value: f64,
1145 pub higher_is_better: bool,
1146}
1147
1148#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
1150#[serde(deny_unknown_fields)]
1151pub struct EvalMetricGate {
1152 pub metric: EvalNormalizedMetric,
1153 pub threshold: f64,
1154 pub comparison: EvalMetricComparison,
1155 pub conclusion: EvalMetricGateConclusion,
1156}
1157
1158#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
1160#[serde(deny_unknown_fields)]
1161pub struct EvalTrialSummary {
1162 pub requested_trials: u32,
1163 pub issued_trials: u32,
1164 pub unissued_trials: u32,
1165 pub completed_trials: u32,
1166 pub request_failure_trials: u32,
1167 pub passed_trials: u32,
1168 pub pass_rate: Option<f64>,
1169 pub per_trial_metric: String,
1170 pub per_trial_filter: Option<String>,
1171 pub higher_is_better: bool,
1172}
1173
1174#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
1176#[serde(deny_unknown_fields)]
1177pub struct EvalClientResult {
1178 pub schema_version: u32,
1181 pub status: ClientStatus,
1182 pub metrics: BTreeMap<String, f64>,
1183 #[serde(default)]
1184 pub normalized_metrics: BTreeMap<String, EvalNormalizedMetric>,
1185 #[serde(default)]
1186 pub gate: Option<EvalMetricGate>,
1187 #[serde(default)]
1188 pub trial_summary: Option<EvalTrialSummary>,
1189 pub native_command: Vec<String>,
1190 #[serde(default)]
1191 pub native_exit_code: Option<i32>,
1192 #[serde(default)]
1193 pub native_timed_out: bool,
1194 pub raw_artifacts: Vec<RawArtifact>,
1195 pub failure_kind: Option<EvalFailureKind>,
1196 pub error: Option<String>,
1197}
1198
1199#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
1201#[serde(deny_unknown_fields)]
1202pub struct BenchClientResult {
1203 pub schema_version: u32,
1206 pub status: ClientStatus,
1207 pub completed_requests: u64,
1208 pub failed_requests: u64,
1209 pub normalization_schema: String,
1210 pub metrics: BTreeMap<String, f64>,
1211 #[serde(default)]
1212 pub request_slo: Option<BenchRequestSloResult>,
1213 pub native_command: Vec<String>,
1214 pub native_exit_code: Option<i32>,
1215 pub raw_artifacts: Vec<RawArtifact>,
1216 pub error: Option<String>,
1217}
1218
1219#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
1221#[serde(deny_unknown_fields)]
1222pub struct BenchRequestSloResult {
1223 pub good_requests: u64,
1224 pub good_request_ratio: f64,
1225 pub goodput: f64,
1226 pub profiling_duration_seconds: f64,
1227 pub profiling_duration_source: String,
1228 pub request_count_reconciled: bool,
1229 #[serde(default)]
1230 pub native_aggregate_good_request_count: Option<u64>,
1231 #[serde(default)]
1232 pub native_aggregate_good_request_count_consistent: Option<bool>,
1233}
1234
1235#[derive(Clone, Debug, Deserialize, Eq, JsonSchema, PartialEq, Serialize)]
1237#[serde(deny_unknown_fields)]
1238pub struct RawArtifact {
1239 pub name: String,
1240 pub kind: String,
1241 pub path: PathBuf,
1242}
1243
1244#[derive(Clone, Debug, Deserialize, JsonSchema, PartialEq, Serialize)]
1248#[serde(deny_unknown_fields)]
1249pub struct AdapterProtocol {
1250 pub request: AdapterRequest,
1251 pub response: AdapterResponse,
1252 #[serde(default, skip_serializing_if = "Option::is_none")]
1253 pub eval_client_request: Option<EvalClientRequest>,
1254 #[serde(default, skip_serializing_if = "Option::is_none")]
1255 pub eval_client_result: Option<EvalClientResult>,
1256 #[serde(default, skip_serializing_if = "Option::is_none")]
1257 pub bench_client_request: Option<BenchClientRequest>,
1258 #[serde(default, skip_serializing_if = "Option::is_none")]
1259 pub bench_client_result: Option<BenchClientResult>,
1260 #[serde(default, skip_serializing_if = "Option::is_none")]
1261 pub bench_dataset_preparation_request: Option<BenchDatasetPreparationRequest>,
1262 #[serde(default, skip_serializing_if = "Option::is_none")]
1263 pub bench_dataset_preparation_result: Option<BenchDatasetPreparationResult>,
1264}