@@ -0,0 +1,96 @@
1+-----------------------------------------------------------------------------
4+-- Copyright : (c) Phil Freeman 2013
7+-- Maintainer : Phil Freeman <paf31@cantab.net>
8+-- Stability : experimental
13+-----------------------------------------------------------------------------
15+{-# LANGUAGE FlexibleContexts #-}
19+import Control.Monad (forever)
20+import Control.Monad.Trans.Class
23+import Data.List (isPrefixOf)
25+import System.Console.Haskeline
27+import qualified Language.PureScript as P
28+import qualified Control.Monad.State.Strict as S
29+import qualified Paths_purescript as Paths
30+import qualified System.IO.UTF8 as U (readFile)
32+getPreludeFilename :: IO FilePath
33+getPreludeFilename = Paths.getDataFileName "libraries/prelude/prelude.purs"
36+options = P.Options True False True False
38+data InterpreterState = InterpreterState { interpEnv :: [P.DoNotationElement] } deriving (Show)
40+defaultState :: InterpreterState
41+defaultState = InterpreterState []
43+completion :: (S.MonadState InterpreterState m) => CompletionFunc m
44+completion = completeWord Nothing " \t\n\r" findCompletions
46+ findCompletions :: (S.MonadState InterpreterState m) => String -> m [Completion]
47+ findCompletions str = do
49+ let names = map show . concatMap toNames . interpEnv $ st
50+ let matches = filter (isPrefixOf str) names
51+ return $ map simpleCompletion matches
52+ toNames :: P.DoNotationElement -> [P.Ident]
53+ toNames (P.DoNotationLet binder _) = binderToNames binder
54+ toNames (P.DoNotationBind binder _) = binderToNames binder
56+ binderToNames :: P.Binder -> [P.Ident]
57+ binderToNames = everything (++) (mkQ [] find)
59+ find (P.VarBinder ident) = [ident]
62+createTemporaryModule :: [P.DoNotationElement] -> P.Module
63+createTemporaryModule decls =
65+ moduleName = P.ProperName "Temp"
66+ importDecl m = P.ImportDeclaration m Nothing
67+ prelude = P.ModuleName (P.ProperName "Prelude")
68+ effModule = P.ModuleName (P.ProperName "Eff")
69+ effMonad = P.Var (P.Qualified (Just effModule) (P.Ident "eff"))
70+ itDecl = P.ValueDeclaration (P.Ident "it") [] Nothing (P.Do effMonad decls)
72+ P.Module moduleName [importDecl prelude, itDecl]
76+ preludeFilename <- getPreludeFilename
77+ preludeText <- U.readFile preludeFilename
78+ let (Right prelude) = P.runIndentParser P.parseModules preludeText
79+ flip S.evalStateT defaultState . runInputT (setComplete completion defaultSettings) $ do
80+ outputStrLn "PureScript Compiler (Interactive Mode)"
82+ line <- getInputLine "> "
86+ case P.runIndentParser P.parseDoNotationElement line' of
87+ Left err -> outputStrLn (show err)
90+ let m = createTemporaryModule (interpEnv st ++ [decl])
91+ case P.compile options (prelude ++ [m]) of
92+ Left err -> outputStrLn err
93+ Right (js, _, _) -> do
95+ lift . S.put $ st { interpEnv = interpEnv st ++ [decl] }