33 * Copyright (c) "2025" . The DeepCausality Authors and Contributors. All Rights Reserved.
44 */
55
6- use crate :: {
7- ActionError , CSMMap , CausalAction , CausalState , CsmError , DeonticExplainable , EffectEthos ,
8- PropagatingEffect , ProposedAction , StateAction , TeloidModal , TeloidTag , UpdateError ,
9- } ;
10- use crate :: { Datable , DeonticInferable , SpaceTemporal , Spatial , Symbolic , Temporal } ;
6+ mod eval;
7+
8+ use crate :: { CSMMap , CausalAction , CausalState , EffectEthos , StateAction , TeloidTag , UpdateError } ;
9+ use crate :: { Datable , SpaceTemporal , Spatial , Symbolic , Temporal } ;
1110use std:: collections:: HashMap ;
1211use std:: fmt:: Debug ;
1312use std:: sync:: { Arc , RwLock } ;
@@ -140,69 +139,6 @@ where
140139 Ok ( ( ) )
141140 }
142141
143- /// Evaluates a single causal state at the index position id.
144- /// If the state evaluates to `PropagatingEffect::Deterministic(true)`, the associated action is fired.
145- ///
146- /// # Errors
147- /// Returns `CsmError` if the state does not exist, evaluation fails, the effect is not
148- /// deterministic, or the action fails to fire.
149- pub fn eval_single_state ( & self , id : usize , data : & PropagatingEffect ) -> Result < ( ) , CsmError > {
150- let binding = self . state_actions . read ( ) . unwrap ( ) ;
151-
152- let ( state, action) = binding. get ( & id) . ok_or_else ( || {
153- CsmError :: Action (
154- format ! ( "State {id} does not exist. Add it first before evaluating." ) . into ( ) ,
155- )
156- } ) ?;
157-
158- let effect = state. eval_with_data ( data) ?;
159-
160- match & effect {
161- PropagatingEffect :: Deterministic ( true ) => {
162- if let Some ( ( ethos, tags) ) = & self . effect_ethos {
163- if let Some ( context) = state. context ( ) {
164- let action_name = format ! (
165- "proposed action for CSM State: {} version: {}" ,
166- state. id( ) ,
167- state. version( )
168- ) ;
169-
170- let proposed_action =
171- self . create_proposed_action ( action_name, state, & effect) ?;
172- let verdict = ethos. evaluate_action ( & proposed_action, context, tags) ?;
173-
174- if verdict. outcome ( ) == TeloidModal :: Impermissible {
175- let explanation = ethos. explain_verdict ( & verdict) ?;
176- return Err ( CsmError :: Forbidden ( explanation) ) ;
177- } else {
178- action. fire ( ) ?;
179- }
180- } else {
181- return Err ( CsmError :: Action ( ActionError :: new (
182- "Cannot evaluate action with ethos because state context is missing."
183- . into ( ) ,
184- ) ) ) ;
185- }
186- } else {
187- action. fire ( ) ?;
188- }
189- Ok ( ( ) )
190- }
191- PropagatingEffect :: Deterministic ( false ) => {
192- // State evaluated to false, do nothing.
193- Ok ( ( ) )
194- }
195- _ => {
196- // The effect was not deterministic, which is an invalid state for a CSM.
197- Err ( CsmError :: Action ( ActionError ( format ! (
198- "CSM[eval]: Invalid non-deterministic effect '{:?}' for state {}" ,
199- effect,
200- state. id( )
201- ) ) ) )
202- }
203- }
204- }
205-
206142 /// Updates a causal state with a new state at the index position idx.
207143 /// Returns UpdateError if the update operation failed.
208144 pub fn update_single_state (
@@ -226,65 +162,6 @@ where
226162 Ok ( ( ) )
227163 }
228164
229- /// Evaluates all causal states in the CSM using their internal data.
230- /// For each state that evaluates to `PropagatingEffect::Deterministic(true)`, the associated action is fired.
231- ///
232- /// # Errors
233- /// Returns `CsmError` if any state evaluation fails, produces a non-deterministic effect,
234- /// or any triggered action fails to fire.
235- pub fn eval_all_states ( & self ) -> Result < ( ) , CsmError > {
236- let binding = self . state_actions . read ( ) . unwrap ( ) ;
237-
238- for ( _id, ( state, action) ) in binding. iter ( ) {
239- let effect = state. eval ( ) ?;
240-
241- match & effect {
242- PropagatingEffect :: Deterministic ( true ) => {
243- if let Some ( ( ethos, tags) ) = & self . effect_ethos {
244- if let Some ( context) = state. context ( ) {
245- let action_name = format ! (
246- "proposed action for CSM State: {} version: {}" ,
247- state. id( ) ,
248- state. version( )
249- ) ;
250-
251- let proposed_action =
252- self . create_proposed_action ( action_name, state, & effect) ?;
253- let verdict = ethos. evaluate_action ( & proposed_action, context, tags) ?;
254-
255- if verdict. outcome ( ) == TeloidModal :: Impermissible {
256- let explanation = ethos. explain_verdict ( & verdict) ?;
257- return Err ( CsmError :: Forbidden ( explanation) ) ;
258- } else {
259- action. fire ( ) ?;
260- }
261- } else {
262- return Err ( CsmError :: Action ( ActionError :: new (
263- "Cannot evaluate action with ethos because state context is missing."
264- . into ( ) ,
265- ) ) ) ;
266- }
267- } else {
268- action. fire ( ) ?
269- }
270- }
271- PropagatingEffect :: Deterministic ( false ) => {
272- // State evaluated to false, do nothing, continue loop.
273- }
274- _ => {
275- // The effect was not deterministic, which is an invalid state for a CSM.
276- return Err ( CsmError :: Action ( ActionError ( format ! (
277- "CSM[eval]: Invalid non-deterministic effect '{:?}' for state {}" ,
278- effect,
279- state. id( )
280- ) ) ) ) ;
281- }
282- }
283- }
284-
285- Ok ( ( ) )
286- }
287-
288165 /// Updates all causal state with a new state collection.
289166 /// Note, this operation erases all previous states in the CSM by generating a new collection.
290167 /// Returns UpdateError if the update operation failed.
@@ -302,16 +179,4 @@ where
302179 * self . state_actions . write ( ) . unwrap ( ) = state_map;
303180 Ok ( ( ) )
304181 }
305-
306- fn create_proposed_action (
307- & self ,
308- action_name : String ,
309- state : & CausalState < D , S , T , ST , SYM , VS , VT > ,
310- effect : & PropagatingEffect ,
311- ) -> Result < ProposedAction , CsmError > {
312- let mut params = HashMap :: new ( ) ;
313- params. insert ( "trigger_effect" . to_string ( ) , effect. clone ( ) . into ( ) ) ;
314-
315- Ok ( ProposedAction :: new ( * state. id ( ) as u64 , action_name, params) )
316- }
317182}
0 commit comments