diff --git a/hledger-lib/Hledger/Data/Matching.hs b/hledger-lib/Hledger/Data/Matching.hs index bc6ba6eb9..4e7c95bfc 100644 --- a/hledger-lib/Hledger/Data/Matching.hs +++ b/hledger-lib/Hledger/Data/Matching.hs @@ -28,8 +28,8 @@ import Hledger.Data.AccountName -- import Hledger.Data.Amount -- import Hledger.Data.Commodity (canonicaliseCommodities) import Hledger.Data.Dates --- import Hledger.Data.Transaction (journalTransactionWithDate,balanceTransaction) --- import Hledger.Data.Posting +import Hledger.Data.Posting +import Hledger.Data.Transaction -- import Hledger.Data.TimeLog -- | A matcher is an arbitrary boolean expression of various search criteria. @@ -136,10 +136,14 @@ parseMatcher _ ('d':'e':'p':'t':'h':':':s) = Left $ MatchDepth True $ readDef 0 parseMatcher _ "" = Left $ MatchAny parseMatcher d s = parseMatcher d $ defaultprefix++":"++s -parseStatus "*" = True -parseStatus _ = False +parseStatus :: String -> Bool +parseStatus s = s `elem` (truestrings ++ ["*"]) -parseBool s = s `elem` ["t","true","1","on"] +parseBool :: String -> Bool +parseBool s = s `elem` truestrings + +truestrings :: [String] +truestrings = ["t","true","1","on"] -- | Quote-and-prefix-aware version of words - don't split on spaces which -- are inside quotes, including quotes which may have one of the specified @@ -203,6 +207,8 @@ matchesPosting (MatchEDate True span) p = Nothing -> False where d = maybe Nothing teffectivedate $ ptransaction p matchesPosting (MatchEDate False span) p = not $ (MatchEDate True span) `matchesPosting` p +matchesPosting (MatchStatus True status) p = status == postingCleared p +matchesPosting (MatchStatus False status) p = status /= postingCleared p matchesPosting _ _ = False -- | Does the match expression match this transaction ? @@ -220,6 +226,8 @@ matchesTransaction (MatchDate False span) t = not $ (MatchDate True span) `match matchesTransaction (MatchEDate True span) Transaction{teffectivedate=Just d} = spanContainsDate span d matchesTransaction _ Transaction{teffectivedate=Nothing} = False matchesTransaction (MatchEDate False span) t = not $ (MatchEDate True span) `matchesTransaction` t +matchesTransaction (MatchStatus True status) t = status == tstatus t +matchesTransaction (MatchStatus False status) t = status /= tstatus t matchesTransaction _ _ = False -- | Does the match expression match this account ? @@ -290,10 +298,24 @@ tests_Hledger_Data_Matching = TestList parseQuery d "inacct:a desc:b" `is` (MatchDesc True "b", [QueryOptInAcct "b"]) parseQuery d "inacct:a inacct:b" `is` (MatchAny, [QueryOptInAcct "a"]) + parseQuery d "status:1" `is` (MatchStatus True True, []) + parseQuery d "status:0" `is` (MatchStatus True False, []) + ,"matchesAccount" ~: do assertBool "positive acct match" $ matchesAccount (MatchAcct True "b:c") "a:bb:c:d" -- assertBool "acct should match at beginning" $ not $ matchesAccount (MatchAcct True "a:b") "c:a:b" - -- ,"matchesAccount" ~: do - -- matchesAccount (MatchAcct ) + ,"matchesPosting" ~: do + -- matching posting status.. + assertBool "positive match on true posting status" $ + (MatchStatus True True) `matchesPosting` nullposting{pstatus=True} + assertBool "negative match on true posting status" $ + not $ (MatchStatus False True) `matchesPosting` nullposting{pstatus=True} + assertBool "positive match on false posting status" $ + (MatchStatus True False) `matchesPosting` nullposting{pstatus=False} + assertBool "negative match on false posting status" $ + not $ (MatchStatus False False) `matchesPosting` nullposting{pstatus=False} + assertBool "positive match on true posting status acquired from transaction" $ + (MatchStatus True True) `matchesPosting` nullposting{pstatus=False,ptransaction=Just nulltransaction{tstatus=True}} + ] diff --git a/hledger-web/.hledger/web/templates/searchform.hamlet b/hledger-web/.hledger/web/templates/searchform.hamlet index 372639d80..3518b95e0 100644 --- a/hledger-web/.hledger/web/templates/searchform.hamlet +++ b/hledger-web/.hledger/web/templates/searchform.hamlet @@ -23,6 +23,7 @@
acct:REGEXP to filter postings/transactions by account, # desc:REGEXP by description, # - date:PERIODEXP or edate:PERIODEXP by date or effective date. + date:PERIODEXP or edate:PERIODEXP by date or effective date, + status:BOOL by cleared status
not: to negate, use single or double quotes to include spaces, multiple patterns are AND'ed.