11use std:: { collections:: HashMap , sync:: Arc } ;
22
33use anyhow:: Context ;
4+ use futures_util:: { future:: { BoxFuture , Shared } , FutureExt } ;
5+ use spin_factor_variables:: VariablesFactor ;
46use spin_factor_wasi:: WasiFactor ;
57use spin_factors:: { Factor , FactorInstancePreparer , Result , SpinFactors } ;
68use spin_outbound_networking:: { AllowedHostsConfig , HostConfig , PortConfig , ALLOWED_HOSTS_KEY } ;
@@ -17,33 +19,34 @@ impl Factor for OutboundNetworkingFactor {
1719 app : & spin_factors:: App ,
1820 _ctx : spin_factors:: ConfigureAppContext < Factors > ,
1921 ) -> Result < Self :: AppConfig > {
20- let mut cfg = AppConfig :: default ( ) ;
21- // TODO: resolve resolver resolution
22- let resolver = Default :: default ( ) ;
23- for component in app. components ( ) {
24- if let Some ( hosts) = component. get_metadata ( ALLOWED_HOSTS_KEY ) ? {
25- let allowed_hosts = AllowedHostsConfig :: parse ( & hosts, & resolver) ?;
26- cfg. component_allowed_hosts
27- . insert ( component. id ( ) . to_string ( ) , Arc :: new ( allowed_hosts) ) ;
28- }
29- }
30- Ok ( cfg)
22+ // Extract allowed_outbound_hosts for all components
23+ let component_allowed_hosts = app
24+ . components ( )
25+ . map ( |component| {
26+ Ok ( (
27+ component. id ( ) . to_string ( ) ,
28+ component
29+ . get_metadata ( ALLOWED_HOSTS_KEY ) ?
30+ . unwrap_or_default ( ) ,
31+ ) )
32+ } )
33+ . collect :: < Result < _ > > ( ) ?;
34+
35+ Ok ( AppConfig {
36+ component_allowed_hosts,
37+ } )
3138 }
3239}
3340
3441#[ derive( Default ) ]
3542pub struct AppConfig {
36- component_allowed_hosts : HashMap < String , Arc < AllowedHostsConfig > > ,
43+ component_allowed_hosts : HashMap < String , Vec < String > > ,
3744}
3845
39- pub struct InstancePreparer {
40- allowed_hosts : Arc < AllowedHostsConfig > ,
41- }
46+ type AllowedHostsFuture = Shared < BoxFuture < ' static , Arc < anyhow:: Result < AllowedHostsConfig > > > > ;
4247
43- impl InstancePreparer {
44- pub fn allowed_hosts ( & self ) -> & Arc < AllowedHostsConfig > {
45- & self . allowed_hosts
46- }
48+ pub struct InstancePreparer {
49+ allowed_hosts_future : AllowedHostsFuture ,
4750}
4851
4952impl FactorInstancePreparer < OutboundNetworkingFactor > for InstancePreparer {
@@ -52,16 +55,26 @@ impl FactorInstancePreparer<OutboundNetworkingFactor> for InstancePreparer {
5255 app_component : & spin_factors:: AppComponent ,
5356 mut ctx : spin_factors:: PrepareContext < Factors > ,
5457 ) -> Result < Self > {
55- let allowed_hosts = ctx
56- . app_config :: < OutboundNetworkingFactor > ( ) ?
57- . component_allowed_hosts
58- . get ( app_component. id ( ) )
59- . context ( "missing component" ) ?
60- . clone ( ) ;
58+ let hosts =
59+ ctx. app_config :: < OutboundNetworkingFactor > ( )
60+ . unwrap ( )
61+ . component_allowed_hosts
62+ . get ( app_component. id ( ) )
63+ . context ( "missing component allowed hosts" ) ?;
64+ let resolver = ctx. instance_preparer_mut :: < VariablesFactor > ( ) ?. resolver ( ) . clone ( ) ;
65+ let allowed_hosts_future = async move {
66+ let prepared = resolver. prepare ( ) . await ?;
67+ Ok ( AllowedHostsConfig :: parse ( & hosts, & prepared) )
68+ } . boxed ( ) . shared ( ) ;
69+ let prepared_resolver = resolver. prepare ( ) . await ?;
70+ let allowed_hosts = AllowedHostsConfig :: parse (
71+ . context ( "missing component allowed hosts" ) ?,
72+ & prepared_resolver,
73+ ) ?;
6174
6275 // Update Wasi socket allowed ports
6376 let wasi_preparer = ctx. instance_preparer_mut :: < WasiFactor > ( ) ?;
64- match & * allowed_hosts {
77+ match & allowed_hosts {
6578 AllowedHostsConfig :: All => wasi_preparer. inherit_network ( ) ,
6679 AllowedHostsConfig :: SpecificHosts ( configs) => {
6780 for config in configs {
@@ -77,10 +90,18 @@ impl FactorInstancePreparer<OutboundNetworkingFactor> for InstancePreparer {
7790 }
7891 }
7992
80- Ok ( Self { allowed_hosts } )
93+ Ok ( Self {
94+ allowed_hosts : Arc :: new ( allowed_hosts) ,
95+ } )
8196 }
8297
8398 fn prepare ( self ) -> Result < <OutboundNetworkingFactor as Factor >:: InstanceState > {
8499 Ok ( ( ) )
85100 }
86101}
102+
103+ impl InstancePreparer {
104+ pub async fn resolve_allowed_hosts ( & self ) -> Arc < anyhow:: Result < AllowedHostsConfig > > {
105+ self . allowed_hosts_future . clone ( ) . await
106+ }
107+ }
0 commit comments