Skip to main content

spin_factor_outbound_http/
wasi_2026_03_15.rs

1use spin_factor_wasi::{FutureReaderExt as _, convert, convert_result, reborrow};
2use wasmtime::AsContextMut;
3use wasmtime::component::{Access, Accessor, FutureReader, Linker, Resource, StreamReader};
4use wasmtime_wasi_http::p3::bindings as latest;
5use wasmtime_wasi_http::{WasiHttp, WasiHttpCtxView};
6
7mod bindings {
8    use super::latest;
9
10    wasmtime::component::bindgen!({
11        path: "../../wit",
12        world: "wasi:http/service@0.3.0-rc-2026-03-15",
13        imports: {
14            "wasi:http/client.send": store | trappable,
15            "wasi:http/types.[drop]request": store | trappable,
16            "wasi:http/types.[drop]response": store | trappable,
17            "wasi:http/types.[static]request.consume-body": store | trappable,
18            "wasi:http/types.[static]request.new": store | trappable,
19            "wasi:http/types.[static]response.consume-body": store | trappable,
20            "wasi:http/types.[static]response.new": store | trappable,
21            default: trappable,
22        },
23        exports: { default: async | store },
24        with: {
25            "wasi:http/types.fields": latest::http::types::Fields,
26            "wasi:http/types.request": latest::http::types::Request,
27            "wasi:http/types.request-options": latest::http::types::RequestOptions,
28            "wasi:http/types.response": latest::http::types::Response,
29        },
30    });
31}
32
33pub use bindings::{Service, ServiceIndices};
34
35mod wasi {
36    pub use super::bindings::wasi::http0_3_0_rc_2026_03_15 as http;
37}
38
39pub(crate) fn add_to_linker<T>(
40    linker: &mut Linker<T>,
41    closure: fn(&mut T) -> WasiHttpCtxView<'_>,
42) -> anyhow::Result<()>
43where
44    T: Send + 'static,
45{
46    wasi::http::types::add_to_linker::<_, WasiHttp>(linker, closure)?;
47    wasi::http::client::add_to_linker::<_, WasiHttp>(linker, closure)?;
48    Ok(())
49}
50
51impl wasi::http::types::Host for WasiHttpCtxView<'_> {}
52
53impl wasi::http::types::HostResponse for WasiHttpCtxView<'_> {
54    fn get_status_code(
55        &mut self,
56        res: Resource<wasi::http::types::Response>,
57    ) -> wasmtime::Result<wasi::http::types::StatusCode> {
58        latest::http::types::HostResponse::get_status_code(self, res)
59    }
60
61    fn set_status_code(
62        &mut self,
63        res: Resource<wasi::http::types::Response>,
64        status_code: wasi::http::types::StatusCode,
65    ) -> wasmtime::Result<Result<(), ()>> {
66        latest::http::types::HostResponse::set_status_code(self, res, status_code)
67    }
68
69    fn get_headers(
70        &mut self,
71        res: Resource<wasi::http::types::Response>,
72    ) -> wasmtime::Result<Resource<wasi::http::types::Headers>> {
73        latest::http::types::HostResponse::get_headers(self, res)
74    }
75}
76
77impl wasi::http::types::HostRequestOptions for WasiHttpCtxView<'_> {
78    fn new(&mut self) -> wasmtime::Result<Resource<wasi::http::types::RequestOptions>> {
79        latest::http::types::HostRequestOptions::new(self)
80    }
81
82    fn get_connect_timeout(
83        &mut self,
84        opts: Resource<wasi::http::types::RequestOptions>,
85    ) -> wasmtime::Result<Option<wasi::http::types::Duration>> {
86        latest::http::types::HostRequestOptions::get_connect_timeout(self, opts)
87    }
88
89    fn set_connect_timeout(
90        &mut self,
91        opts: Resource<wasi::http::types::RequestOptions>,
92        duration: Option<wasi::http::types::Duration>,
93    ) -> wasmtime::Result<Result<(), wasi::http::types::RequestOptionsError>> {
94        convert_result(
95            latest::http::types::HostRequestOptions::set_connect_timeout(self, opts, duration),
96        )
97    }
98
99    fn get_first_byte_timeout(
100        &mut self,
101        opts: Resource<wasi::http::types::RequestOptions>,
102    ) -> wasmtime::Result<Option<wasi::http::types::Duration>> {
103        latest::http::types::HostRequestOptions::get_first_byte_timeout(self, opts)
104    }
105
106    fn set_first_byte_timeout(
107        &mut self,
108        opts: Resource<wasi::http::types::RequestOptions>,
109        duration: Option<wasi::http::types::Duration>,
110    ) -> wasmtime::Result<Result<(), wasi::http::types::RequestOptionsError>> {
111        convert_result(
112            latest::http::types::HostRequestOptions::set_first_byte_timeout(self, opts, duration),
113        )
114    }
115
116    fn get_between_bytes_timeout(
117        &mut self,
118        opts: Resource<wasi::http::types::RequestOptions>,
119    ) -> wasmtime::Result<Option<wasi::http::types::Duration>> {
120        latest::http::types::HostRequestOptions::get_between_bytes_timeout(self, opts)
121    }
122
123    fn set_between_bytes_timeout(
124        &mut self,
125        opts: Resource<wasi::http::types::RequestOptions>,
126        duration: Option<wasi::http::types::Duration>,
127    ) -> wasmtime::Result<Result<(), wasi::http::types::RequestOptionsError>> {
128        convert_result(
129            latest::http::types::HostRequestOptions::set_between_bytes_timeout(
130                self, opts, duration,
131            ),
132        )
133    }
134
135    fn clone(
136        &mut self,
137        opts: Resource<wasi::http::types::RequestOptions>,
138    ) -> wasmtime::Result<Resource<wasi::http::types::RequestOptions>> {
139        latest::http::types::HostRequestOptions::clone(self, opts)
140    }
141
142    fn drop(&mut self, opts: Resource<wasi::http::types::RequestOptions>) -> wasmtime::Result<()> {
143        latest::http::types::HostRequestOptions::drop(self, opts)
144    }
145}
146
147impl<T> wasi::http::types::HostRequestWithStore<T> for WasiHttp {
148    fn new(
149        mut store: Access<T, Self>,
150        headers: Resource<wasi::http::types::Headers>,
151        contents: Option<StreamReader<u8>>,
152        trailers: FutureReader<
153            Result<Option<Resource<wasi::http::types::Trailers>>, wasi::http::types::ErrorCode>,
154        >,
155        options: Option<Resource<wasi::http::types::RequestOptions>>,
156    ) -> wasmtime::Result<(
157        Resource<wasi::http::types::Request>,
158        FutureReader<Result<(), wasi::http::types::ErrorCode>>,
159    )> {
160        let trailers = trailers.try_map(store.as_context_mut(), |v| v.map_err(|v| v.into()))?;
161        latest::http::types::HostRequestWithStore::new(
162            reborrow(&mut store),
163            headers,
164            contents,
165            trailers,
166            options,
167        )
168        .and_then(|(req, future)| Ok((req, future.try_map(store, |v| v.map_err(|v| v.into()))?)))
169    }
170
171    fn consume_body(
172        mut store: Access<T, Self>,
173        req: Resource<wasi::http::types::Request>,
174        fut: FutureReader<Result<(), wasi::http::types::ErrorCode>>,
175    ) -> wasmtime::Result<(
176        StreamReader<u8>,
177        FutureReader<
178            Result<Option<Resource<wasi::http::types::Trailers>>, wasi::http::types::ErrorCode>,
179        >,
180    )> {
181        let fut = fut.try_map(store.as_context_mut(), |v| v.map_err(|v| v.into()))?;
182        latest::http::types::HostRequestWithStore::consume_body(reborrow(&mut store), req, fut)
183            .and_then(|(stream, future)| {
184                Ok((stream, future.try_map(store, |v| v.map_err(|v| v.into()))?))
185            })
186    }
187
188    fn drop(
189        store: Access<'_, T, Self>,
190        req: Resource<wasi::http::types::Request>,
191    ) -> wasmtime::Result<()> {
192        latest::http::types::HostRequestWithStore::drop(store, req)
193    }
194}
195
196impl wasi::http::types::HostRequest for WasiHttpCtxView<'_> {
197    fn get_method(
198        &mut self,
199        req: Resource<wasi::http::types::Request>,
200    ) -> wasmtime::Result<wasi::http::types::Method> {
201        latest::http::types::HostRequest::get_method(self, req).map(|v| v.into())
202    }
203
204    fn set_method(
205        &mut self,
206        req: Resource<wasi::http::types::Request>,
207        method: wasi::http::types::Method,
208    ) -> wasmtime::Result<Result<(), ()>> {
209        latest::http::types::HostRequest::set_method(self, req, method.into())
210    }
211
212    fn get_path_with_query(
213        &mut self,
214        req: Resource<wasi::http::types::Request>,
215    ) -> wasmtime::Result<Option<String>> {
216        latest::http::types::HostRequest::get_path_with_query(self, req)
217    }
218
219    fn set_path_with_query(
220        &mut self,
221        req: Resource<wasi::http::types::Request>,
222        path_with_query: Option<String>,
223    ) -> wasmtime::Result<Result<(), ()>> {
224        latest::http::types::HostRequest::set_path_with_query(self, req, path_with_query)
225    }
226
227    fn get_scheme(
228        &mut self,
229        req: Resource<wasi::http::types::Request>,
230    ) -> wasmtime::Result<Option<wasi::http::types::Scheme>> {
231        latest::http::types::HostRequest::get_scheme(self, req).map(|v| v.map(|v| v.into()))
232    }
233
234    fn set_scheme(
235        &mut self,
236        req: Resource<wasi::http::types::Request>,
237        scheme: Option<wasi::http::types::Scheme>,
238    ) -> wasmtime::Result<Result<(), ()>> {
239        latest::http::types::HostRequest::set_scheme(self, req, scheme.map(|v| v.into()))
240    }
241
242    fn get_authority(
243        &mut self,
244        req: Resource<wasi::http::types::Request>,
245    ) -> wasmtime::Result<Option<String>> {
246        latest::http::types::HostRequest::get_authority(self, req)
247    }
248
249    fn set_authority(
250        &mut self,
251        req: Resource<wasi::http::types::Request>,
252        authority: Option<String>,
253    ) -> wasmtime::Result<Result<(), ()>> {
254        latest::http::types::HostRequest::set_authority(self, req, authority)
255    }
256
257    fn get_options(
258        &mut self,
259        req: Resource<wasi::http::types::Request>,
260    ) -> wasmtime::Result<Option<Resource<wasi::http::types::RequestOptions>>> {
261        latest::http::types::HostRequest::get_options(self, req)
262    }
263
264    fn get_headers(
265        &mut self,
266        req: Resource<wasi::http::types::Request>,
267    ) -> wasmtime::Result<Resource<wasi::http::types::Headers>> {
268        latest::http::types::HostRequest::get_headers(self, req)
269    }
270}
271
272impl wasi::http::types::HostFields for WasiHttpCtxView<'_> {
273    fn new(&mut self) -> wasmtime::Result<Resource<wasi::http::types::Fields>> {
274        latest::http::types::HostFields::new(self)
275    }
276
277    fn from_list(
278        &mut self,
279        entries: Vec<(wasi::http::types::FieldName, wasi::http::types::FieldValue)>,
280    ) -> wasmtime::Result<Result<Resource<wasi::http::types::Fields>, wasi::http::types::HeaderError>>
281    {
282        convert_result(latest::http::types::HostFields::from_list(self, entries))
283    }
284
285    fn get(
286        &mut self,
287        fields: Resource<wasi::http::types::Fields>,
288        name: wasi::http::types::FieldName,
289    ) -> wasmtime::Result<Vec<wasi::http::types::FieldValue>> {
290        latest::http::types::HostFields::get(self, fields, name)
291    }
292
293    fn has(
294        &mut self,
295        fields: Resource<wasi::http::types::Fields>,
296        name: wasi::http::types::FieldName,
297    ) -> wasmtime::Result<bool> {
298        latest::http::types::HostFields::has(self, fields, name)
299    }
300
301    fn set(
302        &mut self,
303        fields: Resource<wasi::http::types::Fields>,
304        name: wasi::http::types::FieldName,
305        value: Vec<wasi::http::types::FieldValue>,
306    ) -> wasmtime::Result<Result<(), wasi::http::types::HeaderError>> {
307        convert_result(latest::http::types::HostFields::set(
308            self, fields, name, value,
309        ))
310    }
311
312    fn delete(
313        &mut self,
314        fields: Resource<wasi::http::types::Fields>,
315        name: wasi::http::types::FieldName,
316    ) -> wasmtime::Result<Result<(), wasi::http::types::HeaderError>> {
317        convert_result(latest::http::types::HostFields::delete(self, fields, name))
318    }
319
320    fn get_and_delete(
321        &mut self,
322        fields: Resource<wasi::http::types::Fields>,
323        name: wasi::http::types::FieldName,
324    ) -> wasmtime::Result<Result<Vec<wasi::http::types::FieldValue>, wasi::http::types::HeaderError>>
325    {
326        convert_result(latest::http::types::HostFields::get_and_delete(
327            self, fields, name,
328        ))
329    }
330
331    fn append(
332        &mut self,
333        fields: Resource<wasi::http::types::Fields>,
334        name: wasi::http::types::FieldName,
335        value: wasi::http::types::FieldValue,
336    ) -> wasmtime::Result<Result<(), wasi::http::types::HeaderError>> {
337        convert_result(latest::http::types::HostFields::append(
338            self, fields, name, value,
339        ))
340    }
341
342    fn copy_all(
343        &mut self,
344        fields: Resource<wasi::http::types::Fields>,
345    ) -> wasmtime::Result<Vec<(wasi::http::types::FieldName, wasi::http::types::FieldValue)>> {
346        latest::http::types::HostFields::copy_all(self, fields)
347    }
348
349    fn clone(
350        &mut self,
351        fields: Resource<wasi::http::types::Fields>,
352    ) -> wasmtime::Result<Resource<wasi::http::types::Fields>> {
353        latest::http::types::HostFields::clone(self, fields)
354    }
355
356    fn drop(&mut self, fields: Resource<wasi::http::types::Fields>) -> wasmtime::Result<()> {
357        latest::http::types::HostFields::drop(self, fields)
358    }
359}
360
361impl<T> wasi::http::types::HostResponseWithStore<T> for WasiHttp {
362    fn new(
363        mut store: Access<T, Self>,
364        headers: Resource<wasi::http::types::Headers>,
365        contents: Option<StreamReader<u8>>,
366        trailers: FutureReader<
367            Result<Option<Resource<wasi::http::types::Trailers>>, wasi::http::types::ErrorCode>,
368        >,
369    ) -> wasmtime::Result<(
370        Resource<wasi::http::types::Response>,
371        FutureReader<Result<(), wasi::http::types::ErrorCode>>,
372    )> {
373        let trailers = trailers.try_map(store.as_context_mut(), |v| v.map_err(|v| v.into()))?;
374        latest::http::types::HostResponseWithStore::new(
375            reborrow(&mut store),
376            headers,
377            contents,
378            trailers,
379        )
380        .and_then(|(res, future)| Ok((res, future.try_map(store, |v| v.map_err(|v| v.into()))?)))
381    }
382
383    fn consume_body(
384        mut store: Access<T, Self>,
385        res: Resource<wasi::http::types::Response>,
386        fut: FutureReader<Result<(), wasi::http::types::ErrorCode>>,
387    ) -> wasmtime::Result<(
388        StreamReader<u8>,
389        FutureReader<
390            Result<Option<Resource<wasi::http::types::Trailers>>, wasi::http::types::ErrorCode>,
391        >,
392    )> {
393        let fut = fut.try_map(store.as_context_mut(), |v| v.map_err(|v| v.into()))?;
394        latest::http::types::HostResponseWithStore::consume_body(reborrow(&mut store), res, fut)
395            .and_then(|(stream, future)| {
396                Ok((stream, future.try_map(store, |v| v.map_err(|v| v.into()))?))
397            })
398    }
399
400    fn drop(
401        store: Access<'_, T, Self>,
402        res: Resource<wasi::http::types::Response>,
403    ) -> wasmtime::Result<()> {
404        latest::http::types::HostResponseWithStore::drop(store, res)
405    }
406}
407
408impl<T> wasi::http::client::HostWithStore<T> for WasiHttp {
409    async fn send(
410        store: &Accessor<T, Self>,
411        req: Resource<wasi::http::types::Request>,
412    ) -> wasmtime::Result<Result<Resource<wasi::http::types::Response>, wasi::http::types::ErrorCode>>
413    {
414        convert_result(latest::http::client::HostWithStore::send(store, req).await)
415    }
416}
417
418impl wasi::http::client::Host for WasiHttpCtxView<'_> {}
419
420convert! {
421    struct latest::http::types::DnsErrorPayload [<=>] wasi::http::types::DnsErrorPayload {
422        rcode,
423        info_code,
424    }
425
426    struct latest::http::types::TlsAlertReceivedPayload [<=>] wasi::http::types::TlsAlertReceivedPayload {
427        alert_id,
428        alert_message,
429    }
430
431    struct latest::http::types::FieldSizePayload [<=>] wasi::http::types::FieldSizePayload {
432        field_name,
433        field_size,
434    }
435
436    enum latest::http::types::RequestOptionsError => wasi::http::types::RequestOptionsError {
437        NotSupported,
438        Immutable,
439        Other(v),
440    }
441
442    enum latest::http::types::Method [<=>] wasi::http::types::Method {
443        Get,
444        Head,
445        Post,
446        Put,
447        Delete,
448        Connect,
449        Options,
450        Trace,
451        Patch,
452        Other(v),
453    }
454
455    enum latest::http::types::Scheme [<=>] wasi::http::types::Scheme {
456        Http,
457        Https,
458        Other(v),
459    }
460
461    enum latest::http::types::HeaderError [<=>] wasi::http::types::HeaderError {
462        InvalidSyntax,
463        Forbidden,
464        Immutable,
465        SizeExceeded,
466        Other(v),
467    }
468}
469
470impl From<wasi::http::types::ErrorCode> for latest::http::types::ErrorCode {
471    fn from(e: wasi::http::types::ErrorCode) -> Self {
472        match e {
473            wasi::http::types::ErrorCode::DnsTimeout => latest::http::types::ErrorCode::DnsTimeout,
474            wasi::http::types::ErrorCode::DnsError(e) => {
475                latest::http::types::ErrorCode::DnsError(e.into())
476            }
477            wasi::http::types::ErrorCode::DestinationNotFound => {
478                latest::http::types::ErrorCode::DestinationNotFound
479            }
480            wasi::http::types::ErrorCode::DestinationUnavailable => {
481                latest::http::types::ErrorCode::DestinationUnavailable
482            }
483            wasi::http::types::ErrorCode::DestinationIpProhibited => {
484                latest::http::types::ErrorCode::DestinationIpProhibited
485            }
486            wasi::http::types::ErrorCode::DestinationIpUnroutable => {
487                latest::http::types::ErrorCode::DestinationIpUnroutable
488            }
489            wasi::http::types::ErrorCode::ConnectionRefused => {
490                latest::http::types::ErrorCode::ConnectionRefused
491            }
492            wasi::http::types::ErrorCode::ConnectionTerminated => {
493                latest::http::types::ErrorCode::ConnectionTerminated
494            }
495            wasi::http::types::ErrorCode::ConnectionTimeout => {
496                latest::http::types::ErrorCode::ConnectionTimeout
497            }
498            wasi::http::types::ErrorCode::ConnectionReadTimeout => {
499                latest::http::types::ErrorCode::ConnectionReadTimeout
500            }
501            wasi::http::types::ErrorCode::ConnectionWriteTimeout => {
502                latest::http::types::ErrorCode::ConnectionWriteTimeout
503            }
504            wasi::http::types::ErrorCode::ConnectionLimitReached => {
505                latest::http::types::ErrorCode::ConnectionLimitReached
506            }
507            wasi::http::types::ErrorCode::TlsProtocolError => {
508                latest::http::types::ErrorCode::TlsProtocolError
509            }
510            wasi::http::types::ErrorCode::TlsCertificateError => {
511                latest::http::types::ErrorCode::TlsCertificateError
512            }
513            wasi::http::types::ErrorCode::TlsAlertReceived(e) => {
514                latest::http::types::ErrorCode::TlsAlertReceived(e.into())
515            }
516            wasi::http::types::ErrorCode::HttpRequestDenied => {
517                latest::http::types::ErrorCode::HttpRequestDenied
518            }
519            wasi::http::types::ErrorCode::HttpRequestLengthRequired => {
520                latest::http::types::ErrorCode::HttpRequestLengthRequired
521            }
522            wasi::http::types::ErrorCode::HttpRequestBodySize(e) => {
523                latest::http::types::ErrorCode::HttpRequestBodySize(e)
524            }
525            wasi::http::types::ErrorCode::HttpRequestMethodInvalid => {
526                latest::http::types::ErrorCode::HttpRequestMethodInvalid
527            }
528            wasi::http::types::ErrorCode::HttpRequestUriInvalid => {
529                latest::http::types::ErrorCode::HttpRequestUriInvalid
530            }
531            wasi::http::types::ErrorCode::HttpRequestUriTooLong => {
532                latest::http::types::ErrorCode::HttpRequestUriTooLong
533            }
534            wasi::http::types::ErrorCode::HttpRequestHeaderSectionSize(e) => {
535                latest::http::types::ErrorCode::HttpRequestHeaderSectionSize(e)
536            }
537            wasi::http::types::ErrorCode::HttpRequestHeaderSize(e) => {
538                latest::http::types::ErrorCode::HttpRequestHeaderSize(e.map(|e| e.into()))
539            }
540            wasi::http::types::ErrorCode::HttpRequestTrailerSectionSize(e) => {
541                latest::http::types::ErrorCode::HttpRequestTrailerSectionSize(e)
542            }
543            wasi::http::types::ErrorCode::HttpRequestTrailerSize(e) => {
544                latest::http::types::ErrorCode::HttpRequestTrailerSize(e.into())
545            }
546            wasi::http::types::ErrorCode::HttpResponseIncomplete => {
547                latest::http::types::ErrorCode::HttpResponseIncomplete
548            }
549            wasi::http::types::ErrorCode::HttpResponseHeaderSectionSize(e) => {
550                latest::http::types::ErrorCode::HttpResponseHeaderSectionSize(e)
551            }
552            wasi::http::types::ErrorCode::HttpResponseHeaderSize(e) => {
553                latest::http::types::ErrorCode::HttpResponseHeaderSize(e.into())
554            }
555            wasi::http::types::ErrorCode::HttpResponseBodySize(e) => {
556                latest::http::types::ErrorCode::HttpResponseBodySize(e)
557            }
558            wasi::http::types::ErrorCode::HttpResponseTrailerSectionSize(e) => {
559                latest::http::types::ErrorCode::HttpResponseTrailerSectionSize(e)
560            }
561            wasi::http::types::ErrorCode::HttpResponseTrailerSize(e) => {
562                latest::http::types::ErrorCode::HttpResponseTrailerSize(e.into())
563            }
564            wasi::http::types::ErrorCode::HttpResponseTransferCoding(e) => {
565                latest::http::types::ErrorCode::HttpResponseTransferCoding(e)
566            }
567            wasi::http::types::ErrorCode::HttpResponseContentCoding(e) => {
568                latest::http::types::ErrorCode::HttpResponseContentCoding(e)
569            }
570            wasi::http::types::ErrorCode::HttpResponseTimeout => {
571                latest::http::types::ErrorCode::HttpResponseTimeout
572            }
573            wasi::http::types::ErrorCode::HttpUpgradeFailed => {
574                latest::http::types::ErrorCode::HttpUpgradeFailed
575            }
576            wasi::http::types::ErrorCode::HttpProtocolError => {
577                latest::http::types::ErrorCode::HttpProtocolError
578            }
579            wasi::http::types::ErrorCode::LoopDetected => {
580                latest::http::types::ErrorCode::LoopDetected
581            }
582            wasi::http::types::ErrorCode::ConfigurationError => {
583                latest::http::types::ErrorCode::ConfigurationError
584            }
585            wasi::http::types::ErrorCode::InternalError(e) => {
586                latest::http::types::ErrorCode::InternalError(e)
587            }
588        }
589    }
590}
591
592impl From<latest::http::types::ErrorCode> for wasi::http::types::ErrorCode {
593    fn from(e: latest::http::types::ErrorCode) -> Self {
594        match e {
595            latest::http::types::ErrorCode::DnsTimeout => wasi::http::types::ErrorCode::DnsTimeout,
596            latest::http::types::ErrorCode::DnsError(e) => {
597                wasi::http::types::ErrorCode::DnsError(e.into())
598            }
599            latest::http::types::ErrorCode::DestinationNotFound => {
600                wasi::http::types::ErrorCode::DestinationNotFound
601            }
602            latest::http::types::ErrorCode::DestinationUnavailable => {
603                wasi::http::types::ErrorCode::DestinationUnavailable
604            }
605            latest::http::types::ErrorCode::DestinationIpProhibited => {
606                wasi::http::types::ErrorCode::DestinationIpProhibited
607            }
608            latest::http::types::ErrorCode::DestinationIpUnroutable => {
609                wasi::http::types::ErrorCode::DestinationIpUnroutable
610            }
611            latest::http::types::ErrorCode::ConnectionRefused => {
612                wasi::http::types::ErrorCode::ConnectionRefused
613            }
614            latest::http::types::ErrorCode::ConnectionTerminated => {
615                wasi::http::types::ErrorCode::ConnectionTerminated
616            }
617            latest::http::types::ErrorCode::ConnectionTimeout => {
618                wasi::http::types::ErrorCode::ConnectionTimeout
619            }
620            latest::http::types::ErrorCode::ConnectionReadTimeout => {
621                wasi::http::types::ErrorCode::ConnectionReadTimeout
622            }
623            latest::http::types::ErrorCode::ConnectionWriteTimeout => {
624                wasi::http::types::ErrorCode::ConnectionWriteTimeout
625            }
626            latest::http::types::ErrorCode::ConnectionLimitReached => {
627                wasi::http::types::ErrorCode::ConnectionLimitReached
628            }
629            latest::http::types::ErrorCode::TlsProtocolError => {
630                wasi::http::types::ErrorCode::TlsProtocolError
631            }
632            latest::http::types::ErrorCode::TlsCertificateError => {
633                wasi::http::types::ErrorCode::TlsCertificateError
634            }
635            latest::http::types::ErrorCode::TlsAlertReceived(e) => {
636                wasi::http::types::ErrorCode::TlsAlertReceived(e.into())
637            }
638            latest::http::types::ErrorCode::HttpRequestDenied => {
639                wasi::http::types::ErrorCode::HttpRequestDenied
640            }
641            latest::http::types::ErrorCode::HttpRequestLengthRequired => {
642                wasi::http::types::ErrorCode::HttpRequestLengthRequired
643            }
644            latest::http::types::ErrorCode::HttpRequestBodySize(e) => {
645                wasi::http::types::ErrorCode::HttpRequestBodySize(e)
646            }
647            latest::http::types::ErrorCode::HttpRequestMethodInvalid => {
648                wasi::http::types::ErrorCode::HttpRequestMethodInvalid
649            }
650            latest::http::types::ErrorCode::HttpRequestUriInvalid => {
651                wasi::http::types::ErrorCode::HttpRequestUriInvalid
652            }
653            latest::http::types::ErrorCode::HttpRequestUriTooLong => {
654                wasi::http::types::ErrorCode::HttpRequestUriTooLong
655            }
656            latest::http::types::ErrorCode::HttpRequestHeaderSectionSize(e) => {
657                wasi::http::types::ErrorCode::HttpRequestHeaderSectionSize(e)
658            }
659            latest::http::types::ErrorCode::HttpRequestHeaderSize(e) => {
660                wasi::http::types::ErrorCode::HttpRequestHeaderSize(e.map(|e| e.into()))
661            }
662            latest::http::types::ErrorCode::HttpRequestTrailerSectionSize(e) => {
663                wasi::http::types::ErrorCode::HttpRequestTrailerSectionSize(e)
664            }
665            latest::http::types::ErrorCode::HttpRequestTrailerSize(e) => {
666                wasi::http::types::ErrorCode::HttpRequestTrailerSize(e.into())
667            }
668            latest::http::types::ErrorCode::HttpResponseIncomplete => {
669                wasi::http::types::ErrorCode::HttpResponseIncomplete
670            }
671            latest::http::types::ErrorCode::HttpResponseHeaderSectionSize(e) => {
672                wasi::http::types::ErrorCode::HttpResponseHeaderSectionSize(e)
673            }
674            latest::http::types::ErrorCode::HttpResponseHeaderSize(e) => {
675                wasi::http::types::ErrorCode::HttpResponseHeaderSize(e.into())
676            }
677            latest::http::types::ErrorCode::HttpResponseBodySize(e) => {
678                wasi::http::types::ErrorCode::HttpResponseBodySize(e)
679            }
680            latest::http::types::ErrorCode::HttpResponseTrailerSectionSize(e) => {
681                wasi::http::types::ErrorCode::HttpResponseTrailerSectionSize(e)
682            }
683            latest::http::types::ErrorCode::HttpResponseTrailerSize(e) => {
684                wasi::http::types::ErrorCode::HttpResponseTrailerSize(e.into())
685            }
686            latest::http::types::ErrorCode::HttpResponseTransferCoding(e) => {
687                wasi::http::types::ErrorCode::HttpResponseTransferCoding(e)
688            }
689            latest::http::types::ErrorCode::HttpResponseContentCoding(e) => {
690                wasi::http::types::ErrorCode::HttpResponseContentCoding(e)
691            }
692            latest::http::types::ErrorCode::HttpResponseTimeout => {
693                wasi::http::types::ErrorCode::HttpResponseTimeout
694            }
695            latest::http::types::ErrorCode::HttpUpgradeFailed => {
696                wasi::http::types::ErrorCode::HttpUpgradeFailed
697            }
698            latest::http::types::ErrorCode::HttpProtocolError => {
699                wasi::http::types::ErrorCode::HttpProtocolError
700            }
701            latest::http::types::ErrorCode::LoopDetected => {
702                wasi::http::types::ErrorCode::LoopDetected
703            }
704            latest::http::types::ErrorCode::ConfigurationError => {
705                wasi::http::types::ErrorCode::ConfigurationError
706            }
707            latest::http::types::ErrorCode::InternalError(e) => {
708                wasi::http::types::ErrorCode::InternalError(e)
709            }
710        }
711    }
712}