wick_config/v1/
conversions.rs

1use std::collections::HashMap;
2mod impls;
3mod root_configs;
4mod triggers;
5
6use option_utils::OptionUtils;
7use wick_asset_reference::AssetReference;
8
9use crate::config::components::{self, ComponentReference, GrpcUrlComponent, ManifestComponent};
10use crate::config::package_definition::{PackageConfig, RegistryConfig};
11use crate::config::{
12  self,
13  ComponentDefinition,
14  ComponentImplementation,
15  ComponentOperationExpression,
16  CompositeComponentImplementation,
17  ExecutionSettings,
18  HighLevelComponent,
19  HostConfig,
20  OperationDefinition,
21  TemplateConfig,
22  WasmCommandConfig,
23  WasmRsComponent,
24};
25// use flow_expression_parser::parse_id;
26use crate::config::{
27  AppConfiguration,
28  Binding,
29  CliConfig,
30  HttpRouterConfig,
31  HttpTriggerConfig,
32  ProxyRouterConfig,
33  RawRouterConfig,
34  RestRouterConfig,
35  StaticRouterConfig,
36  TcpPort,
37  TimeTriggerConfig,
38  TriggerDefinition,
39  UdpPort,
40};
41use crate::error::ManifestError;
42use crate::utils::{opt_str_to_ipv4addr, VecTryMapInto};
43use crate::{v1, Result};
44
45impl TryFrom<v1::PackageDefinition> for PackageConfig {
46  type Error = ManifestError;
47
48  fn try_from(value: v1::PackageDefinition) -> std::result::Result<Self, Self::Error> {
49    let registry_config = match value.registry {
50      Some(registry_def) => Some(RegistryConfig::try_from(registry_def)?),
51      None => None,
52    };
53
54    Ok(Self {
55      files: value.files.try_map_into()?,
56      registry: registry_config,
57    })
58  }
59}
60
61impl TryFrom<PackageConfig> for v1::PackageDefinition {
62  type Error = ManifestError;
63
64  fn try_from(value: PackageConfig) -> std::result::Result<Self, Self::Error> {
65    let registry_def = match value.registry {
66      Some(registry_config) => Some(v1::RegistryDefinition::try_from(registry_config)?),
67      None => None,
68    };
69
70    Ok(v1::PackageDefinition {
71      files: value.files.try_map_into()?,
72      registry: registry_def,
73    })
74  }
75}
76
77impl TryFrom<super::helpers::Glob> for config::Glob {
78  type Error = ManifestError;
79
80  fn try_from(value: super::helpers::Glob) -> std::result::Result<Self, Self::Error> {
81    Ok(Self::new(value.0))
82  }
83}
84
85impl TryFrom<config::Glob> for super::helpers::Glob {
86  type Error = ManifestError;
87
88  fn try_from(value: config::Glob) -> std::result::Result<Self, Self::Error> {
89    Ok(Self(value.glob))
90  }
91}
92
93impl TryFrom<v1::RegistryDefinition> for RegistryConfig {
94  type Error = ManifestError;
95
96  fn try_from(value: v1::RegistryDefinition) -> std::result::Result<Self, Self::Error> {
97    Ok(Self {
98      host: value.host,
99      namespace: value.namespace,
100    })
101  }
102}
103
104impl TryFrom<RegistryConfig> for v1::RegistryDefinition {
105  type Error = ManifestError;
106
107  fn try_from(value: RegistryConfig) -> std::result::Result<Self, Self::Error> {
108    Ok(Self {
109      host: value.host,
110      namespace: value.namespace,
111    })
112  }
113}
114
115impl TryFrom<v1::WasmComponentConfiguration> for WasmRsComponent {
116  type Error = ManifestError;
117  fn try_from(value: v1::WasmComponentConfiguration) -> Result<Self> {
118    Ok(Self {
119      reference: value.reference.try_into()?,
120      config: value.with.try_map_into()?,
121      operations: value.operations.try_map_into()?,
122      volumes: value.volumes.try_map_into()?,
123      max_packet_size: value.max_packet_size,
124    })
125  }
126}
127
128impl TryFrom<v1::WasmComponentModel> for config::WasmComponentDefinition {
129  type Error = ManifestError;
130  fn try_from(value: v1::WasmComponentModel) -> Result<Self> {
131    Ok(Self {
132      reference: value.reference.try_into()?,
133      config: value.with.try_map_into()?,
134      operations: value.operations.try_map_into()?,
135      volumes: value.volumes.try_map_into()?,
136    })
137  }
138}
139
140impl TryFrom<config::WasmComponentDefinition> for v1::WasmComponentModel {
141  type Error = ManifestError;
142  fn try_from(value: config::WasmComponentDefinition) -> Result<Self> {
143    Ok(Self {
144      reference: value.reference.try_into()?,
145      with: value.config.try_map_into()?,
146      operations: value.operations.try_map_into()?,
147      volumes: value.volumes.try_map_into()?,
148    })
149  }
150}
151
152impl TryFrom<v1::InterfaceBinding> for Binding<config::InterfaceDefinition> {
153  type Error = ManifestError;
154
155  fn try_from(value: v1::InterfaceBinding) -> std::result::Result<Self, Self::Error> {
156    Ok(Self {
157      id: value.name.into(),
158      kind: value.interface.try_into()?,
159    })
160  }
161}
162
163impl TryFrom<v1::InterfaceDefinition> for config::InterfaceDefinition {
164  type Error = ManifestError;
165
166  fn try_from(value: v1::InterfaceDefinition) -> std::result::Result<Self, Self::Error> {
167    Ok(Self {
168      operations: value.operations.try_map_into()?,
169      types: value.types.try_map_into()?,
170    })
171  }
172}
173
174impl TryFrom<v1::CompositeComponentConfiguration> for CompositeComponentImplementation {
175  type Error = ManifestError;
176  fn try_from(value: v1::CompositeComponentConfiguration) -> Result<Self> {
177    Ok(Self {
178      operations: value.operations.try_map_into()?,
179      config: value.with.try_map_into()?,
180      extends: value.extends,
181    })
182  }
183}
184
185impl TryFrom<CompositeComponentImplementation> for v1::CompositeComponentConfiguration {
186  type Error = ManifestError;
187  fn try_from(value: CompositeComponentImplementation) -> Result<Self> {
188    Ok(Self {
189      operations: value.operations.try_map_into()?,
190      with: value.config.try_map_into()?,
191      extends: value.extends,
192    })
193  }
194}
195
196impl TryFrom<WasmRsComponent> for v1::WasmComponentConfiguration {
197  type Error = ManifestError;
198  fn try_from(value: WasmRsComponent) -> Result<Self> {
199    Ok(Self {
200      operations: value.operations.try_map_into()?,
201      reference: value.reference.try_into()?,
202      with: value.config.try_map_into()?,
203      volumes: value.volumes.try_map_into()?,
204      max_packet_size: value.max_packet_size,
205    })
206  }
207}
208
209impl TryFrom<v1::ExposedVolume> for config::ExposedVolume {
210  type Error = ManifestError;
211
212  fn try_from(value: v1::ExposedVolume) -> std::result::Result<Self, Self::Error> {
213    Ok(Self {
214      path: value.path,
215      resource: value.resource.into(),
216    })
217  }
218}
219
220impl TryFrom<config::ExposedVolume> for v1::ExposedVolume {
221  type Error = ManifestError;
222
223  fn try_from(value: config::ExposedVolume) -> std::result::Result<Self, Self::Error> {
224    Ok(Self {
225      path: value.path,
226      resource: value.resource.id().to_owned(),
227    })
228  }
229}
230
231impl TryFrom<Binding<config::InterfaceDefinition>> for v1::InterfaceBinding {
232  type Error = ManifestError;
233
234  fn try_from(value: Binding<config::InterfaceDefinition>) -> std::result::Result<Self, Self::Error> {
235    Ok(Self {
236      name: value.id().to_owned(),
237      interface: value.kind.try_into()?,
238    })
239  }
240}
241
242impl TryFrom<config::InterfaceDefinition> for v1::InterfaceDefinition {
243  type Error = ManifestError;
244
245  fn try_from(value: config::InterfaceDefinition) -> std::result::Result<Self, Self::Error> {
246    Ok(Self {
247      operations: value.operations.try_map_into()?,
248      types: value.types.try_map_into()?,
249    })
250  }
251}
252
253impl TryFrom<v1::ComponentOperationExpression> for ComponentOperationExpression {
254  type Error = ManifestError;
255  fn try_from(literal: v1::ComponentOperationExpression) -> Result<Self> {
256    Ok(Self {
257      name: literal.name,
258      component: literal.component.try_into()?,
259      config: literal.with.map_into(),
260      settings: literal.timeout.map(ExecutionSettings::from_timeout_millis),
261    })
262  }
263}
264
265impl TryFrom<v1::AppConfiguration> for AppConfiguration {
266  type Error = ManifestError;
267
268  fn try_from(def: v1::AppConfiguration) -> Result<Self> {
269    Ok(AppConfiguration {
270      source: None,
271      metadata: def.metadata.try_map_into()?,
272      name: def.name,
273      options: None,
274      import: def.import.try_map_into()?,
275      resources: def.resources.try_map_into()?,
276      triggers: def.triggers.into_iter().map(|v| v.try_into()).collect::<Result<_>>()?,
277      cached_types: Default::default(),
278      type_cache: Default::default(),
279      package: def.package.try_map_into()?,
280      root_config: Default::default(),
281      env: Default::default(),
282    })
283  }
284}
285
286impl TryFrom<AppConfiguration> for v1::AppConfiguration {
287  type Error = ManifestError;
288
289  fn try_from(value: AppConfiguration) -> std::result::Result<Self, Self::Error> {
290    Ok(Self {
291      metadata: value.metadata.try_map_into()?,
292      name: value.name,
293      import: value.import.try_map_into()?,
294      resources: value.resources.try_map_into()?,
295      triggers: value.triggers.try_map_into()?,
296      package: value.package.try_map_into()?,
297    })
298  }
299}
300
301impl TryFrom<ComponentOperationExpression> for v1::ComponentOperationExpression {
302  type Error = ManifestError;
303  fn try_from(value: ComponentOperationExpression) -> Result<Self> {
304    Ok(Self {
305      name: value.name,
306      component: value.component.try_into()?,
307      with: value.config.map_into(),
308      timeout: value.settings.and_then(|t| t.timeout_millis()),
309    })
310  }
311}
312
313impl TryFrom<config::ResourceDefinition> for v1::ResourceDefinition {
314  type Error = ManifestError;
315  fn try_from(value: config::ResourceDefinition) -> Result<Self> {
316    Ok(match value {
317      config::ResourceDefinition::TcpPort(v) => v1::ResourceDefinition::TcpPort(v.try_into()?),
318      config::ResourceDefinition::UdpPort(v) => v1::ResourceDefinition::UdpPort(v.try_into()?),
319      config::ResourceDefinition::Url(v) => v1::ResourceDefinition::Url(v.try_into()?),
320      config::ResourceDefinition::Volume(v) => v1::ResourceDefinition::Volume(v.try_into()?),
321    })
322  }
323}
324
325impl TryFrom<config::UrlResource> for v1::Url {
326  type Error = ManifestError;
327  fn try_from(value: config::UrlResource) -> Result<Self> {
328    Ok(Self { url: value.to_string() })
329  }
330}
331
332impl TryFrom<config::Volume> for v1::Volume {
333  type Error = ManifestError;
334  fn try_from(value: config::Volume) -> Result<Self> {
335    Ok(Self {
336      path: value.unrender()?,
337    })
338  }
339}
340
341impl TryFrom<UdpPort> for v1::UdpPort {
342  type Error = ManifestError;
343  fn try_from(value: UdpPort) -> Result<Self> {
344    Ok(Self {
345      port: value.port.to_string(),
346      address: value.host.to_string(),
347    })
348  }
349}
350
351impl TryFrom<TcpPort> for v1::TcpPort {
352  type Error = ManifestError;
353  fn try_from(value: TcpPort) -> Result<Self> {
354    Ok(Self {
355      port: value.port.unrender()?,
356      address: value.host.unrender()?,
357    })
358  }
359}
360
361impl TryFrom<crate::v1::CompositeOperationDefinition> for config::FlowOperation {
362  type Error = ManifestError;
363
364  fn try_from(op: crate::v1::CompositeOperationDefinition) -> Result<Self> {
365    let instances: Result<HashMap<String, config::InstanceReference>> = op
366      .uses
367      .into_iter()
368      .map(|v| Ok((v.name.clone(), v.try_into()?)))
369      .collect();
370    let expressions: Result<Vec<flow_expression_parser::ast::FlowExpression>> =
371      op.flow.into_iter().map(TryInto::try_into).collect();
372    Ok(Self {
373      name: op.name,
374      inputs: op.inputs.try_map_into()?,
375      outputs: op.outputs.try_map_into()?,
376      instances: instances?,
377      expressions: expressions?,
378      config: op.with.try_map_into()?,
379      flows: op.operations.try_map_into()?,
380    })
381  }
382}
383
384impl TryFrom<v1::ComponentKind> for ComponentImplementation {
385  type Error = ManifestError;
386  fn try_from(value: v1::ComponentKind) -> Result<Self> {
387    Ok(match value {
388      v1::ComponentKind::CompositeComponentConfiguration(v) => ComponentImplementation::Composite(v.try_into()?),
389      v1::ComponentKind::WasmComponentConfiguration(v) => ComponentImplementation::WasmRs(v.try_into()?),
390      v1::ComponentKind::HttpClientComponent(v) => ComponentImplementation::HttpClient(v.try_into()?),
391      v1::ComponentKind::SqlComponent(v) => ComponentImplementation::Sql(v.try_into()?),
392      v1::ComponentKind::WasmComponentModel(v) => ComponentImplementation::Wasm(v.try_into()?),
393    })
394  }
395}
396
397impl TryFrom<ComponentImplementation> for v1::ComponentKind {
398  type Error = ManifestError;
399  fn try_from(value: ComponentImplementation) -> Result<Self> {
400    Ok(match value {
401      ComponentImplementation::Composite(v) => v1::ComponentKind::CompositeComponentConfiguration(v.try_into()?),
402      ComponentImplementation::Wasm(v) => v1::ComponentKind::WasmComponentModel(v.try_into()?),
403      ComponentImplementation::WasmRs(v) => v1::ComponentKind::WasmComponentConfiguration(v.try_into()?),
404      ComponentImplementation::Sql(v) => v1::ComponentKind::SqlComponent(v.try_into()?),
405      ComponentImplementation::HttpClient(v) => v1::ComponentKind::HttpClientComponent(v.try_into()?),
406    })
407  }
408}
409
410impl TryFrom<crate::v1::OperationDefinition> for OperationDefinition {
411  type Error = ManifestError;
412
413  fn try_from(op: crate::v1::OperationDefinition) -> Result<Self> {
414    Ok(Self {
415      name: op.name,
416      config: op.with.try_map_into()?,
417      inputs: op.inputs.try_map_into()?,
418      outputs: op.outputs.try_map_into()?,
419    })
420  }
421}
422
423impl TryFrom<OperationDefinition> for crate::v1::OperationDefinition {
424  type Error = ManifestError;
425
426  fn try_from(op: OperationDefinition) -> Result<Self> {
427    Ok(Self {
428      name: op.name,
429      with: op.config.try_map_into()?,
430      inputs: op.inputs.try_map_into()?,
431      outputs: op.outputs.try_map_into()?,
432    })
433  }
434}
435
436impl TryFrom<Binding<config::ImportDefinition>> for v1::ImportBinding {
437  type Error = ManifestError;
438  fn try_from(def: Binding<config::ImportDefinition>) -> Result<Self> {
439    Ok(Self {
440      name: def.id().to_owned(),
441      component: def.kind.try_into()?,
442    })
443  }
444}
445
446impl TryFrom<config::ImportDefinition> for v1::ImportDefinition {
447  type Error = ManifestError;
448  fn try_from(def: config::ImportDefinition) -> Result<Self> {
449    Ok(match def {
450      crate::config::ImportDefinition::Component(comp) => match comp {
451        ComponentDefinition::Native(_) => unreachable!("Native components are not allowed in imports"),
452        #[allow(deprecated)]
453        ComponentDefinition::Wasm(_) => unreachable!("Wasm components are not allowed in v1 imports"),
454        ComponentDefinition::Reference(_) => unreachable!("Component references can't exist in v1 imports"),
455        ComponentDefinition::GrpcUrl(_) => unreachable!("GrpcUrl components are not allowed in v1 imports"),
456        ComponentDefinition::Manifest(c) => v1::ImportDefinition::ManifestComponent(c.try_into()?),
457        ComponentDefinition::HighLevelComponent(c) => match c {
458          HighLevelComponent::Sql(c) => v1::ImportDefinition::SqlComponent(c.try_into()?),
459          HighLevelComponent::HttpClient(c) => v1::ImportDefinition::HttpClientComponent(c.try_into()?),
460        },
461      },
462      crate::config::ImportDefinition::Types(c) => v1::ImportDefinition::TypesComponent(c.try_into()?),
463    })
464  }
465}
466
467impl TryFrom<Binding<config::ResourceDefinition>> for v1::ResourceBinding {
468  type Error = ManifestError;
469  fn try_from(value: Binding<config::ResourceDefinition>) -> Result<Self> {
470    Ok(Self {
471      name: value.id().to_owned(),
472      resource: value.kind.try_into()?,
473    })
474  }
475}
476
477impl TryFrom<config::components::TypesComponent> for v1::TypesComponent {
478  type Error = ManifestError;
479  fn try_from(value: config::components::TypesComponent) -> Result<Self> {
480    Ok(Self {
481      reference: value.reference.try_into()?,
482      types: value.types,
483    })
484  }
485}
486
487impl TryFrom<ComponentDefinition> for v1::ComponentDefinition {
488  type Error = ManifestError;
489  fn try_from(kind: ComponentDefinition) -> Result<Self> {
490    let def = match kind {
491      #[allow(deprecated)]
492      ComponentDefinition::Wasm(_) => unimplemented!(
493        "Wasm component definition is no longer supported in v1 manifests. Use ManifestComponent instead."
494      ),
495      ComponentDefinition::GrpcUrl(grpc) => Self::GrpcUrlComponent(grpc.into()),
496      ComponentDefinition::Native(_) => todo!(),
497      ComponentDefinition::Reference(v) => Self::ComponentReference(v.into()),
498      ComponentDefinition::Manifest(v) => Self::ManifestComponent(v.try_into()?),
499      ComponentDefinition::HighLevelComponent(v) => match v {
500        config::HighLevelComponent::Sql(v) => Self::SqlComponent(v.try_into()?),
501        config::HighLevelComponent::HttpClient(v) => Self::HttpClientComponent(v.try_into()?),
502      },
503    };
504    Ok(def)
505  }
506}
507
508impl TryFrom<ManifestComponent> for v1::ManifestComponent {
509  type Error = ManifestError;
510  fn try_from(def: ManifestComponent) -> Result<Self> {
511    Ok(Self {
512      reference: def.reference.try_into()?,
513      with: def.config.map_into(),
514      provide: def.provide,
515      max_packet_size: def.max_packet_size,
516    })
517  }
518}
519
520impl From<ComponentReference> for v1::ComponentReference {
521  fn from(value: ComponentReference) -> Self {
522    Self { id: value.id }
523  }
524}
525
526impl From<GrpcUrlComponent> for v1::GrpcUrlComponent {
527  fn from(def: GrpcUrlComponent) -> Self {
528    Self {
529      url: def.url,
530      with: def.config.map_into(),
531    }
532  }
533}
534
535impl TryFrom<config::components::HttpClientComponentConfig> for v1::HttpClientComponent {
536  type Error = ManifestError;
537  fn try_from(value: config::components::HttpClientComponentConfig) -> Result<Self> {
538    Ok(Self {
539      resource: value.resource.id().to_owned(),
540      with: value.config.try_map_into()?,
541      codec: value.codec.map_into(),
542      proxy: value.proxy.try_map_into()?,
543      timeout: value.timeout,
544      operations: value.operations.try_map_into()?,
545    })
546  }
547}
548
549impl TryFrom<config::components::Proxy> for v1::Proxy {
550  type Error = ManifestError;
551  fn try_from(value: config::components::Proxy) -> std::result::Result<Self, Self::Error> {
552    Ok(Self {
553      resource: value.resource.id().to_owned(),
554      username: value.username,
555      password: value.password,
556    })
557  }
558}
559
560impl From<config::common::Codec> for v1::Codec {
561  fn from(value: config::common::Codec) -> Self {
562    match value {
563      config::common::Codec::Json => Self::Json,
564      config::common::Codec::Raw => Self::Raw,
565      config::common::Codec::FormData => Self::FormData,
566      config::common::Codec::Text => Self::Text,
567    }
568  }
569}
570
571impl From<v1::Codec> for config::common::Codec {
572  fn from(value: v1::Codec) -> Self {
573    match value {
574      v1::Codec::Json => Self::Json,
575      v1::Codec::Raw => Self::Raw,
576      v1::Codec::FormData => Self::FormData,
577      v1::Codec::Text => Self::Text,
578    }
579  }
580}
581
582impl TryFrom<config::FlowOperation> for v1::CompositeOperationDefinition {
583  type Error = ManifestError;
584
585  fn try_from(value: config::FlowOperation) -> std::result::Result<Self, Self::Error> {
586    let instances: Vec<v1::OperationInstance> = value
587      .instances
588      .into_iter()
589      .map(|(n, v)| new_operation_instance(n, v))
590      .collect();
591    let connections: Result<Vec<v1::FlowExpression>> = value.expressions.try_map_into();
592    Ok(Self {
593      name: value.name,
594      inputs: value.inputs.try_map_into()?,
595      outputs: value.outputs.try_map_into()?,
596      with: value.config.try_map_into()?,
597      uses: instances,
598      flow: connections?,
599      operations: value.flows.try_map_into()?,
600    })
601  }
602}
603
604fn new_operation_instance(id: String, value: config::InstanceReference) -> v1::OperationInstance {
605  v1::OperationInstance {
606    name: id,
607    operation: v1::ComponentOperationExpression {
608      name: value.name,
609      component: v1::ComponentDefinition::ComponentReference(v1::ComponentReference { id: value.component_id }),
610      with: None,
611      timeout: None,
612    },
613    timeout: value.settings.and_then(|v| v.timeout.map(|v| v.as_millis() as _)),
614    with: value.data.map_into(),
615  }
616}
617
618impl TryFrom<crate::v1::ComponentDefinition> for ComponentDefinition {
619  type Error = ManifestError;
620  fn try_from(def: crate::v1::ComponentDefinition) -> Result<Self> {
621    let res = match def {
622      v1::ComponentDefinition::GrpcUrlComponent(v) => ComponentDefinition::GrpcUrl(GrpcUrlComponent {
623        url: v.url,
624        config: v.with.map_into(),
625      }),
626      v1::ComponentDefinition::ManifestComponent(v) => ComponentDefinition::Manifest(ManifestComponent {
627        reference: v.reference.try_into()?,
628        config: v.with.map_into(),
629        provide: v.provide,
630        max_packet_size: v.max_packet_size,
631      }),
632      v1::ComponentDefinition::ComponentReference(v) => ComponentDefinition::Reference(ComponentReference { id: v.id }),
633      v1::ComponentDefinition::SqlComponent(v) => {
634        ComponentDefinition::HighLevelComponent(HighLevelComponent::Sql(v.try_into()?))
635      }
636      v1::ComponentDefinition::HttpClientComponent(v) => {
637        ComponentDefinition::HighLevelComponent(HighLevelComponent::HttpClient(v.try_into()?))
638      }
639    };
640    Ok(res)
641  }
642}
643
644impl TryFrom<crate::v1::OperationInstance> for config::InstanceReference {
645  type Error = ManifestError;
646  fn try_from(def: crate::v1::OperationInstance) -> Result<Self> {
647    let ns = def.operation.component.component_id().unwrap_or("<anonymous>");
648    let name = def.operation.name;
649    Ok(config::InstanceReference {
650      component_id: ns.to_owned(),
651      name,
652      data: def.with.map_into(),
653      settings: def.timeout.map(ExecutionSettings::from_timeout_millis),
654    })
655  }
656}
657
658impl TryFrom<crate::v1::HostConfig> for HostConfig {
659  type Error = ManifestError;
660  fn try_from(def: crate::v1::HostConfig) -> Result<Self> {
661    Ok(Self {
662      allow_latest: def.allow_latest,
663      insecure_registries: def.insecure_registries,
664      rpc: def.rpc.try_map_into()?,
665    })
666  }
667}
668
669impl TryFrom<HostConfig> for crate::v1::HostConfig {
670  type Error = ManifestError;
671  fn try_from(def: HostConfig) -> Result<Self> {
672    Ok(Self {
673      allow_latest: def.allow_latest,
674      insecure_registries: def.insecure_registries,
675      rpc: def.rpc.try_map_into()?,
676    })
677  }
678}
679
680impl TryFrom<crate::v1::HttpConfig> for config::HttpConfig {
681  type Error = ManifestError;
682  fn try_from(def: crate::v1::HttpConfig) -> Result<Self> {
683    Ok(Self {
684      enabled: def.enabled,
685      port: def.port,
686      address: opt_str_to_ipv4addr(&def.address)?,
687      pem: match def.pem {
688        Some(v) => Some(v.try_into()?),
689        None => None,
690      },
691      key: match def.key {
692        Some(v) => Some(v.try_into()?),
693        None => None,
694      },
695      ca: match def.ca {
696        Some(v) => Some(v.try_into()?),
697        None => None,
698      },
699    })
700  }
701}
702
703impl TryFrom<config::HttpConfig> for crate::v1::HttpConfig {
704  type Error = ManifestError;
705  fn try_from(def: config::HttpConfig) -> Result<Self> {
706    Ok(Self {
707      enabled: def.enabled,
708      port: def.port,
709      address: def.address.map(|v| v.to_string()),
710      pem: def.pem.try_map_into()?,
711      key: def.key.try_map_into()?,
712      ca: def.ca.try_map_into()?,
713    })
714  }
715}
716
717impl TryFrom<v1::ResourceDefinition> for config::ResourceDefinition {
718  type Error = ManifestError;
719  fn try_from(value: v1::ResourceDefinition) -> Result<Self> {
720    Ok(match value {
721      v1::ResourceDefinition::TcpPort(v) => Self::TcpPort(v.into()),
722      v1::ResourceDefinition::UdpPort(v) => Self::UdpPort(v.into()),
723      v1::ResourceDefinition::Url(v) => Self::Url(v.into()),
724      v1::ResourceDefinition::Volume(v) => Self::Volume(v.into()),
725    })
726  }
727}
728
729impl From<v1::Volume> for config::Volume {
730  fn from(value: v1::Volume) -> Self {
731    config::Volume::new(value.path)
732  }
733}
734
735impl From<v1::Url> for config::UrlResource {
736  fn from(value: v1::Url) -> Self {
737    Self {
738      url: TemplateConfig::new_template(value.url),
739    }
740  }
741}
742
743impl From<v1::TcpPort> for TcpPort {
744  fn from(value: v1::TcpPort) -> Self {
745    Self {
746      port: TemplateConfig::new_template(value.port),
747      host: TemplateConfig::new_template(value.address),
748    }
749  }
750}
751
752impl From<v1::UdpPort> for UdpPort {
753  fn from(value: v1::UdpPort) -> Self {
754    Self {
755      port: TemplateConfig::new_template(value.port),
756      host: TemplateConfig::new_template(value.address),
757    }
758  }
759}
760
761impl TryFrom<v1::TriggerDefinition> for TriggerDefinition {
762  type Error = ManifestError;
763  fn try_from(trigger: v1::TriggerDefinition) -> Result<Self> {
764    let rv = match trigger {
765      v1::TriggerDefinition::CliTrigger(cli) => Self::Cli(CliConfig {
766        operation: cli.operation.try_into()?,
767      }),
768      v1::TriggerDefinition::HttpTrigger(v) => Self::Http(HttpTriggerConfig {
769        resource: v.resource.into(),
770        routers: v.routers.try_map_into()?,
771      }),
772      v1::TriggerDefinition::TimeTrigger(time) => Self::Time(TimeTriggerConfig {
773        schedule: time.schedule.try_into()?,
774        operation: time.operation.try_into()?,
775        payload: time.payload.try_map_into()?,
776      }),
777      v1::TriggerDefinition::WasmCommandTrigger(v) => Self::WasmCommand(WasmCommandConfig {
778        reference: v.reference.try_into()?,
779        volumes: v.volumes.try_map_into()?,
780      }),
781    };
782    Ok(rv)
783  }
784}
785
786impl TryFrom<v1::HttpRouter> for HttpRouterConfig {
787  type Error = ManifestError;
788  fn try_from(router: v1::HttpRouter) -> Result<Self> {
789    let rv = match router {
790      v1::HttpRouter::RawRouter(v) => Self::RawRouter(RawRouterConfig {
791        path: v.path,
792        codec: v.codec.map_into(),
793        operation: v.operation.try_into()?,
794        middleware: v.middleware.try_map_into()?,
795      }),
796      v1::HttpRouter::RestRouter(v) => Self::RestRouter(RestRouterConfig {
797        path: v.path,
798        tools: v.tools.try_map_into()?,
799        routes: v.routes.try_map_into()?,
800        info: v.info.try_map_into()?,
801        middleware: v.middleware.try_map_into()?,
802      }),
803      v1::HttpRouter::StaticRouter(v) => Self::StaticRouter(StaticRouterConfig {
804        path: v.path,
805        volume: v.volume.into(),
806        fallback: v.fallback,
807        middleware: v.middleware.try_map_into()?,
808        indexes: v.indexes,
809      }),
810      v1::HttpRouter::ProxyRouter(v) => Self::ProxyRouter(ProxyRouterConfig {
811        path: v.path,
812        url: v.url.into(),
813        strip_path: v.strip_path,
814        middleware: v.middleware.try_map_into()?,
815      }),
816    };
817    Ok(rv)
818  }
819}
820
821impl TryFrom<v1::ImportBinding> for Binding<config::ImportDefinition> {
822  type Error = ManifestError;
823  fn try_from(value: v1::ImportBinding) -> Result<Self> {
824    Ok(Self {
825      id: value.name.into(),
826      kind: value.component.try_into()?,
827    })
828  }
829}
830
831impl TryFrom<v1::ImportDefinition> for config::ImportDefinition {
832  type Error = ManifestError;
833  fn try_from(value: v1::ImportDefinition) -> Result<Self> {
834    Ok(match value {
835      v1::ImportDefinition::TypesComponent(c) => config::ImportDefinition::Types(c.try_into()?),
836      v1::ImportDefinition::ManifestComponent(c) => {
837        let c = v1::ComponentDefinition::ManifestComponent(c);
838        config::ImportDefinition::Component(c.try_into()?)
839      }
840      v1::ImportDefinition::SqlComponent(c) => config::ImportDefinition::Component(
841        config::ComponentDefinition::HighLevelComponent(config::HighLevelComponent::Sql(c.try_into()?)),
842      ),
843      v1::ImportDefinition::HttpClientComponent(c) => config::ImportDefinition::Component(
844        config::ComponentDefinition::HighLevelComponent(config::HighLevelComponent::HttpClient(c.try_into()?)),
845      ),
846    })
847  }
848}
849
850impl TryFrom<v1::TypesComponent> for config::components::TypesComponent {
851  type Error = ManifestError;
852
853  fn try_from(value: v1::TypesComponent) -> std::result::Result<Self, Self::Error> {
854    Ok(Self {
855      reference: value.reference.try_into()?,
856      types: value.types,
857    })
858  }
859}
860
861impl TryFrom<v1::ResourceBinding> for Binding<config::ResourceDefinition> {
862  type Error = ManifestError;
863  fn try_from(value: v1::ResourceBinding) -> Result<Self> {
864    Ok(Self {
865      id: value.name.into(),
866      kind: value.resource.try_into()?,
867    })
868  }
869}
870
871impl TryFrom<v1::helpers::LocationReference> for AssetReference {
872  type Error = crate::Error;
873  fn try_from(value: v1::helpers::LocationReference) -> Result<Self> {
874    Ok(value.0.try_into()?)
875  }
876}
877
878impl TryFrom<AssetReference> for v1::helpers::LocationReference {
879  type Error = crate::Error;
880  fn try_from(value: AssetReference) -> Result<Self> {
881    Ok(Self(value.location().to_owned()))
882  }
883}
884
885impl TryFrom<v1::Metadata> for config::Metadata {
886  type Error = crate::Error;
887  fn try_from(value: v1::Metadata) -> Result<Self> {
888    Ok(Self {
889      version: value.version,
890      authors: value.authors,
891      vendors: value.vendors,
892      description: value.description,
893      documentation: value.documentation,
894      licenses: value.licenses,
895      icon: value.icon.try_map_into()?,
896    })
897  }
898}
899
900impl TryFrom<config::Metadata> for v1::Metadata {
901  type Error = crate::Error;
902  fn try_from(value: config::Metadata) -> Result<Self> {
903    Ok(Self {
904      version: value.version,
905      authors: value.authors,
906      vendors: value.vendors,
907      description: value.description,
908      documentation: value.documentation,
909      licenses: value.licenses,
910      icon: value.icon.try_map_into()?,
911    })
912  }
913}
914
915impl TryFrom<v1::SqlComponent> for components::SqlComponentConfig {
916  type Error = crate::Error;
917  fn try_from(value: v1::SqlComponent) -> Result<Self> {
918    Ok(Self {
919      resource: value.resource.into(),
920      tls: value.tls,
921      config: value.with.try_map_into()?,
922      operations: value
923        .operations
924        .into_iter()
925        .map(TryInto::try_into)
926        .collect::<Result<_>>()?,
927    })
928  }
929}
930
931impl TryFrom<v1::SqlQueryKind> for components::SqlOperationDefinition {
932  type Error = crate::Error;
933  fn try_from(value: v1::SqlQueryKind) -> Result<Self> {
934    Ok(match value {
935      v1::SqlQueryKind::SqlQueryOperationDefinition(v) => Self::Query(v.try_into()?),
936      v1::SqlQueryKind::SqlExecOperationDefinition(v) => Self::Exec(v.try_into()?),
937    })
938  }
939}
940
941impl TryFrom<v1::SqlQueryOperationDefinition> for components::SqlQueryOperationDefinition {
942  type Error = crate::Error;
943  fn try_from(value: v1::SqlQueryOperationDefinition) -> Result<Self> {
944    Ok(Self {
945      name: value.name,
946      inputs: value.inputs.try_map_into()?,
947      outputs: value.outputs.try_map_into()?,
948      query: value.query,
949      arguments: value.arguments,
950      config: value.with.try_map_into()?,
951      on_error: value.on_error.unwrap_or_default().try_into()?,
952    })
953  }
954}
955
956impl TryFrom<v1::SqlExecOperationDefinition> for components::SqlExecOperationDefinition {
957  type Error = crate::Error;
958  fn try_from(value: v1::SqlExecOperationDefinition) -> Result<Self> {
959    Ok(Self {
960      name: value.name,
961      inputs: value.inputs.try_map_into()?,
962      outputs: value.outputs.try_map_into()?,
963      exec: value.exec,
964      arguments: value.arguments,
965      config: value.with.try_map_into()?,
966      on_error: value.on_error.unwrap_or_default().try_into()?,
967    })
968  }
969}
970
971impl TryFrom<v1::HttpClientOperationDefinition> for components::HttpClientOperationDefinition {
972  type Error = crate::Error;
973  fn try_from(value: v1::HttpClientOperationDefinition) -> Result<Self> {
974    Ok(Self {
975      name: value.name,
976      codec: value.codec.map_into(),
977      inputs: value.inputs.try_map_into()?,
978      path: value.path,
979      body: value.body,
980      method: value.method.into(),
981      config: value.with.try_map_into()?,
982      headers: value.headers,
983    })
984  }
985}
986
987impl From<v1::HttpMethod> for config::HttpMethod {
988  fn from(value: v1::HttpMethod) -> Self {
989    match value {
990      v1::HttpMethod::Get => Self::Get,
991      v1::HttpMethod::Post => Self::Post,
992      v1::HttpMethod::Put => Self::Put,
993      v1::HttpMethod::Delete => Self::Delete,
994    }
995  }
996}
997
998impl From<config::HttpMethod> for v1::HttpMethod {
999  fn from(value: config::HttpMethod) -> Self {
1000    match value {
1001      config::HttpMethod::Get => Self::Get,
1002      config::HttpMethod::Post => Self::Post,
1003      config::HttpMethod::Put => Self::Put,
1004      config::HttpMethod::Delete => Self::Delete,
1005    }
1006  }
1007}
1008
1009impl TryFrom<v1::HttpClientComponent> for components::HttpClientComponentConfig {
1010  type Error = crate::Error;
1011  fn try_from(value: v1::HttpClientComponent) -> Result<Self> {
1012    Ok(Self {
1013      resource: value.resource.into(),
1014      config: value.with.try_map_into()?,
1015      codec: value.codec.map_into(),
1016      proxy: value.proxy.try_map_into()?,
1017      timeout: value.timeout,
1018      operations: value.operations.try_map_into()?,
1019    })
1020  }
1021}
1022
1023impl TryFrom<v1::Proxy> for components::Proxy {
1024  type Error = crate::Error;
1025  fn try_from(value: v1::Proxy) -> Result<Self> {
1026    Ok(Self {
1027      resource: value.resource.into(),
1028      username: value.username,
1029      password: value.password,
1030    })
1031  }
1032}
1033
1034impl TryFrom<components::SqlComponentConfig> for v1::SqlComponent {
1035  type Error = crate::Error;
1036  fn try_from(value: components::SqlComponentConfig) -> Result<Self> {
1037    Ok(Self {
1038      resource: value.resource.id().to_owned(),
1039      with: value.config.try_map_into()?,
1040      tls: value.tls,
1041      operations: value.operations.try_map_into()?,
1042    })
1043  }
1044}
1045
1046impl TryFrom<components::SqlOperationDefinition> for v1::SqlQueryKind {
1047  type Error = crate::Error;
1048
1049  fn try_from(value: components::SqlOperationDefinition) -> std::result::Result<Self, Self::Error> {
1050    Ok(match value {
1051      components::SqlOperationDefinition::Query(v) => Self::SqlQueryOperationDefinition(v.try_into()?),
1052      components::SqlOperationDefinition::Exec(v) => Self::SqlExecOperationDefinition(v.try_into()?),
1053    })
1054  }
1055}
1056
1057impl TryFrom<components::SqlQueryOperationDefinition> for v1::SqlQueryOperationDefinition {
1058  type Error = crate::Error;
1059  fn try_from(value: components::SqlQueryOperationDefinition) -> Result<Self> {
1060    Ok(Self {
1061      name: value.name,
1062      inputs: value.inputs.try_map_into()?,
1063      outputs: value.outputs.try_map_into()?,
1064      query: value.query,
1065      arguments: value.arguments,
1066      on_error: Some(value.on_error.try_into()?),
1067      with: value.config.try_map_into()?,
1068    })
1069  }
1070}
1071
1072impl TryFrom<components::SqlExecOperationDefinition> for v1::SqlExecOperationDefinition {
1073  type Error = crate::Error;
1074  fn try_from(value: components::SqlExecOperationDefinition) -> Result<Self> {
1075    Ok(Self {
1076      name: value.name,
1077      inputs: value.inputs.try_map_into()?,
1078      outputs: value.outputs.try_map_into()?,
1079      exec: value.exec,
1080      arguments: value.arguments,
1081      on_error: Some(value.on_error.try_into()?),
1082      with: value.config.try_map_into()?,
1083    })
1084  }
1085}
1086
1087impl TryFrom<config::ErrorBehavior> for v1::ErrorBehavior {
1088  type Error = crate::Error;
1089  fn try_from(value: config::ErrorBehavior) -> Result<Self> {
1090    Ok(match value {
1091      config::ErrorBehavior::Commit => Self::Commit,
1092      config::ErrorBehavior::Ignore => Self::Ignore,
1093      config::ErrorBehavior::Rollback => Self::Rollback,
1094    })
1095  }
1096}
1097
1098impl TryFrom<v1::ErrorBehavior> for config::ErrorBehavior {
1099  type Error = crate::Error;
1100  fn try_from(value: v1::ErrorBehavior) -> Result<Self> {
1101    Ok(match value {
1102      v1::ErrorBehavior::Commit => Self::Commit,
1103      v1::ErrorBehavior::Ignore => Self::Ignore,
1104      v1::ErrorBehavior::Rollback => Self::Rollback,
1105    })
1106  }
1107}
1108
1109impl TryFrom<components::HttpClientOperationDefinition> for v1::HttpClientOperationDefinition {
1110  type Error = crate::Error;
1111  fn try_from(value: components::HttpClientOperationDefinition) -> Result<Self> {
1112    Ok(Self {
1113      name: value.name,
1114      inputs: value.inputs.try_map_into()?,
1115      path: value.path,
1116      body: value.body,
1117      codec: value.codec.map_into(),
1118      method: value.method.into(),
1119      with: value.config.try_map_into()?,
1120      headers: value.headers,
1121    })
1122  }
1123}