-- Copyright (c) 2016-present, Facebook, Inc.
-- All rights reserved.
--
-- This source code is licensed under the BSD-style license found in the
-- LICENSE file in the root directory of this source tree.


{-# LANGUAGE GADTs #-}
{-# LANGUAGE LambdaCase #-}
{-# LANGUAGE OverloadedStrings #-}
module Duckling.AmountOfMoney.HE.Rules
  ( rules
  ) where

import Data.Maybe
import Data.String
import Prelude

import Duckling.AmountOfMoney.Helpers
import Duckling.AmountOfMoney.Types
  ( Currency(..)
  , AmountOfMoneyData(..)
  )
import Duckling.Dimensions.Types
import Duckling.Numeral.Helpers
  ( isPositive
  )
import Duckling.Numeral.Types (NumeralData(..))
import Duckling.Types
import qualified Duckling.AmountOfMoney.Types as TAmountOfMoney
import qualified Duckling.Numeral.Types as TNumeral

ruleUnitAmount :: Rule
ruleUnitAmount :: Rule
ruleUnitAmount = Rule :: Text -> Pattern -> Production -> Rule
Rule
  { name :: Text
name = Text
"<unit> <amount>"
  , pattern :: Pattern
pattern =
    [ Predicate -> PatternItem
Predicate Predicate
isCurrencyOnly
    , Predicate -> PatternItem
Predicate Predicate
isPositive
    ]
  , prod :: Production
prod = \case
      (Token Dimension a
AmountOfMoney AmountOfMoneyData{TAmountOfMoney.currency = c}:
       Token Dimension a
Numeral NumeralData{TNumeral.value = v}:
       [Token]
_) -> Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Token)
-> (AmountOfMoneyData -> AmountOfMoneyData)
-> AmountOfMoneyData
-> Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> AmountOfMoneyData -> AmountOfMoneyData
withValue Double
v (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$ Currency -> AmountOfMoneyData
currencyOnly Currency
c
      [Token]
_ -> Maybe Token
forall a. Maybe a
Nothing
  }

ruleOneShekel :: Rule
ruleOneShekel :: Rule
ruleOneShekel = Rule :: Text -> Pattern -> Production -> Rule
Rule
  { name :: Text
name    = Text
"שקל"
  , pattern :: Pattern
pattern = [String -> PatternItem
regex String
"שקל( אחד| בודד)?"]
  , prod :: Production
prod    = \[Token]
_ -> Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$ Double -> AmountOfMoneyData -> AmountOfMoneyData
withValue Double
1 (AmountOfMoneyData -> AmountOfMoneyData)
-> AmountOfMoneyData -> AmountOfMoneyData
forall a b. (a -> b) -> a -> b
$ Currency -> AmountOfMoneyData
currencyOnly Currency
ILS
  }
ruleTwoShekel :: Rule
ruleTwoShekel :: Rule
ruleTwoShekel = Rule :: Text -> Pattern -> Production -> Rule
Rule
  { name :: Text
name    = Text
"שנקל"
  , pattern :: Pattern
pattern = [String -> PatternItem
regex String
"שנקל"]
  , prod :: Production
prod    = \[Token]
_ -> Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$ Double -> AmountOfMoneyData -> AmountOfMoneyData
withValue Double
2 (AmountOfMoneyData -> AmountOfMoneyData)
-> AmountOfMoneyData -> AmountOfMoneyData
forall a b. (a -> b) -> a -> b
$ Currency -> AmountOfMoneyData
currencyOnly Currency
ILS
  }
ruleOneAgura :: Rule
ruleOneAgura :: Rule
ruleOneAgura = Rule :: Text -> Pattern -> Production -> Rule
Rule
  { name :: Text
name    = Text
"oneAgura"
  , pattern :: Pattern
pattern = [String -> PatternItem
regex String
"אגורה( אחת| בודדת)?"]
  , prod :: Production
prod    = \[Token]
_ -> Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$ Double -> AmountOfMoneyData -> AmountOfMoneyData
withValue Double
0.01 (AmountOfMoneyData -> AmountOfMoneyData)
-> AmountOfMoneyData -> AmountOfMoneyData
forall a b. (a -> b) -> a -> b
$
                    Currency -> AmountOfMoneyData
currencyOnly Currency
ILS
  }
ruleShekel :: Rule
ruleShekel :: Rule
ruleShekel = Rule :: Text -> Pattern -> Production -> Rule
Rule
  { name :: Text
name    = Text
"שקל"
  , pattern :: Pattern
pattern = [String -> PatternItem
regex String
"שקל(ים)?|ש״?ח"]
  , prod :: Production
prod    = \[Token]
_ -> Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$ Currency -> AmountOfMoneyData
currencyOnly Currency
ILS
  }

ruleThousandShekel :: Rule
ruleThousandShekel :: Rule
ruleThousandShekel = Rule :: Text -> Pattern -> Production -> Rule
Rule
    { name :: Text
name = Text
"אש״ח"
    , pattern :: Pattern
pattern =
      [ Predicate -> PatternItem
Predicate Predicate
isPositive
      , String -> PatternItem
regex String
"אש״?ח"
      ]
    , prod :: Production
prod = \case
        (Token Dimension a
Numeral NumeralData{TNumeral.value = v}:
         [Token]
_) -> Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$ Double -> AmountOfMoneyData -> AmountOfMoneyData
withValue (Double
vDouble -> Double -> Double
forall a. Num a => a -> a -> a
*Double
1000) (AmountOfMoneyData -> AmountOfMoneyData)
-> AmountOfMoneyData -> AmountOfMoneyData
forall a b. (a -> b) -> a -> b
$
               Currency -> AmountOfMoneyData
currencyOnly Currency
ILS
        [Token]
_ -> Maybe Token
forall a. Maybe a
Nothing
    }

ruleMillionShekel :: Rule
ruleMillionShekel :: Rule
ruleMillionShekel = Rule :: Text -> Pattern -> Production -> Rule
Rule
    { name :: Text
name = Text
"מש״ח"
    , pattern :: Pattern
pattern =
      [ Predicate -> PatternItem
Predicate Predicate
isPositive
      , String -> PatternItem
regex String
"מש״?ח"
      ]
    , prod :: Production
prod = \case
        (Token Dimension a
Numeral NumeralData{TNumeral.value = v}:
         [Token]
_) -> Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$ Double -> AmountOfMoneyData -> AmountOfMoneyData
withValue (Double
vDouble -> Double -> Double
forall a. Num a => a -> a -> a
*Double
1000000) (AmountOfMoneyData -> AmountOfMoneyData)
-> AmountOfMoneyData -> AmountOfMoneyData
forall a b. (a -> b) -> a -> b
$
               Currency -> AmountOfMoneyData
currencyOnly Currency
ILS
        [Token]
_ -> Maybe Token
forall a. Maybe a
Nothing
    }
ruleAgura :: Rule
ruleAgura :: Rule
ruleAgura = Rule :: Text -> Pattern -> Production -> Rule
Rule
    { name :: Text
name = Text
"multiple agura"
    , pattern :: Pattern
pattern =
      [ Predicate -> PatternItem
Predicate Predicate
isPositive
      , String -> PatternItem
regex String
"אגורות"
      ]
    , prod :: Production
prod = \case
        (Token Dimension a
Numeral NumeralData{TNumeral.value = v}:
         [Token]
_) -> Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$ Double -> AmountOfMoneyData -> AmountOfMoneyData
withValue (Double
vDouble -> Double -> Double
forall a. Num a => a -> a -> a
*Double
0.01) (AmountOfMoneyData -> AmountOfMoneyData)
-> AmountOfMoneyData -> AmountOfMoneyData
forall a b. (a -> b) -> a -> b
$
               Currency -> AmountOfMoneyData
currencyOnly Currency
ILS
        [Token]
_ -> Maybe Token
forall a. Maybe a
Nothing
    }

ruleIntersect :: Rule
ruleIntersect :: Rule
ruleIntersect = Rule :: Text -> Pattern -> Production -> Rule
Rule
  { name :: Text
name = Text
"intersect"
  , pattern :: Pattern
pattern =
    [ Predicate -> PatternItem
Predicate Predicate
isWithoutCents
    , String -> PatternItem
regex String
"ו"
    , Predicate -> PatternItem
Predicate Predicate
isPositive
    ]
  , prod :: Production
prod = \case
      (Token Dimension a
AmountOfMoney AmountOfMoneyData{TAmountOfMoney.value = Just v,
                  TAmountOfMoney.currency = c}:
       Token
_:
       Token Dimension a
Numeral NumeralData { TNumeral.value = p }:
       [Token]
_) -> Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$ Double -> AmountOfMoneyData -> AmountOfMoneyData
withValue (Double
v Double -> Double -> Double
forall a. Num a => a -> a -> a
+ Double
p) (AmountOfMoneyData -> AmountOfMoneyData)
-> AmountOfMoneyData -> AmountOfMoneyData
forall a b. (a -> b) -> a -> b
$ Currency -> AmountOfMoneyData
currencyOnly Currency
c
      [Token]
_ -> Maybe Token
forall a. Maybe a
Nothing
  }

ruleIntersectAndXCents :: Rule
ruleIntersectAndXCents :: Rule
ruleIntersectAndXCents = Rule :: Text -> Pattern -> Production -> Rule
Rule
  { name :: Text
name = Text
"intersect (and X cents)"
  , pattern :: Pattern
pattern =
    [ Predicate -> PatternItem
Predicate Predicate
isWithoutCents
    , String -> PatternItem
regex String
"ו"
    , Predicate -> PatternItem
Predicate Predicate
isCents
    ]
  , prod :: Production
prod = \case
      (Token Dimension a
AmountOfMoney a
fd :
       Token
_ :
       Token Dimension a
AmountOfMoney AmountOfMoneyData { TAmountOfMoney.value = Just c }:
       [Token]
_) -> Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$ Double -> AmountOfMoneyData -> AmountOfMoneyData
withCents Double
c a
AmountOfMoneyData
fd
      [Token]
_ -> Maybe Token
forall a. Maybe a
Nothing
  }

rulePounds :: Rule
rulePounds :: Rule
rulePounds = Rule :: Text -> Pattern -> Production -> Rule
Rule
  { name :: Text
name = Text
"£"
  , pattern :: Pattern
pattern =
    [ String -> PatternItem
regex String
"פאונד(ים)?"
    ]
  , prod :: Production
prod = \[Token]
_ -> Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$ Currency -> AmountOfMoneyData
currencyOnly Currency
Pound
  }

ruleDollar :: Rule
ruleDollar :: Rule
ruleDollar = Rule :: Text -> Pattern -> Production -> Rule
Rule
  { name :: Text
name    = Text
"$"
  , pattern :: Pattern
pattern =
    [ String -> PatternItem
regex String
"דולר(ים)?"
    ]
  , prod :: Production
prod    = \[Token]
_ -> Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$ Currency -> AmountOfMoneyData
currencyOnly Currency
Dollar
  }

ruleCent :: Rule
ruleCent :: Rule
ruleCent = Rule :: Text -> Pattern -> Production -> Rule
Rule
  { name :: Text
name = Text
"cent"
  , pattern :: Pattern
pattern =
      [ String -> PatternItem
regex String
"סנט(ים)?"
      ]
  , prod :: Production
prod = \[Token]
_ -> Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$ Currency -> AmountOfMoneyData
currencyOnly Currency
Cent
  }

ruleEUR :: Rule
ruleEUR :: Rule
ruleEUR = Rule :: Text -> Pattern -> Production -> Rule
Rule
  { name :: Text
name    = Text
"€"
  , pattern :: Pattern
pattern =
    [ String -> PatternItem
regex String
"אירו|יורו"
    ]
  , prod :: Production
prod    = \[Token]
_ -> Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$ Currency -> AmountOfMoneyData
currencyOnly Currency
EUR
  }
ruleOneGBP :: Rule
ruleOneGBP :: Rule
ruleOneGBP = Rule :: Text -> Pattern -> Production -> Rule
Rule
  { name :: Text
name = Text
"OneGBP"
  , pattern :: Pattern
pattern =
    [ String -> PatternItem
regex String
"לירה שטרלינג"
    ]
  , prod :: Production
prod = \[Token]
_ -> Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$ Double -> AmountOfMoneyData -> AmountOfMoneyData
withValue Double
1 (AmountOfMoneyData -> AmountOfMoneyData)
-> AmountOfMoneyData -> AmountOfMoneyData
forall a b. (a -> b) -> a -> b
$ Currency -> AmountOfMoneyData
currencyOnly Currency
GBP
  }
ruleGBP :: Rule
ruleGBP :: Rule
ruleGBP = Rule :: Text -> Pattern -> Production -> Rule
Rule
  { name :: Text
name = Text
"OneGBP"
  , pattern :: Pattern
pattern =
    [ String -> PatternItem
regex String
"לירות שטרלינג"
    ]
  , prod :: Production
prod = \[Token]
_ -> Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$ Currency -> AmountOfMoneyData
currencyOnly Currency
GBP
  }

rulePrecision :: Rule
rulePrecision :: Rule
rulePrecision = Rule :: Text -> Pattern -> Production -> Rule
Rule
  { name :: Text
name = Text
"about|exactly <amount-of-money>"
  , pattern :: Pattern
pattern =
      [ String -> PatternItem
regex String
"בערך|בדיוק|קרוב ל"
      , Predicate -> PatternItem
Predicate Predicate
isMoneyWithValue
      ]
  , prod :: Production
prod = \case
      (Token
_:
       Token
token:
       [Token]
_) -> Token -> Maybe Token
forall a. a -> Maybe a
Just Token
token
      [Token]
_ -> Maybe Token
forall a. Maybe a
Nothing
  }

ruleIntervalBetweenNumeral :: Rule
ruleIntervalBetweenNumeral :: Rule
ruleIntervalBetweenNumeral = Rule :: Text -> Pattern -> Production -> Rule
Rule
  { name :: Text
name = Text
"between|from <numeral> to|and <amount-of-money>"
  , pattern :: Pattern
pattern =
      [ String -> PatternItem
regex String
"מ?|בין "
      , Predicate -> PatternItem
Predicate Predicate
isPositive
      , String -> PatternItem
regex String
"עד |ל"
      , Predicate -> PatternItem
Predicate Predicate
isSimpleAmountOfMoney
      ]
  , prod :: Production
prod = \case
      (Token
_:
       Token Dimension a
Numeral NumeralData { TNumeral.value = from }:
       Token
_:
       Token Dimension a
AmountOfMoney AmountOfMoneyData { TAmountOfMoney.value = Just to,
                  TAmountOfMoney.currency = c }:
       [Token]
_) | Double
from Double -> Double -> Bool
forall a. Ord a => a -> a -> Bool
< Double
to ->
        Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Token)
-> (AmountOfMoneyData -> AmountOfMoneyData)
-> AmountOfMoneyData
-> Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Double, Double) -> AmountOfMoneyData -> AmountOfMoneyData
withInterval (Double
from, Double
to) (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$ Currency -> AmountOfMoneyData
currencyOnly Currency
c
      [Token]
_ -> Maybe Token
forall a. Maybe a
Nothing
  }

ruleIntervalBetween :: Rule
ruleIntervalBetween :: Rule
ruleIntervalBetween = Rule :: Text -> Pattern -> Production -> Rule
Rule
  { name :: Text
name = Text
"between|from <amount-of-money> to|and <amount-of-money>"
  , pattern :: Pattern
pattern =
      [ String -> PatternItem
regex String
"מ?|בין "
      , Predicate -> PatternItem
Predicate Predicate
isSimpleAmountOfMoney
      , String -> PatternItem
regex String
"עד |ל"
      , Predicate -> PatternItem
Predicate Predicate
isSimpleAmountOfMoney
      ]
  , prod :: Production
prod = \case
      (Token
_:
       Token Dimension a
AmountOfMoney AmountOfMoneyData { TAmountOfMoney.value = Just from,
                  TAmountOfMoney.currency = c1 }:
       Token
_:
       Token Dimension a
AmountOfMoney AmountOfMoneyData { TAmountOfMoney.value = Just to,
                  TAmountOfMoney.currency = c2 }:
       [Token]
_) | Double
from Double -> Double -> Bool
forall a. Ord a => a -> a -> Bool
< Double
to Bool -> Bool -> Bool
&& Currency
c1 Currency -> Currency -> Bool
forall a. Eq a => a -> a -> Bool
== Currency
c2 ->
            Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Token)
-> (AmountOfMoneyData -> AmountOfMoneyData)
-> AmountOfMoneyData
-> Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Double, Double) -> AmountOfMoneyData -> AmountOfMoneyData
withInterval (Double
from, Double
to) (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$
              Currency -> AmountOfMoneyData
currencyOnly Currency
c1
      [Token]
_ -> Maybe Token
forall a. Maybe a
Nothing
  }

ruleIntervalNumeralDash :: Rule
ruleIntervalNumeralDash :: Rule
ruleIntervalNumeralDash = Rule :: Text -> Pattern -> Production -> Rule
Rule
  { name :: Text
name = Text
"<numeral> - <amount-of-money>"
  , pattern :: Pattern
pattern =
    [ Predicate -> PatternItem
Predicate Predicate
isPositive
    , String -> PatternItem
regex String
"-"
    , Predicate -> PatternItem
Predicate Predicate
isSimpleAmountOfMoney
    ]
  , prod :: Production
prod = \case
      (Token Dimension a
Numeral NumeralData { TNumeral.value = from }:
       Token
_:
       Token Dimension a
AmountOfMoney AmountOfMoneyData { TAmountOfMoney.value = Just to,
                  TAmountOfMoney.currency = c }:
       [Token]
_) | Double
from Double -> Double -> Bool
forall a. Ord a => a -> a -> Bool
< Double
to -> Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Token)
-> (AmountOfMoneyData -> AmountOfMoneyData)
-> AmountOfMoneyData
-> Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Double, Double) -> AmountOfMoneyData -> AmountOfMoneyData
withInterval (Double
from, Double
to) (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$
            Currency -> AmountOfMoneyData
currencyOnly Currency
c
      [Token]
_ -> Maybe Token
forall a. Maybe a
Nothing
  }

ruleIntervalDash :: Rule
ruleIntervalDash :: Rule
ruleIntervalDash = Rule :: Text -> Pattern -> Production -> Rule
Rule
  { name :: Text
name = Text
"<amount-of-money> - <amount-of-money>"
  , pattern :: Pattern
pattern =
      [ Predicate -> PatternItem
Predicate Predicate
isSimpleAmountOfMoney
      , String -> PatternItem
regex String
"-"
      , Predicate -> PatternItem
Predicate Predicate
isSimpleAmountOfMoney
      ]
  , prod :: Production
prod = \case
      (Token Dimension a
AmountOfMoney AmountOfMoneyData { TAmountOfMoney.value = Just from,
                  TAmountOfMoney.currency = c1 }:
       Token
_:
       Token Dimension a
AmountOfMoney AmountOfMoneyData { TAmountOfMoney.value = Just to,
                  TAmountOfMoney.currency = c2 }:
       [Token]
_) | Double
from Double -> Double -> Bool
forall a. Ord a => a -> a -> Bool
< Double
to Bool -> Bool -> Bool
&& Currency
c1 Currency -> Currency -> Bool
forall a. Eq a => a -> a -> Bool
== Currency
c2 ->
            Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Token)
-> (AmountOfMoneyData -> AmountOfMoneyData)
-> AmountOfMoneyData
-> Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Double, Double) -> AmountOfMoneyData -> AmountOfMoneyData
withInterval (Double
from, Double
to) (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$
              Currency -> AmountOfMoneyData
currencyOnly Currency
c1
      [Token]
_ -> Maybe Token
forall a. Maybe a
Nothing
  }

ruleIntervalMax :: Rule
ruleIntervalMax :: Rule
ruleIntervalMax = Rule :: Text -> Pattern -> Production -> Rule
Rule
  { name :: Text
name = Text
"under/less/lower/no more than <amount-of-money>"
  , pattern :: Pattern
pattern =
      [ String -> PatternItem
regex String
"פחות מ|עד|לא יותר מ|מתחת ל?|לא מעל"
      , Predicate -> PatternItem
Predicate Predicate
isSimpleAmountOfMoney
      ]
  , prod :: Production
prod = \case
      (Token
_:
       Token Dimension a
AmountOfMoney AmountOfMoneyData { TAmountOfMoney.value = Just to,
                  TAmountOfMoney.currency = c }:
       [Token]
_) -> Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Token)
-> (AmountOfMoneyData -> AmountOfMoneyData)
-> AmountOfMoneyData
-> Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> AmountOfMoneyData -> AmountOfMoneyData
withMax Double
to (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$ Currency -> AmountOfMoneyData
currencyOnly Currency
c
      [Token]
_ -> Maybe Token
forall a. Maybe a
Nothing
  }

ruleIntervalMin :: Rule
ruleIntervalMin :: Rule
ruleIntervalMin = Rule :: Text -> Pattern -> Production -> Rule
Rule
  { name :: Text
name = Text
"over/above/at least/more than <amount-of-money>"
  , pattern :: Pattern
pattern =
      [ String -> PatternItem
regex String
"יותר מ|מעל|מ|לא פחות מ|לא מתחת ל"
      , Predicate -> PatternItem
Predicate Predicate
isSimpleAmountOfMoney
      ]
  , prod :: Production
prod = \case
      (Token
_:
       Token Dimension a
AmountOfMoney AmountOfMoneyData { TAmountOfMoney.value = Just to,
                  TAmountOfMoney.currency = c }:
       [Token]
_) -> Token -> Maybe Token
forall a. a -> Maybe a
Just (Token -> Maybe Token)
-> (AmountOfMoneyData -> Token) -> AmountOfMoneyData -> Maybe Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Dimension AmountOfMoneyData -> AmountOfMoneyData -> Token
forall a.
(Resolve a, Eq a, Hashable a, Show a, NFData a) =>
Dimension a -> a -> Token
Token Dimension AmountOfMoneyData
AmountOfMoney (AmountOfMoneyData -> Token)
-> (AmountOfMoneyData -> AmountOfMoneyData)
-> AmountOfMoneyData
-> Token
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> AmountOfMoneyData -> AmountOfMoneyData
withMin Double
to (AmountOfMoneyData -> Maybe Token)
-> AmountOfMoneyData -> Maybe Token
forall a b. (a -> b) -> a -> b
$ Currency -> AmountOfMoneyData
currencyOnly Currency
c
      [Token]
_ -> Maybe Token
forall a. Maybe a
Nothing
  }

rules :: [Rule]
rules :: [Rule]
rules =
  [ Rule
ruleUnitAmount
  , Rule
ruleCent
  , Rule
ruleEUR
  , Rule
ruleIntersectAndXCents
  , Rule
ruleIntervalBetweenNumeral
  , Rule
ruleIntervalBetween
  , Rule
ruleIntervalMax
  , Rule
ruleIntervalMin
  , Rule
ruleIntervalNumeralDash
  , Rule
ruleIntervalDash
  , Rule
rulePounds
  , Rule
ruleOneGBP
  , Rule
ruleGBP
  , Rule
rulePrecision
  , Rule
ruleIntersect
  , Rule
ruleAgura
  , Rule
ruleShekel
  , Rule
ruleOneShekel
  , Rule
ruleTwoShekel
  , Rule
ruleOneAgura
  , Rule
ruleThousandShekel
  , Rule
ruleMillionShekel
  , Rule
ruleDollar
  ]