1
1
use crate :: BigNum ;
2
2
use serde:: { Deserialize , Serialize } ;
3
3
use serde_json:: { value:: Value as SerdeValue , Number } ;
4
- use std:: { convert:: TryFrom , fmt, ops:: Div , str:: FromStr } ;
4
+ use std:: { convert:: TryFrom , fmt, ops:: { Div , Mul , Rem , Add , Sub } , str:: FromStr } ;
5
5
6
6
pub type Map = serde_json:: value:: Map < String , SerdeValue > ;
7
7
@@ -83,8 +83,13 @@ impl TryFrom<SerdeValue> for Value {
83
83
#[ serde( rename_all = "camelCase" ) ]
84
84
// TODO: https://github.com/AdExNetwork/adex-validator-stack-rust/issues/296
85
85
pub enum Function {
86
- /// Math `div`
87
86
Div ( Box < Rule > , Box < Rule > ) ,
87
+ Mul ( Box < Rule > , Box < Rule > ) ,
88
+ Mod ( Box < Rule > , Box < Rule > ) ,
89
+ Add ( Box < Rule > , Box < Rule > ) ,
90
+ Sub ( Box < Rule > , Box < Rule > ) ,
91
+ Max ( Box < Rule > , Box < Rule > ) ,
92
+ Min ( Box < Rule > , Box < Rule > ) ,
88
93
If ( Box < Rule > , Box < Rule > ) ,
89
94
And ( Box < Rule > , Box < Rule > ) ,
90
95
Intersects ( Box < Rule > , Box < Rule > ) ,
@@ -217,6 +222,144 @@ fn eval(input: &Input, output: &mut Output, rule: &Rule) -> Result<Option<Value>
217
222
218
223
Some ( value)
219
224
}
225
+ Function :: Mul ( first_rule, second_rule) => {
226
+ let first_eval = first_rule. eval ( input, output) ?. ok_or ( Error :: TypeError ) ?;
227
+ let second_eval = second_rule. eval ( input, output) ?. ok_or ( Error :: TypeError ) ?;
228
+
229
+ let value = match ( first_eval, second_eval) {
230
+ ( Value :: BigNum ( bignum) , rhs_value) => {
231
+ let rhs_bignum = BigNum :: try_from ( rhs_value) ?;
232
+
233
+ Value :: BigNum ( bignum. mul ( rhs_bignum) )
234
+ } ,
235
+ ( lhs_value, Value :: BigNum ( rhs_bignum) ) => {
236
+ let lhs_bignum = BigNum :: try_from ( lhs_value) ?;
237
+
238
+ Value :: BigNum ( lhs_bignum. mul ( rhs_bignum) )
239
+ }
240
+ ( Value :: Number ( lhs) , Value :: Number ( rhs) ) => {
241
+ Value :: Number ( math_operator ( lhs, rhs, MathOperator :: Multiplication ) ?)
242
+ }
243
+ _ => return Err ( Error :: TypeError ) ,
244
+ } ;
245
+
246
+ Some ( value)
247
+ }
248
+ Function :: Mod ( first_rule, second_rule) => {
249
+ let first_eval = first_rule. eval ( input, output) ?. ok_or ( Error :: TypeError ) ?;
250
+ let second_eval = second_rule. eval ( input, output) ?. ok_or ( Error :: TypeError ) ?;
251
+
252
+ let value = match ( first_eval, second_eval) {
253
+ ( Value :: BigNum ( bignum) , rhs_value) => {
254
+ let rhs_bignum = BigNum :: try_from ( rhs_value) ?;
255
+
256
+ Value :: BigNum ( bignum. rem ( rhs_bignum) )
257
+ } ,
258
+ ( lhs_value, Value :: BigNum ( rhs_bignum) ) => {
259
+ let lhs_bignum = BigNum :: try_from ( lhs_value) ?;
260
+
261
+ Value :: BigNum ( lhs_bignum. rem ( rhs_bignum) )
262
+ }
263
+ ( Value :: Number ( lhs) , Value :: Number ( rhs) ) => {
264
+ Value :: Number ( math_operator ( lhs, rhs, MathOperator :: Modulus ) ?)
265
+ }
266
+ _ => return Err ( Error :: TypeError ) ,
267
+ } ;
268
+
269
+ Some ( value)
270
+ }
271
+ Function :: Add ( first_rule, second_rule) => {
272
+ let first_eval = first_rule. eval ( input, output) ?. ok_or ( Error :: TypeError ) ?;
273
+ let second_eval = second_rule. eval ( input, output) ?. ok_or ( Error :: TypeError ) ?;
274
+
275
+ let value = match ( first_eval, second_eval) {
276
+ ( Value :: BigNum ( bignum) , rhs_value) => {
277
+ let rhs_bignum = BigNum :: try_from ( rhs_value) ?;
278
+
279
+ Value :: BigNum ( bignum. add ( rhs_bignum) )
280
+ } ,
281
+ ( lhs_value, Value :: BigNum ( rhs_bignum) ) => {
282
+ let lhs_bignum = BigNum :: try_from ( lhs_value) ?;
283
+
284
+ Value :: BigNum ( lhs_bignum. add ( rhs_bignum) )
285
+ }
286
+ ( Value :: Number ( lhs) , Value :: Number ( rhs) ) => {
287
+ Value :: Number ( math_operator ( lhs, rhs, MathOperator :: Addition ) ?)
288
+ }
289
+ _ => return Err ( Error :: TypeError ) ,
290
+ } ;
291
+
292
+ Some ( value)
293
+ }
294
+ Function :: Sub ( first_rule, second_rule) => {
295
+ let first_eval = first_rule. eval ( input, output) ?. ok_or ( Error :: TypeError ) ?;
296
+ let second_eval = second_rule. eval ( input, output) ?. ok_or ( Error :: TypeError ) ?;
297
+
298
+ let value = match ( first_eval, second_eval) {
299
+ ( Value :: BigNum ( bignum) , rhs_value) => {
300
+ let rhs_bignum = BigNum :: try_from ( rhs_value) ?;
301
+
302
+ Value :: BigNum ( bignum. sub ( rhs_bignum) )
303
+ } ,
304
+ ( lhs_value, Value :: BigNum ( rhs_bignum) ) => {
305
+ let lhs_bignum = BigNum :: try_from ( lhs_value) ?;
306
+
307
+ Value :: BigNum ( lhs_bignum. sub ( rhs_bignum) )
308
+ }
309
+ ( Value :: Number ( lhs) , Value :: Number ( rhs) ) => {
310
+ Value :: Number ( math_operator ( lhs, rhs, MathOperator :: Subtraction ) ?)
311
+ }
312
+ _ => return Err ( Error :: TypeError ) ,
313
+ } ;
314
+
315
+ Some ( value)
316
+ }
317
+ Function :: Max ( first_rule, second_rule) => {
318
+ let first_eval = first_rule. eval ( input, output) ?. ok_or ( Error :: TypeError ) ?;
319
+ let second_eval = second_rule. eval ( input, output) ?. ok_or ( Error :: TypeError ) ?;
320
+
321
+ let value = match ( first_eval, second_eval) {
322
+ ( Value :: BigNum ( bignum) , rhs_value) => {
323
+ let rhs_bignum = BigNum :: try_from ( rhs_value) ?;
324
+
325
+ Value :: BigNum ( bignum. max ( rhs_bignum) )
326
+ } ,
327
+ ( lhs_value, Value :: BigNum ( rhs_bignum) ) => {
328
+ let lhs_bignum = BigNum :: try_from ( lhs_value) ?;
329
+
330
+ Value :: BigNum ( lhs_bignum. max ( rhs_bignum) )
331
+ }
332
+ ( Value :: Number ( lhs) , Value :: Number ( rhs) ) => {
333
+ Value :: Number ( math_operator ( lhs, rhs, MathOperator :: Max ) ?)
334
+ }
335
+ _ => return Err ( Error :: TypeError ) ,
336
+ } ;
337
+
338
+ Some ( value)
339
+ }
340
+ Function :: Min ( first_rule, second_rule) => {
341
+ let first_eval = first_rule. eval ( input, output) ?. ok_or ( Error :: TypeError ) ?;
342
+ let second_eval = second_rule. eval ( input, output) ?. ok_or ( Error :: TypeError ) ?;
343
+
344
+ let value = match ( first_eval, second_eval) {
345
+ ( Value :: BigNum ( bignum) , rhs_value) => {
346
+ let rhs_bignum = BigNum :: try_from ( rhs_value) ?;
347
+
348
+ Value :: BigNum ( bignum. min ( rhs_bignum) )
349
+ } ,
350
+ ( lhs_value, Value :: BigNum ( rhs_bignum) ) => {
351
+ let lhs_bignum = BigNum :: try_from ( lhs_value) ?;
352
+
353
+ Value :: BigNum ( lhs_bignum. min ( rhs_bignum) )
354
+ }
355
+ ( Value :: Number ( lhs) , Value :: Number ( rhs) ) => {
356
+ Value :: Number ( math_operator ( lhs, rhs, MathOperator :: Min ) ?)
357
+ }
358
+ _ => return Err ( Error :: TypeError ) ,
359
+ } ;
360
+
361
+ Some ( value)
362
+ }
220
363
Function :: If ( first_rule, second_rule) => {
221
364
let eval_if = eval ( input, output, first_rule) ?
222
365
. ok_or ( Error :: TypeError ) ?
@@ -303,15 +446,45 @@ fn eval(input: &Input, output: &mut Output, rule: &Rule) -> Result<Option<Value>
303
446
}
304
447
305
448
enum MathOperator {
306
- Division
449
+ Division ,
450
+ Multiplication ,
451
+ Modulus ,
452
+ Addition ,
453
+ Subtraction ,
454
+ Max ,
455
+ Min ,
307
456
}
308
457
309
458
fn handle_u64 ( lhs : u64 , rhs : u64 , ops : MathOperator ) -> Result < Number , Error > {
310
459
match ops {
311
460
MathOperator :: Division => {
312
461
let divided = lhs. checked_div ( rhs) . ok_or ( Error :: TypeError ) ?;
313
462
Ok ( divided. into ( ) )
314
- }
463
+ } ,
464
+ MathOperator :: Multiplication => {
465
+ let multiplied = lhs. checked_mul ( rhs) . ok_or ( Error :: TypeError ) ?;
466
+ Ok ( multiplied. into ( ) )
467
+ } ,
468
+ MathOperator :: Modulus => {
469
+ let modulus = lhs. checked_rem ( rhs) . ok_or ( Error :: TypeError ) ?;
470
+ Ok ( modulus. into ( ) )
471
+ } ,
472
+ MathOperator :: Addition => {
473
+ let added = lhs. checked_add ( rhs) . ok_or ( Error :: TypeError ) ?;
474
+ Ok ( added. into ( ) )
475
+ } ,
476
+ MathOperator :: Subtraction => {
477
+ let subtracted = lhs. checked_sub ( rhs) . ok_or ( Error :: TypeError ) ?;
478
+ Ok ( subtracted. into ( ) )
479
+ } ,
480
+ MathOperator :: Max => {
481
+ let max = lhs. max ( rhs) ;
482
+ Ok ( max. into ( ) )
483
+ } ,
484
+ MathOperator :: Min => {
485
+ let min = lhs. min ( rhs) ;
486
+ Ok ( min. into ( ) )
487
+ } ,
315
488
}
316
489
}
317
490
@@ -320,7 +493,31 @@ fn handle_i64(lhs: i64, rhs: i64, ops: MathOperator) -> Result<Number, Error> {
320
493
MathOperator :: Division => {
321
494
let divided = lhs. checked_div ( rhs) . ok_or ( Error :: TypeError ) ?;
322
495
Ok ( divided. into ( ) )
323
- }
496
+ } ,
497
+ MathOperator :: Multiplication => {
498
+ let multiplied = lhs. checked_mul ( rhs) . ok_or ( Error :: TypeError ) ?;
499
+ Ok ( multiplied. into ( ) )
500
+ } ,
501
+ MathOperator :: Modulus => {
502
+ let modulus = lhs. checked_rem ( rhs) . ok_or ( Error :: TypeError ) ?;
503
+ Ok ( modulus. into ( ) )
504
+ } ,
505
+ MathOperator :: Addition => {
506
+ let added = lhs. checked_add ( rhs) . ok_or ( Error :: TypeError ) ?;
507
+ Ok ( added. into ( ) )
508
+ } ,
509
+ MathOperator :: Subtraction => {
510
+ let subtracted = lhs. checked_sub ( rhs) . ok_or ( Error :: TypeError ) ?;
511
+ Ok ( subtracted. into ( ) )
512
+ } ,
513
+ MathOperator :: Max => {
514
+ let max = lhs. max ( rhs) ;
515
+ Ok ( max. into ( ) )
516
+ } ,
517
+ MathOperator :: Min => {
518
+ let min = lhs. min ( rhs) ;
519
+ Ok ( min. into ( ) )
520
+ } ,
324
521
}
325
522
}
326
523
@@ -329,7 +526,31 @@ fn handle_f64(lhs: f64, rhs: f64, ops:MathOperator) -> Result<Number, Error> {
329
526
MathOperator :: Division => {
330
527
let divided = lhs. div ( rhs) ;
331
528
Ok ( Number :: from_f64 ( divided) . ok_or ( Error :: TypeError ) ?)
332
- }
529
+ } ,
530
+ MathOperator :: Multiplication => {
531
+ let multiplied = lhs. mul ( rhs) ;
532
+ Ok ( Number :: from_f64 ( multiplied) . ok_or ( Error :: TypeError ) ?)
533
+ } ,
534
+ MathOperator :: Modulus => {
535
+ let modulus = lhs. rem ( rhs) ;
536
+ Ok ( Number :: from_f64 ( modulus) . ok_or ( Error :: TypeError ) ?)
537
+ } ,
538
+ MathOperator :: Addition => {
539
+ let added = lhs. add ( rhs) ;
540
+ Ok ( Number :: from_f64 ( added) . ok_or ( Error :: TypeError ) ?)
541
+ } ,
542
+ MathOperator :: Subtraction => {
543
+ let subtracted = lhs. sub ( rhs) ;
544
+ Ok ( Number :: from_f64 ( subtracted) . ok_or ( Error :: TypeError ) ?)
545
+ } ,
546
+ MathOperator :: Max => {
547
+ let max = lhs. max ( rhs) ;
548
+ Ok ( Number :: from_f64 ( max) . ok_or ( Error :: TypeError ) ?)
549
+ } ,
550
+ MathOperator :: Min => {
551
+ let min = lhs. min ( rhs) ;
552
+ Ok ( Number :: from_f64 ( min) . ok_or ( Error :: TypeError ) ?)
553
+ } ,
333
554
}
334
555
}
335
556
0 commit comments