buuka/src/Data/Query.hs

56 lines
1.2 KiB
Haskell
Raw Normal View History

2021-01-02 09:09:38 +02:00
{-# LANGUAGE GADTs #-}
{-# LANGUAGE LambdaCase #-}
module Data.Query
(
2021-01-02 09:17:29 +02:00
-- * AST
Field(..)
2021-01-02 09:09:38 +02:00
-- * Combinators
2021-01-02 09:17:29 +02:00
, startsWith
2021-01-02 09:09:38 +02:00
, endsWith
, (.&&.)
-- * Evaluating queries
, evaluate
)
where
import Data.Buuka
(BuukaEntry(..), URL(..))
import Data.List
(isPrefixOf, isSuffixOf)
import Data.Functor.Foldable
(Fix(..))
data Field a where
Url :: Field String
Title :: Field String
2021-01-03 00:14:52 +02:00
data QueryF f where
2021-01-03 00:16:36 +02:00
StartsWith :: Field String -> String -> QueryF f
EndsWith :: Field String -> String -> QueryF f
2021-01-03 00:14:52 +02:00
And :: f -> f -> QueryF f
2021-01-02 09:09:38 +02:00
deriving instance Functor QueryF
type Query = Fix QueryF
2021-01-03 00:16:36 +02:00
startsWith :: Field String -> String -> Query
2021-01-02 09:09:38 +02:00
startsWith field x = Fix (StartsWith field x)
2021-01-03 00:16:36 +02:00
endsWith :: Field String -> String -> Query
2021-01-02 09:09:38 +02:00
endsWith field x = Fix (EndsWith field x)
(.&&.) :: Query -> Query -> Query
a .&&. b = Fix (And a b)
evaluate :: QueryF (BuukaEntry -> Bool) -> (BuukaEntry -> Bool)
evaluate = \case
StartsWith Url x -> \BuukaEntry{url=URL u} -> x `isPrefixOf` u
EndsWith Url x -> \BuukaEntry{url=URL u} -> x `isSuffixOf` u
StartsWith Title x -> \BuukaEntry{title=t} -> maybe False (x `isPrefixOf`) t
EndsWith Title x -> \BuukaEntry{title=t} -> maybe False (x `isSuffixOf`) t
And a b -> \e -> a e && b e