packages feed

HXQ-0.8.4: Main.hs

{--------------------------------------------------------------
-
- The main program of the XQuery interpreter
- Programmer: Leonidas Fegaras (fegaras@cse.uta.edu)
- Date: 06/26/2008
-
---------------------------------------------------------------}


module Main where

import System.Environment
import qualified Control.Exception
import XML.HXQ.Compiler(functions)
import XML.HXQ.Interpreter(evalInput,xqueryE)
import XML.HXQ.XQuery

version = "0.8.4"


parseEnv :: [String] -> [(String,String)]
parseEnv [] = [("o","Temp.hs")]
parseEnv ("-help":xs) = ("help",""):(parseEnv xs)
parseEnv ("-c":file:xs) = ("c",file):(parseEnv xs)
parseEnv ("-o":file:xs) = ("o",file):(parseEnv xs)
parseEnv ("-db":file:xs) = ("db",file):(parseEnv xs)
parseEnv ("-v":xs) = ("v",""):(parseEnv xs)
parseEnv ("-p":query:file:xs) = ("p","doc('"++file++"')"++query):(parseEnv xs)
parseEnv (('-':x):_) = error ("Unrecognized option -"++x++". Use -help.")
parseEnv (file:xs) = ("r",file):(parseEnv xs)


main = do senv <- getArgs
          let env = parseEnv senv
              Just system_path = lookup "ghc" env
              Just hxq_path = lookup "hxq" env
              Just dbname = lookup "db" env
              verbose = case lookup "v" env of Nothing -> False; _ -> True
          case lookup "help" env of
            Just _ -> do putStrLn ("HXQ: XQuery Interpreter version "++version++".")
                         putStrLn "Command line options and files:"
                         putStrLn "   xquery-file               interpret the XQuery in xquery-file"
                         putStrLn "   -db file-path             use the relational database in file-path during querying"
                         putStrLn "   -c xquery-file            compile the XQuery in xquery-file into Haskell code"
                         putStrLn "   -o haskell-file           set the Haskell file for -c (default is Temp.hs)"
                         putStrLn "   -p XPath-query xml-file   interpret the XPath query against the xml-file"
                         putStrLn "   -v                        verbose information"
                         putStrLn "Without an xquery-file, it reads and interprets the input"
                         putStrLn "   The input may be an XQuery or a declare variable/function"
                         putStrLn "   To write an XQuery in multiple lines, wrap it in {}"
                         putStrLn ("Functions:  "++(foldr (\(f,_,_) r -> f++" "++r) "" functions))
            _ -> case lookup "c" env of
                   Just file -> do query <- readFile file
                                   let qf = map (\c -> if c=='\"' then '\'' else c)
                                                (foldr1 (\a r -> a++" "++r) (lines query))
                                       pr = "{-# OPTIONS_GHC -fth #-}\nmodule Main where\nimport XML.HXQ.XQuery\n\nmain = do res <- $(xq \""
                                            ++ qf ++ "\")\n          putXSeq res\n"
                                       Just ofile = lookup "o" env
                                   writeFile ofile pr
                   _ -> case lookup "r" env of
                          Just file -> case lookup "db" env of
                                         Just filepath -> do db <- connect filepath
                                                             result <- xfileDB file db
                                                             disconnect db
                                                             putXSeq result
                                         _ -> do query <- readFile file
                                                 (result,_,_) <- xqueryE query [] [] (\sql -> return []) verbose
                                                 putXSeq result
                          _ -> case lookup "p" env of
                                 Just query -> do (result,_,_) <- xqueryE query [] [] (\sql -> return []) verbose
                                                  putXSeq result
                                 _ -> do putStrLn ("HXQ: XQuery Interpreter version "++version++". Use -help for help.")
                                         case lookup "db" env of
                                           Just filepath
                                               -> do db <- connect filepath
                                                     evalInput (\s vs fs-> Control.Exception.catch
                                                                          (do (result,nvs,nfs) <- xqueryE s vs fs
                                                                                                  (\sql -> do stmt <- prepareSQL db sql
                                                                                                              return [XStmt stmt]) verbose
                                                                              putXSeq result
                                                                              return (nvs,nfs))
                                                                          (\e -> do putStrLn (show e); return (vs,fs))) [] []
                                                     disconnect db
                                           _ -> evalInput (\s vs fs-> Control.Exception.catch
                                                                      (do (result,nvs,nfs) <- xqueryE s vs fs
                                                                                                 (\_ -> error "Missing Database Connection") verbose
                                                                          putXSeq result
                                                                          return (nvs,nfs))
                                                                      (\e -> do putStrLn (show e); return (vs,fs))) [] []