1 import Base 2 import ./execution_resource_policy.bend as Policy 3 import ./clock_state.bend as Clock 4 import ./ordinary_declaration.bend as Identity 5 import ./ordinary_schema.bend as Resource 6 import ./schema_fragments.bend as Fragment 7 import ./execution_composer_layout.bend as Layout 8 import ./persistence_declaration.bend as Persist 9 import ./decode_data.bend as Decode 10 import ./world.bend as W 11 12 type FragmentSchema<-S:Data,-C:Type,-R:Type> is Data: 13 FragmentSchema{entries:List<&2,Fragment.Entry>} 14 def component(~S:Data,~P:Type,~V:Data,~refresh:P -> P & V,identity:Identity.Declaration) -> Layout.Layout: 15 Layout.LayoutLeaf{P,V,refresh,Identity.key(~S,~P,identity),Policy.Ordinary{}} 16 def resource(~S:Data,~P:Type,~V:Data,~refresh:P -> P & V,identity:Resource.Resource) -> Layout.Layout: 17 Layout.LayoutLeaf{P,V,refresh,Resource.resource_key(~S,~P,identity),Policy.Ordinary{}} 18 def plain(~S:Data,~P:Type,~identity:Identity.Declaration,~V:Data,~refresh:P -> P & V,extension:Persist.Plain) -> Layout.Layout: 19 Layout.ClassifiedLayoutLeaf{P,V,refresh,Identity.key(~S,~P,identity),Fragment.Plain{},Policy.Ordinary{}} 20 def transient(~S:Data,~P:Type,~identity:Identity.Declaration,~V:Data,~refresh:P -> P & V,extension:Persist.Transient) -> Layout.Layout: 21 Layout.ClassifiedLayoutLeaf{P,V,refresh,Identity.key(~S,~P,identity),Fragment.Transient{},Policy.Ordinary{}} 22 def constructed(~S:Data,~P:Type,~identity:Identity.Declaration,~project:P -> P & Decode.Raw,~V:Data,~refresh:P -> P & V,extension:Persist.Constructed) -> Layout.Layout: 23 Layout.ClassifiedLayoutLeaf{P,V,refresh,Identity.key(~S,~P,identity),Fragment.Constructed{},Policy.Ordinary{}} 24 def layout_entries(~S:Data,+kind:Fragment.RegistryKind,layout:Layout.Layout) -> List<&2,Fragment.Entry>: 25 match layout: 26 case Layout.EmptyLayout{}:[] 27 case Layout.LayoutLeaf{_,_,_,+key,_}:[Fragment.Entry{kind,key,key}] 28 case Layout.ClassifiedLayoutLeaf{_,_,_,+key,persistence,_}:[Fragment.Classified{kind,key,key,persistence}] 29 case Layout.LayoutPair{left,right}:List.append(&2,Fragment.Entry,layout_entries(~S,kind,left),layout_entries(~S,kind,right)) 30 def inventory(~S:Data,~components:Layout.Layout,~resources:Layout.Layout) -> List<&2,Fragment.Entry>: 31 List.append(&2,Fragment.Entry,layout_entries(~S,Fragment.Component{},components),layout_entries(~S,Fragment.Resource{},resources)) 32 def declared(~S:Data,~components:Layout.Layout,~resources:Layout.Layout) -> FragmentSchema: 33 FragmentSchema{inventory(~S,~components,~resources)} 34 def entries(~S:Data,~C:Type,~R:Type,value:FragmentSchema) -> List<&2,Fragment.Entry>: 35 match value: 36 case FragmentSchema{entries}:entries 37 def fragment(~S:Data,~components:Layout.Layout,~resources:Layout.Layout,~Provisions:Type,provisions:Provisions) -> Fragment.Fragment: 38 Fragment.Fragment{inventory(~S,~components,~resources),provisions} 39 def validate(~S:Data,~components:Layout.Layout,~resources:Layout.Layout) -> Fragment.Validation: 40 Fragment.validate(~S,inventory(~S,~components,~resources)) 41 def empty_columns(~S:Data,~components:Layout.Layout,_:Unit) -> Layout.columns(~S,components): 42 Layout.empty_columns(~S,components) 43 type Initialized<-S:Data,-Components:Layout.Layout,-Resources:Layout.Layout,-E:Data> is Type: 44 SchemaCreated{factory:W.Factory,world:W.World} 45 SchemaRefused{factory:W.Factory,resources:Layout.resources(~S,Resources),error:Fragment.Error} 46 NamespaceRefused{factory:W.Factory,resources:Layout.resources(~S,Resources)} 47 def initialized_world(~S:Data,~components:Layout.Layout,~resources:Layout.Layout,~E:Data,world:W.World) -> W.World: 48 match world: 49 case W.World{namespace,allocator,store,owners,events,pending,registrations,next,+clock,lifecycle}:W.World{namespace,allocator,store,Layout.initialize_resources(~S,resources,Clock.current(clock),owners),events,pending,registrations,next,clock,lifecycle} 50 def created(~S:Data,~components:Layout.Layout,~resources:Layout.Layout,~E:Data,result:W.Creation) -> Initialized: 51 match result: 52 case W.Created{factory,world}:SchemaCreated{factory,initialized_world(~S,~components,~resources,~E,world)} 53 case W.CreateRejected{factory,resource}:NamespaceRefused{factory,resource} 54 def create_checked(~S:Data,~components:Layout.Layout,~resources:Layout.Layout,~E:Data,result:Fragment.Validation,factory:W.Factory,owners:Layout.resources(~S,resources)) -> Initialized: 55 match result: 56 case Fragment.Invalid{error}:SchemaRefused{factory,owners,error} 57 case Fragment.Valid{}:created(~S,~components,~resources,~E,W.create(~S,~Layout.columns(~S,components),~Layout.resources(~S,resources),~E,~empty_columns(~S,~components),factory,owners)) 58 def create(~S:Data,~components:Layout.Layout,~resources:Layout.Layout,~E:Data,factory:W.Factory,owners:Layout.resources(~S,resources)) -> Initialized: 59 create_checked(~S,~components,~resources,~E,validate(~S,~components,~resources),factory,owners) 60 # The trusted closed seed must initialize every occupied row through Layout.initialize. 61 # It constructs initial storage and never receives runtime execution authority. 62 def trusted_create_seeded_checked(~S:Data,~components:Layout.Layout,~resources:Layout.Layout,~E:Data,~seed:Unit -> Layout.columns(~S,components),result:Fragment.Validation,factory:W.Factory,owners:Layout.resources(~S,resources)) -> Initialized: 63 match result: 64 case Fragment.Invalid{error}:SchemaRefused{factory,owners,error} 65 case Fragment.Valid{}:created(~S,~components,~resources,~E,W.create(~S,~Layout.columns(~S,components),~Layout.resources(~S,resources),~E,~seed,factory,owners)) 66 def trusted_create_seeded(~S:Data,~components:Layout.Layout,~resources:Layout.Layout,~E:Data,~seed:Unit -> Layout.columns(~S,components),factory:W.Factory,owners:Layout.resources(~S,resources)) -> Initialized: 67 trusted_create_seeded_checked(~S,~components,~resources,~E,~seed,validate(~S,~components,~resources),factory,owners)