11{-# OPTIONS_GHC -fno-warn-unused-pattern-binds #-}
22module Aws.Lambda.Configuration
3- ( LambdaOptions (.. )
3+ ( Main. LambdaOptions (.. )
4+ , Main. generate
5+ , Main. getRecord
46 , configureLambda
57 , returnAndFail
68 , returnAndSucceed
79 , decodeObj
8- , Options. getRecord
910 )
1011where
1112
1213import Data.Aeson
1314
14- import Control.Monad
1515import qualified Data.ByteString.Lazy as LazyByteString
16- import Data.Function ((&) )
1716import Data.Text (Text )
1817import qualified Data.Text as Text
1918import qualified Data.Text.Encoding as Encoding
20- import GHC.Generics
2119import Language.Haskell.TH
22- import qualified Options.Generic as Options
2320import System.Exit (exitFailure , exitSuccess )
2421import System.IO (hFlush , stderr , stdout )
2522
26- import Path
27- import qualified Path.IO as PathIO
28-
29- import Aws.Lambda.ThHelpers
23+ import qualified Aws.Lambda.Meta.Main as Main
24+ import qualified Aws.Lambda.Meta.Run as Run
3025
3126putTextLn :: Text -> IO ()
3227putTextLn = putStrLn . Text. unpack
3328
34- data LambdaOptions = LambdaOptions
35- { eventObject :: Text
36- , contextObject :: Text
37- , functionHandler :: Text
38- , executionUuid :: Text
39- } deriving (Generic )
40- instance Options. ParseRecord LambdaOptions
41-
42-
43- -- This function is the reason why we disable the warning on top of the module
44- mkMain :: Q [Dec ]
45- mkMain = [d |
46- $(pName "main") = getRecord "" >>= run
47- |]
48-
49- mkRun :: Q Dec
50- mkRun = do
51- handlers <- runIO getHandlers
52- clause' <- recordQ " LambdaOptions" [" functionHandler" , " contextObject" , " eventObject" , " executionUuid" ]
53- body <- dispatcherCaseQ handlers
54- pure $ FunD (mkName " run" ) [Clause [clause'] (NormalB body) [] ]
55-
56-
57- dispatcherCaseQ :: [Text ] -> Q Exp
58- dispatcherCaseQ fileNames = do
59- caseExp <- eName " functionHandler"
60- matches <- traverse handlerCaseQ fileNames
61- unmatched <- unmatchedCaseQ
62- pure $ CaseE caseExp (matches <> [unmatched])
63-
64-
65- handlerCaseQ :: Text -> Q Match
66- handlerCaseQ lambdaHandler = do
67- let pat = LitP (StringL $ Text. unpack lambdaHandler)
68- body <- [e |do
69- result <- $(eName qualifiedName) (decodeObj $(eName "eventObject")) (decodeObj $(eName "contextObject"))
70- either (returnAndFail $(eName "executionUuid")) (returnAndSucceed $(eName "executionUuid")) result |]
71- pure $ Match pat (NormalB body) []
72- where
73- qualifiedName =
74- lambdaHandler
75- & Text. dropWhile (/= ' /' )
76- & Text. drop 1
77- & Text. replace " /" " ."
78-
79-
80- unmatchedCaseQ :: Q Match
81- unmatchedCaseQ = do
82- let pattern = WildP
83- body <- [e |
84- returnAndFail $(eName "executionUuid") ("Handler " <> $(eName "functionHandler") <> " does not exist on project")
85- |]
86- pure $ Match pattern (NormalB body) []
87-
8829configureLambda :: Q [Dec ]
8930configureLambda = do
90- main <- mkMain
91- run <- mkRun
31+ main <- Main. generate
32+ run <- Run. generate
9233 return $ main <> [run]
9334
94-
9535returnAndFail :: ToJSON a => Text -> a -> IO ()
9636returnAndFail uuid v = do
9737 hFlush stdout
@@ -115,23 +55,4 @@ decodeObj :: FromJSON a => Text -> a
11555decodeObj x =
11656 case (eitherDecode $ LazyByteString. fromStrict $ Encoding. encodeUtf8 x) of
11757 Left e -> error e
118- Right v -> v
119-
120- getHandlers :: IO [Text ]
121- getHandlers = do
122- (_, files) <- PathIO. listDirRecurRel [reldir |.|]
123- handlerFiles <- files
124- & fmap toFilePath
125- & fmap Text. pack
126- & filter (Text. isSuffixOf " .hs" )
127- & filterM containsHandler
128- & fmap (fmap $ Text. dropEnd 3 )
129- & fmap (fmap $ Text. drop 2 )
130- & fmap (fmap (<> " .handler" ))
131- return handlerFiles
132-
133-
134- containsHandler :: Text -> IO Bool
135- containsHandler file = do
136- fileContents <- readFile $ Text. unpack file
137- return $ " handler :: " `Text.isInfixOf` Text. pack fileContents
58+ Right v -> v
0 commit comments