@@ -224,29 +224,6 @@ impl<'e> Evaluator<'e> {
224
224
}
225
225
}
226
226
227
- /// Run an expression as far as possible.
228
- /// however, if an error is encountered, instead of error-ing, wrap the error
229
- /// in a call the `error` extension function.
230
- pub fn run_to_error (
231
- & self ,
232
- e : & Expr ,
233
- slots : & SlotEnv ,
234
- ) -> ( PartialValue , Option < EvaluationError > ) {
235
- match self . partial_interpret ( e, slots) {
236
- Ok ( e) => ( e, None ) ,
237
- Err ( err) => {
238
- let arg = Expr :: val ( format ! ( "{err}" ) ) ;
239
- // PANIC SAFETY: Input to `parse` is fully static and a valid extension function name
240
- #[ allow( clippy:: unwrap_used) ]
241
- let fn_name = "error" . parse ( ) . unwrap ( ) ;
242
- (
243
- PartialValue :: Residual ( Expr :: call_extension_fn ( fn_name, vec ! [ arg] ) ) ,
244
- Some ( err) ,
245
- )
246
- }
247
- }
248
- }
249
-
250
227
/// Interpret an `Expr` into a `Value` in this evaluation environment.
251
228
///
252
229
/// Ensures the result is not a residual.
@@ -315,10 +292,9 @@ impl<'e> Evaluator<'e> {
315
292
ExprKind :: And { left, right } => {
316
293
match self . partial_interpret ( left, slots) ? {
317
294
// PE Case
318
- PartialValue :: Residual ( e) => Ok ( PartialValue :: Residual ( Expr :: and (
319
- e,
320
- self . run_to_error ( right. as_ref ( ) , slots) . 0 . into ( ) ,
321
- ) ) ) ,
295
+ PartialValue :: Residual ( e) => {
296
+ Ok ( PartialValue :: Residual ( Expr :: and ( e, right. as_ref ( ) . clone ( ) ) ) )
297
+ }
322
298
// Full eval case
323
299
PartialValue :: Value ( v) => {
324
300
if v. get_as_bool ( ) ? {
@@ -342,10 +318,9 @@ impl<'e> Evaluator<'e> {
342
318
ExprKind :: Or { left, right } => {
343
319
match self . partial_interpret ( left, slots) ? {
344
320
// PE cases
345
- PartialValue :: Residual ( r) => Ok ( PartialValue :: Residual ( Expr :: or (
346
- r,
347
- self . run_to_error ( right, slots) . 0 . into ( ) ,
348
- ) ) ) ,
321
+ PartialValue :: Residual ( r) => {
322
+ Ok ( PartialValue :: Residual ( Expr :: or ( r, right. as_ref ( ) . clone ( ) ) ) )
323
+ }
349
324
// Full eval case
350
325
PartialValue :: Value ( lhs) => {
351
326
if lhs. get_as_bool ( ) ? {
@@ -687,8 +662,8 @@ impl<'e> Evaluator<'e> {
687
662
fn eval_if (
688
663
& self ,
689
664
guard : & Expr ,
690
- consequent : & Expr ,
691
- alternative : & Expr ,
665
+ consequent : & Arc < Expr > ,
666
+ alternative : & Arc < Expr > ,
692
667
slots : & SlotEnv ,
693
668
) -> Result < PartialValue > {
694
669
match self . partial_interpret ( guard, slots) ? {
@@ -700,13 +675,7 @@ impl<'e> Evaluator<'e> {
700
675
}
701
676
}
702
677
PartialValue :: Residual ( guard) => {
703
- let ( consequent, consequent_errored) = self . run_to_error ( consequent, slots) ;
704
- let ( alternative, alternative_errored) = self . run_to_error ( alternative, slots) ;
705
- // If both branches errored, the expression will always error
706
- match ( consequent_errored, alternative_errored) {
707
- ( Some ( e) , Some ( _) ) => Err ( e) ,
708
- _ => Ok ( Expr :: ite ( guard, consequent. into ( ) , alternative. into ( ) ) . into ( ) ) ,
709
- }
678
+ Ok ( Expr :: ite_arc ( Arc :: new ( guard) , consequent. clone ( ) , alternative. clone ( ) ) . into ( ) )
710
679
}
711
680
}
712
681
}
@@ -4889,7 +4858,7 @@ pub mod test {
4889
4858
let b = Expr :: and ( Expr :: val ( 1 ) , Expr :: val ( 2 ) ) ;
4890
4859
let c = Expr :: val ( true ) ;
4891
4860
4892
- let e = Expr :: ite ( a, b, c) ;
4861
+ let e = Expr :: ite ( a, b. clone ( ) , c) ;
4893
4862
4894
4863
let es = Entities :: new ( ) ;
4895
4864
@@ -4902,10 +4871,7 @@ pub mod test {
4902
4871
r,
4903
4872
PartialValue :: Residual ( Expr :: ite(
4904
4873
Expr :: unknown( Unknown :: new_untyped( "guard" ) ) ,
4905
- Expr :: call_extension_fn(
4906
- "error" . parse( ) . unwrap( ) ,
4907
- vec![ Expr :: val( "type error: expected bool, got long" ) ]
4908
- ) ,
4874
+ b,
4909
4875
Expr :: val( true )
4910
4876
) )
4911
4877
)
@@ -4970,14 +4936,21 @@ pub mod test {
4970
4936
let b = Expr :: and ( Expr :: val ( 1 ) , Expr :: val ( 2 ) ) ;
4971
4937
let c = Expr :: or ( Expr :: val ( 1 ) , Expr :: val ( 3 ) ) ;
4972
4938
4973
- let e = Expr :: ite ( a, b, c) ;
4939
+ let e = Expr :: ite ( a, b. clone ( ) , c. clone ( ) ) ;
4974
4940
4975
4941
let es = Entities :: new ( ) ;
4976
4942
4977
4943
let exts = Extensions :: none ( ) ;
4978
4944
let eval = Evaluator :: new ( empty_request ( ) , & es, & exts) ;
4979
4945
4980
- assert_matches ! ( eval. partial_interpret( & e, & HashMap :: new( ) ) , Err ( _) ) ;
4946
+ assert_eq ! (
4947
+ eval. partial_interpret( & e, & HashMap :: new( ) ) . unwrap( ) ,
4948
+ PartialValue :: Residual ( Expr :: ite(
4949
+ Expr :: unknown( Unknown :: new_untyped( "guard" ) ) ,
4950
+ b,
4951
+ c
4952
+ ) )
4953
+ ) ;
4981
4954
}
4982
4955
4983
4956
#[ test]
@@ -5224,22 +5197,15 @@ pub mod test {
5224
5197
let guard = Expr :: get_attr ( Expr :: unknown ( Unknown :: new_untyped ( "a" ) ) , "field" . into ( ) ) ;
5225
5198
let cons = Expr :: binary_app ( BinaryOp :: Add , Expr :: val ( 1 ) , Expr :: val ( true ) ) ;
5226
5199
let alt = Expr :: val ( 2 ) ;
5227
- let e = Expr :: ite ( guard. clone ( ) , cons, alt) ;
5200
+ let e = Expr :: ite ( guard. clone ( ) , cons. clone ( ) , alt) ;
5228
5201
5229
5202
let es = Entities :: new ( ) ;
5230
5203
let exts = Extensions :: none ( ) ;
5231
5204
let eval = Evaluator :: new ( empty_request ( ) , & es, & exts) ;
5232
5205
5233
5206
let r = eval. partial_interpret ( & e, & HashMap :: new ( ) ) . unwrap ( ) ;
5234
5207
5235
- let expected = Expr :: ite (
5236
- guard,
5237
- Expr :: call_extension_fn (
5238
- "error" . parse ( ) . unwrap ( ) ,
5239
- vec ! [ Expr :: val( "type error: expected long, got bool" ) ] ,
5240
- ) ,
5241
- Expr :: val ( 2 ) ,
5242
- ) ;
5208
+ let expected = Expr :: ite ( guard, cons, Expr :: val ( 2 ) ) ;
5243
5209
5244
5210
assert_eq ! ( r, PartialValue :: Residual ( expected) ) ;
5245
5211
}
@@ -5249,22 +5215,15 @@ pub mod test {
5249
5215
let guard = Expr :: get_attr ( Expr :: unknown ( Unknown :: new_untyped ( "a" ) ) , "field" . into ( ) ) ;
5250
5216
let cons = Expr :: val ( 2 ) ;
5251
5217
let alt = Expr :: binary_app ( BinaryOp :: Add , Expr :: val ( 1 ) , Expr :: val ( true ) ) ;
5252
- let e = Expr :: ite ( guard. clone ( ) , cons, alt) ;
5218
+ let e = Expr :: ite ( guard. clone ( ) , cons, alt. clone ( ) ) ;
5253
5219
5254
5220
let es = Entities :: new ( ) ;
5255
5221
let exts = Extensions :: none ( ) ;
5256
5222
let eval = Evaluator :: new ( empty_request ( ) , & es, & exts) ;
5257
5223
5258
5224
let r = eval. partial_interpret ( & e, & HashMap :: new ( ) ) . unwrap ( ) ;
5259
5225
5260
- let expected = Expr :: ite (
5261
- guard,
5262
- Expr :: val ( 2 ) ,
5263
- Expr :: call_extension_fn (
5264
- "error" . parse ( ) . unwrap ( ) ,
5265
- vec ! [ Expr :: val( "type error: expected long, got bool" ) ] ,
5266
- ) ,
5267
- ) ;
5226
+ let expected = Expr :: ite ( guard, Expr :: val ( 2 ) , alt) ;
5268
5227
assert_eq ! ( r, PartialValue :: Residual ( expected) ) ;
5269
5228
}
5270
5229
@@ -5273,13 +5232,16 @@ pub mod test {
5273
5232
let guard = Expr :: get_attr ( Expr :: unknown ( Unknown :: new_untyped ( "a" ) ) , "field" . into ( ) ) ;
5274
5233
let cons = Expr :: binary_app ( BinaryOp :: Add , Expr :: val ( 1 ) , Expr :: val ( true ) ) ;
5275
5234
let alt = Expr :: less ( Expr :: val ( "hello" ) , Expr :: val ( "bye" ) ) ;
5276
- let e = Expr :: ite ( guard, cons, alt) ;
5235
+ let e = Expr :: ite ( guard. clone ( ) , cons. clone ( ) , alt. clone ( ) ) ;
5277
5236
5278
5237
let es = Entities :: new ( ) ;
5279
5238
let exts = Extensions :: none ( ) ;
5280
5239
let eval = Evaluator :: new ( empty_request ( ) , & es, & exts) ;
5281
5240
5282
- assert_matches ! ( eval. partial_interpret( & e, & HashMap :: new( ) ) , Err ( _) ) ;
5241
+ assert_eq ! (
5242
+ eval. partial_interpret( & e, & HashMap :: new( ) ) . unwrap( ) ,
5243
+ PartialValue :: Residual ( Expr :: ite( guard, cons, alt) )
5244
+ ) ;
5283
5245
}
5284
5246
5285
5247
// err && res -> err
@@ -5346,27 +5308,27 @@ pub mod test {
5346
5308
fn partial_and_res_true ( ) {
5347
5309
let lhs = Expr :: get_attr ( Expr :: unknown ( Unknown :: new_untyped ( "test" ) ) , "field" . into ( ) ) ;
5348
5310
let rhs = Expr :: binary_app ( BinaryOp :: Eq , Expr :: val ( 2 ) , Expr :: val ( 2 ) ) ;
5349
- let e = Expr :: and ( lhs. clone ( ) , rhs) ;
5311
+ let e = Expr :: and ( lhs. clone ( ) , rhs. clone ( ) ) ;
5350
5312
let es = Entities :: new ( ) ;
5351
5313
let exts = Extensions :: none ( ) ;
5352
5314
let eval = Evaluator :: new ( empty_request ( ) , & es, & exts) ;
5353
5315
5354
5316
let r = eval. partial_interpret ( & e, & HashMap :: new ( ) ) . unwrap ( ) ;
5355
- let expected = Expr :: and ( lhs, Expr :: val ( true ) ) ;
5317
+ let expected = Expr :: and ( lhs, rhs ) ;
5356
5318
assert_eq ! ( r, PartialValue :: Residual ( expected) ) ;
5357
5319
}
5358
5320
5359
5321
#[ test]
5360
5322
fn partial_and_res_false ( ) {
5361
5323
let lhs = Expr :: get_attr ( Expr :: unknown ( Unknown :: new_untyped ( "test" ) ) , "field" . into ( ) ) ;
5362
5324
let rhs = Expr :: binary_app ( BinaryOp :: Eq , Expr :: val ( 2 ) , Expr :: val ( 1 ) ) ;
5363
- let e = Expr :: and ( lhs. clone ( ) , rhs) ;
5325
+ let e = Expr :: and ( lhs. clone ( ) , rhs. clone ( ) ) ;
5364
5326
let es = Entities :: new ( ) ;
5365
5327
let exts = Extensions :: none ( ) ;
5366
5328
let eval = Evaluator :: new ( empty_request ( ) , & es, & exts) ;
5367
5329
5368
5330
let r = eval. partial_interpret ( & e, & HashMap :: new ( ) ) . unwrap ( ) ;
5369
- let expected = Expr :: and ( lhs, Expr :: val ( false ) ) ;
5331
+ let expected = Expr :: and ( lhs, rhs ) ;
5370
5332
assert_eq ! ( r, PartialValue :: Residual ( expected) ) ;
5371
5333
}
5372
5334
@@ -5394,7 +5356,7 @@ pub mod test {
5394
5356
fn partial_and_res_err ( ) {
5395
5357
let lhs = Expr :: get_attr ( Expr :: unknown ( Unknown :: new_untyped ( "test" ) ) , "field" . into ( ) ) ;
5396
5358
let rhs = Expr :: binary_app ( BinaryOp :: Add , Expr :: val ( 1 ) , Expr :: val ( "oops" ) ) ;
5397
- let e = Expr :: and ( lhs, rhs) ;
5359
+ let e = Expr :: and ( lhs, rhs. clone ( ) ) ;
5398
5360
let es = Entities :: new ( ) ;
5399
5361
let exts = Extensions :: none ( ) ;
5400
5362
let eval = Evaluator :: new ( empty_request ( ) , & es, & exts) ;
@@ -5403,10 +5365,7 @@ pub mod test {
5403
5365
5404
5366
let expected = Expr :: and (
5405
5367
Expr :: get_attr ( Expr :: unknown ( Unknown :: new_untyped ( "test" ) ) , "field" . into ( ) ) ,
5406
- Expr :: call_extension_fn (
5407
- "error" . parse ( ) . unwrap ( ) ,
5408
- vec ! [ Expr :: val( "type error: expected long, got string" ) ] ,
5409
- ) ,
5368
+ rhs,
5410
5369
) ;
5411
5370
assert_eq ! ( r, PartialValue :: Residual ( expected) ) ;
5412
5371
}
@@ -5448,27 +5407,27 @@ pub mod test {
5448
5407
fn partial_or_res_true ( ) {
5449
5408
let lhs = Expr :: get_attr ( Expr :: unknown ( Unknown :: new_untyped ( "test" ) ) , "field" . into ( ) ) ;
5450
5409
let rhs = Expr :: binary_app ( BinaryOp :: Eq , Expr :: val ( 2 ) , Expr :: val ( 2 ) ) ;
5451
- let e = Expr :: or ( lhs. clone ( ) , rhs) ;
5410
+ let e = Expr :: or ( lhs. clone ( ) , rhs. clone ( ) ) ;
5452
5411
let es = Entities :: new ( ) ;
5453
5412
let exts = Extensions :: none ( ) ;
5454
5413
let eval = Evaluator :: new ( empty_request ( ) , & es, & exts) ;
5455
5414
5456
5415
let r = eval. partial_interpret ( & e, & HashMap :: new ( ) ) . unwrap ( ) ;
5457
- let expected = Expr :: or ( lhs, Expr :: val ( true ) ) ;
5416
+ let expected = Expr :: or ( lhs, rhs ) ;
5458
5417
assert_eq ! ( r, PartialValue :: Residual ( expected) ) ;
5459
5418
}
5460
5419
5461
5420
#[ test]
5462
5421
fn partial_or_res_false ( ) {
5463
5422
let lhs = Expr :: get_attr ( Expr :: unknown ( Unknown :: new_untyped ( "test" ) ) , "field" . into ( ) ) ;
5464
5423
let rhs = Expr :: binary_app ( BinaryOp :: Eq , Expr :: val ( 2 ) , Expr :: val ( 1 ) ) ;
5465
- let e = Expr :: or ( lhs. clone ( ) , rhs) ;
5424
+ let e = Expr :: or ( lhs. clone ( ) , rhs. clone ( ) ) ;
5466
5425
let es = Entities :: new ( ) ;
5467
5426
let exts = Extensions :: none ( ) ;
5468
5427
let eval = Evaluator :: new ( empty_request ( ) , & es, & exts) ;
5469
5428
5470
5429
let r = eval. partial_interpret ( & e, & HashMap :: new ( ) ) . unwrap ( ) ;
5471
- let expected = Expr :: or ( lhs, Expr :: val ( false ) ) ;
5430
+ let expected = Expr :: or ( lhs, rhs ) ;
5472
5431
assert_eq ! ( r, PartialValue :: Residual ( expected) ) ;
5473
5432
}
5474
5433
@@ -5496,7 +5455,7 @@ pub mod test {
5496
5455
fn partial_or_res_err ( ) {
5497
5456
let lhs = Expr :: get_attr ( Expr :: unknown ( Unknown :: new_untyped ( "test" ) ) , "field" . into ( ) ) ;
5498
5457
let rhs = Expr :: binary_app ( BinaryOp :: Add , Expr :: val ( 1 ) , Expr :: val ( "oops" ) ) ;
5499
- let e = Expr :: or ( lhs, rhs) ;
5458
+ let e = Expr :: or ( lhs, rhs. clone ( ) ) ;
5500
5459
let es = Entities :: new ( ) ;
5501
5460
let exts = Extensions :: none ( ) ;
5502
5461
let eval = Evaluator :: new ( empty_request ( ) , & es, & exts) ;
@@ -5505,10 +5464,7 @@ pub mod test {
5505
5464
5506
5465
let expected = Expr :: or (
5507
5466
Expr :: get_attr ( Expr :: unknown ( Unknown :: new_untyped ( "test" ) ) , "field" . into ( ) ) ,
5508
- Expr :: call_extension_fn (
5509
- "error" . parse ( ) . unwrap ( ) ,
5510
- vec ! [ Expr :: val( "type error: expected long, got string" ) ] ,
5511
- ) ,
5467
+ rhs,
5512
5468
) ;
5513
5469
assert_eq ! ( r, PartialValue :: Residual ( expected) ) ;
5514
5470
}
0 commit comments