1 module PursLoader.Loader
7 import Prelude (Unit(), ($), (>>=), (<$>), (<*>), (<<<), (++), bind, const)
9 import Control.Bind (join)
10 import Control.Monad.Eff (Eff())
11 import Control.Monad.Eff.Exception (Error(), error)
13 import Data.Array ((!!))
14 import Data.Function (Fn2(), mkFn2)
15 import Data.Maybe (Maybe(..), maybe)
16 import Data.Either (either)
17 import Data.Foreign (Foreign())
18 import Data.Foreign.Class (read)
19 import Data.Foreign.Null (runNull)
20 import Data.String.Regex (Regex(), match, noFlags, regex)
22 import Unsafe.Coerce (unsafeCoerce)
24 import PursLoader.LoaderRef
35 import PursLoader.LoaderUtil (parseQuery)
36 import PursLoader.Options (runOptions)
37 import PursLoader.Path (dirname, relative)
39 type Effects eff = (loader :: Loader | eff)
41 type PurescriptWebpackPluginContext eff = { compile :: (Foreign -> Eff (Effects eff) Unit) -> Eff (Effects eff) Unit }
43 loader :: forall eff. LoaderRef -> String -> Eff (Effects eff) Unit
44 loader ref source = do
49 let parsed = parseQuery $ query ref
51 options = either (const Nothing) (Just <<< runOptions) (read parsed)
53 moduleName = join $ match moduleRegex source >>= \as -> as !! 1
55 resourceDir = dirname (resourcePath ref)
57 modulePath = (\opts -> relative resourceDir opts.bundleOutput) <$> options
59 result = (\path name -> "module.exports = require('" ++ path ++ "')['" ++ name ++ "'];") <$> modulePath <*> moduleName
63 addDependency ref (resourcePath ref)
65 pluginContext.compile (\err -> maybe (callback (Just $ error "Failed to run loader") "")
66 (callback (compileError err)) result)
69 moduleRegex = regex "(?:^|\\n)module\\s+([\\w\\.]+)" noFlags { ignoreCase = true }
71 pluginContext :: PurescriptWebpackPluginContext eff
72 pluginContext = (unsafeCoerce ref).purescriptWebpackPluginContext
74 compileError :: Foreign -> Maybe Error
75 compileError value = either (const $ Just (error "Failed to compile")) ((<$>) error) (runNull <$> read value)
77 loaderFn :: forall eff. Fn2 LoaderRef String (Eff (Effects eff) Unit)
78 loaderFn = mkFn2 loader