ordinary_app_machine_handler.bend
bendvy-ecs-core@0.1.0.1 · 65 lines · 0 definitions
1import Base
2import bendvy-ecs-core@0.1.0.1/change_tick.bend as Tick
3import bendvy-ecs-core@0.1.0.1/world.bend as W
4import bendvy-ecs-core@0.1.0.1/system.bend as Sys
5import bendvy-ecs-core@0.1.0.1/machine.bend as M
6import bendvy-ecs-core@0.1.0.1/machine_handlers.bend as H
7import bendvy-ecs-core@0.1.0.1/machine_handler_bundle.bend as B
8import bendvy-ecs-core@0.1.0.1/ordinary_machine_handler_bundle.bend as Operation
9import bendvy-ecs-core@0.1.0.1/ordinary_machine_schedule.bend as Ordinary
10import bendvy-ecs-core@0.1.0.1/schedule.bend as Sch
11
12# Detached handler selector/requirements and actual registry metadata for display.
13# Does not own a handler, grant capabilities or duplicate Local/capture state.
14type EntryView<S:Data,K:Data,V:Data,Q:Data> is Data:
15 EntryView{selector:B.Selector<S,K,V>,requirements:List<&2,Q>,namespace:U32,entryId:U32,id:U32,name:String,access:List<&2,String>,cursor:Maybe<&2,Tick.Tick>}
16# Detached marker schedule phases and ordered handler entry views.
17type Description<S:Data,K:Data,V:Data,Q:Data> is Data:
18 Description{namespace:U32,name:String,steps:List<&2,Sch.Step>,entries:List<&2,EntryView<S,K,V,Q>>}
19# Affine World, handler bundle and extra owners with declaration/debug. Recovering
20# retains an existing MarkerResult rather than silently starting another marker.
21type Application<S:Data,K:Data,V:Data,Q:Data,C:Type,R:Type,E:Data,-runner:W.World<S,C,R,E> -> H.Invocation<V> -> Sys.Outcome<W.World<S,C,R,E>,String,Unit>,Extra:Type> is Type:
22 Application{world:W.World<S,C,R,E>,bundle:B.Bundle<S,K,V,Q,C,R,E,runner>,declaration:Ordinary.Declaration<S>,extra:Extra,debug:Bool}
23 Recovering{result:Operation.MarkerResult<S,K,V,Q,C,R,E,runner>,declaration:Ordinary.Declaration<S>,extra:Extra,debug:Bool}
24def entries_returned(~S:Data,~K:Data,~V:Data,~Q:Data,~C:Type,~R:Type,~E:Data,~runner:W.World<S,C,R,E> -> H.Invocation<V> -> Sys.Outcome<W.World<S,C,R,E>,String,Unit>,+selector:B.Selector<S,K,V>,+requirements:List<&2,Q>,+namespace:U32,+entryId:U32,+id:U32,+name:String,+access:List<&2,String>,+cursor:Maybe<&2,Tick.Tick>,result:List<&1,B.Scheduled<S,K,V,Q,C,R,E,runner>> & List<&2,EntryView<S,K,V,Q>>) -> List<&1,B.Scheduled<S,K,V,Q,C,R,E,runner>> & List<&2,EntryView<S,K,V,Q>>:
25 (rest,views)=result
26 (B.Scheduled{selector,requirements,H.Entry{entryId,Sys.Registry{namespace,id,name,access,cursor}}} <> rest,EntryView{selector,requirements,namespace,entryId,id,name,access,cursor} <> views)
27# Describe scheduled handlers in list order while returning all actual owners.
28# Detached selector/requirements/registry fields do not execute handlers or prove
29# that requirements are satisfied. This advanced helper has no debug bypass.
30def entries(~S:Data,~K:Data,~V:Data,~Q:Data,~C:Type,~R:Type,~E:Data,~runner:W.World<S,C,R,E> -> H.Invocation<V> -> Sys.Outcome<W.World<S,C,R,E>,String,Unit>,items:List<&1,B.Scheduled<S,K,V,Q,C,R,E,runner>>) -> List<&1,B.Scheduled<S,K,V,Q,C,R,E,runner>> & List<&2,EntryView<S,K,V,Q>>:
31 match items:
32 case []:([],[])
33 case B.Scheduled{selector,requirements,H.Entry{entryId,Sys.Registry{namespace,id,name,access,cursor}}} <> rest:entries_returned(~S,~K,~V,~Q,~C,~R,~E,~runner,selector,requirements,namespace,entryId,id,name,access,cursor,entries(~S,~K,~V,~Q,~C,~R,~E,~runner,rest))
34# Retain supplied actual World/bundle/extra owners as an App with debug off.
35# No preflight, phase execution or payload cleanup occurs at binding.
36def bind(~S:Data,~K:Data,~V:Data,~Q:Data,~C:Type,~R:Type,~E:Data,~runner:W.World<S,C,R,E> -> H.Invocation<V> -> Sys.Outcome<W.World<S,C,R,E>,String,Unit>,~Extra:Type,world:W.World<S,C,R,E>,bundle:B.Bundle<S,K,V,Q,C,R,E,runner>,declaration:Ordinary.Declaration<S>,extra:Extra) -> Application<S,K,V,Q,C,R,E,runner,Extra>:
37 Application{world,bundle,declaration,extra,False{}}
38# Change only observation enablement, retaining normal or recovering owner state.
39def enabled(~S:Data,~K:Data,~V:Data,~Q:Data,~C:Type,~R:Type,~E:Data,~runner:W.World<S,C,R,E> -> H.Invocation<V> -> Sys.Outcome<W.World<S,C,R,E>,String,Unit>,~Extra:Type,app:Application<S,K,V,Q,C,R,E,runner,Extra>,debug:Bool) -> Application<S,K,V,Q,C,R,E,runner,Extra>:
40 match app:
41 case Application{world,bundle,declaration,extra,_}:Application{world,bundle,declaration,extra,debug}
42 case Recovering{result,declaration,extra,_}:Recovering{result,declaration,extra,debug}
43def described(~S:Data,~K:Data,~V:Data,~Q:Data,~C:Type,~R:Type,~E:Data,~runner:W.World<S,C,R,E> -> H.Invocation<V> -> Sys.Outcome<W.World<S,C,R,E>,String,Unit>,~Extra:Type,world:W.World<S,C,R,E>,+namespace:U32,+name:String,extra:Extra,result:List<&1,B.Scheduled<S,K,V,Q,C,R,E,runner>> & List<&2,EntryView<S,K,V,Q>>) -> Application<S,K,V,Q,C,R,E,runner,Extra> & Maybe<&2,Description<S,K,V,Q>>:
44 (items,views)=result
45 (Application{world,B.Bundle{namespace,items},Ordinary.Declaration{name},extra,True{}},Some{Description{namespace,name,Ordinary.steps(),views}})
46# Describe normal enabled App entries, returning all actual handler owners.
47# Disabled or Recovering returns None without entry derivation; does not run
48# handlers, apply queued transitions or validate requirements.
49def snapshot(~S:Data,~K:Data,~V:Data,~Q:Data,~C:Type,~R:Type,~E:Data,~runner:W.World<S,C,R,E> -> H.Invocation<V> -> Sys.Outcome<W.World<S,C,R,E>,String,Unit>,~Extra:Type,app:Application<S,K,V,Q,C,R,E,runner,Extra>) -> Application<S,K,V,Q,C,R,E,runner,Extra> & Maybe<&2,Description<S,K,V,Q>>:
50 match app:
51 case Application{world,B.Bundle{namespace,items},Ordinary.Declaration{name},extra,True{}}:described(~S,~K,~V,~Q,~C,~R,~E,~runner,~Extra,world,namespace,name,extra,entries(~S,~K,~V,~Q,~C,~R,~E,~runner,items))
52 case app:(app,None{})
53
54# Retained marker result plus original declaration, extra owners and debug.
55# Inspect its BundleResult for status rather than inferring success from observations.
56type RunResult<S:Data,K:Data,V:Data,Q:Data,C:Type,R:Type,E:Data,-runner:W.World<S,C,R,E> -> H.Invocation<V> -> Sys.Outcome<W.World<S,C,R,E>,String,Unit>,Extra:Type> is Type:
57 RunResult{result:Operation.MarkerResult<S,K,V,Q,C,R,E,runner>,declaration:Ordinary.Declaration<S>,extra:Extra,debug:Bool}
58# Normal App executes ordinary marker preflight/barrier/phase machinery. Recovering
59# passes through its retained result without rerun. Returned marker keeps actual
60# owners; exit/transition failure leaves retryable pending work, while enter failure
61# retains committed current/publication. No schedule-wide transaction is added.
62def run_app(~S:Data,~K:Data,~V:Data,~Q:Data,~C:Type,~R:Type,~E:Data,~runner:W.World<S,C,R,E> -> H.Invocation<V> -> Sys.Outcome<W.World<S,C,R,E>,String,Unit>,~take:W.World<S,C,R,E> -> W.World<S,C,R,E> & M.Slot<S,K,V>,~put:W.World<S,C,R,E> -> M.Slot<S,K,V> -> W.World<S,C,R,E>,~publish:W.World<S,C,R,E> -> M.Transition<V> -> W.World<S,C,R,E>,~same:V -> V -> Bool,~requirement_same:Q -> Q -> Bool,~has:W.World<S,C,R,E> -> Q -> W.World<S,C,R,E> & Bool,~frame:W.World<S,C,R,E> -> W.World<S,C,R,E>,~Extra:Type,app:Application<S,K,V,Q,C,R,E,runner,Extra>) -> RunResult<S,K,V,Q,C,R,E,runner,Extra>:
63 match app:
64 case Recovering{result,declaration,extra,debug}:RunResult{result,declaration,extra,debug}
65 case Application{world,bundle,+declaration,extra,debug}:RunResult{Operation.run(~S,~K,~V,~Q,~C,~R,~E,~runner,~take,~put,~publish,~same,~requirement_same,~has,~frame,declaration,bundle,world),declaration,extra,debug}