csv reader: add the include directive, useful for factoring out common rules used with multiple CSV files
This commit is contained in:
parent
308916185c
commit
eff1d3f1a5
@ -549,8 +549,12 @@ The following kinds of rule can appear in any order:
|
|||||||
%-m/%-d/%Y
|
%-m/%-d/%Y
|
||||||
%Y-%h-%d
|
%Y-%h-%d
|
||||||
|
|
||||||
|
**include** *RULESFILE*
|
||||||
|
: Include another rules file at this point. Useful for common rules shared across multiple CSV files.
|
||||||
|
|
||||||
Typically you'll keep one rules file for each account which you
|
Typically you'll keep one rules file for each account which you
|
||||||
download as CSV. For an example, see [How to read CSV files](CSV.html).
|
download as CSV. For an example, see [How to read CSV
|
||||||
|
files](CSV.html).
|
||||||
|
|
||||||
Other notes:
|
Other notes:
|
||||||
|
|
||||||
|
|||||||
@ -22,7 +22,7 @@ import Control.Exception hiding (try)
|
|||||||
import Control.Monad
|
import Control.Monad
|
||||||
import Control.Monad.Error
|
import Control.Monad.Error
|
||||||
-- import Test.HUnit
|
-- import Test.HUnit
|
||||||
import Data.Char (toLower, isDigit)
|
import Data.Char (toLower, isDigit, isSpace)
|
||||||
import Data.List
|
import Data.List
|
||||||
import Data.Maybe
|
import Data.Maybe
|
||||||
import Data.Ord
|
import Data.Ord
|
||||||
@ -319,7 +319,7 @@ getDirective directivename = lookup directivename . rdirectives
|
|||||||
|
|
||||||
parseRulesFile :: FilePath -> IO (Either ParseError CsvRules)
|
parseRulesFile :: FilePath -> IO (Either ParseError CsvRules)
|
||||||
parseRulesFile f = do
|
parseRulesFile f = do
|
||||||
s <- readFile' f
|
s <- readFile' f >>= expandIncludes
|
||||||
let rules = parseCsvRules f s
|
let rules = parseCsvRules f s
|
||||||
return $ case rules of
|
return $ case rules of
|
||||||
Left e -> Left e
|
Left e -> Left e
|
||||||
@ -329,6 +329,19 @@ parseRulesFile f = do
|
|||||||
where
|
where
|
||||||
toParseError s = newErrorMessage (Message s) (initialPos "")
|
toParseError s = newErrorMessage (Message s) (initialPos "")
|
||||||
|
|
||||||
|
-- | Pre-parse csv rules to interpolate included files, recursively.
|
||||||
|
-- This is a cheap hack to avoid rewriting the existing parser.
|
||||||
|
expandIncludes :: String -> IO String
|
||||||
|
expandIncludes s = do
|
||||||
|
let (ls,rest) = break (isPrefixOf "include") $ lines s
|
||||||
|
case rest of
|
||||||
|
[] -> return $ unlines ls
|
||||||
|
(('i':'n':'c':'l':'u':'d':'e':f):ls') -> do
|
||||||
|
let f' = dropWhile isSpace f
|
||||||
|
included <- readFile f' >>= expandIncludes
|
||||||
|
return $ unlines [unlines ls, included, unlines ls']
|
||||||
|
ls' -> return $ unlines $ ls ++ ls' -- should never get here
|
||||||
|
|
||||||
parseCsvRules :: FilePath -> String -> Either ParseError CsvRules
|
parseCsvRules :: FilePath -> String -> Either ParseError CsvRules
|
||||||
-- parseCsvRules rulesfile s = runParser csvrulesfile nullrules{baseAccount=takeBaseName rulesfile} rulesfile s
|
-- parseCsvRules rulesfile s = runParser csvrulesfile nullrules{baseAccount=takeBaseName rulesfile} rulesfile s
|
||||||
parseCsvRules rulesfile s =
|
parseCsvRules rulesfile s =
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user