Skip to content

Commit

Permalink
Initial query command (#1087)
Browse files Browse the repository at this point in the history
  • Loading branch information
snoyberg committed Oct 8, 2015
1 parent ff17216 commit e875c04
Show file tree
Hide file tree
Showing 2 changed files with 63 additions and 1 deletion.
56 changes: 55 additions & 1 deletion src/Stack/Build.hs
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,8 @@ module Stack.Build
(build
,clean
,withLoadPackage
,mkBaseConfigOpts)
,mkBaseConfigOpts
,queryBuildInfo)
where

import Control.Monad
Expand All @@ -25,11 +26,20 @@ import Control.Monad.IO.Class
import Control.Monad.Logger
import Control.Monad.Reader (MonadReader, asks)
import Control.Monad.Trans.Resource
import Data.Aeson (Value (Object, Array), (.=), object)
import Data.Function
import qualified Data.HashMap.Strict as HM
import qualified Data.Map as Map
import Data.Map.Strict (Map)
import Data.Set (Set)
import qualified Data.Set as Set
import Data.Text (Text)
import qualified Data.Text as T
import qualified Data.Text.IO as TIO
import Data.Text.Encoding (decodeUtf8)
import Data.Text.Read (decimal)
import qualified Data.Vector as V
import qualified Data.Yaml as Yaml
import Network.HTTP.Client.Conduit (HasHttpManager)
import Path
import Path.IO
Expand Down Expand Up @@ -228,3 +238,47 @@ fixCodePage' inner = do
if mcp
then fixCodePage inner
else inner

-- | Query information about the build and print the result to stdout in YAML format.
queryBuildInfo :: M env m
=> [Text] -- ^ selectors
-> m ()
queryBuildInfo selectors0 = do
rawBuildInfo
>>= select id selectors0
>>= liftIO . TIO.putStrLn . decodeUtf8 . Yaml.encode
where
select _ [] value = return value
select front (sel:sels) value =
case value of
Object o ->
case HM.lookup sel o of
Nothing -> err "Selector not found"
Just value' -> cont value'
Array v ->
case decimal sel of
Right (i, "")
| i >= 0 && i < V.length v -> cont $ v V.! i
| otherwise -> err "Index out of range"
_ -> err "Encountered array and needed numeric selector"
_ -> err $ "Cannot apply selector to " ++ show value
where
cont = select (front . (sel:)) sels
err msg = error $ msg ++ ": " ++ show (front [sel])

-- | Get the raw build information object
rawBuildInfo :: M env m => m Value
rawBuildInfo = do
(_, _mbp, locals, _extraToBuild, _sourceMap) <- loadSourceMap NeedTargets defaultBuildOpts
return $ object
[ "locals" .= Object (HM.fromList $ map localToPair locals)
]
where
localToPair lp =
(T.pack $ packageNameString $ packageName p, value)
where
p = lpPackage lp
value = object
[ "version" .= packageVersion p
, "path" .= toFilePath (lpDir lp)
]
8 changes: 8 additions & 0 deletions src/main/Main.hs
Original file line number Diff line number Diff line change
Expand Up @@ -256,6 +256,10 @@ main = withInterpreterArgs stackProgName $ \args isInterpreter -> do
"and package version.") <>
value " " <>
showDefault))
addCommand "query"
"Query general build information (experimental)"
queryCmd
(many $ strArgument $ metavar "SELECTOR...")
addSubCommands
"ide"
"IDE-specific commands"
Expand Down Expand Up @@ -945,3 +949,7 @@ dotCmd dotOpts go = withBuildConfigAndLock go (\_ -> dot dotOpts)
listDependenciesCmd :: Text -> GlobalOpts -> IO ()
listDependenciesCmd sep go = withBuildConfig go (listDependencies sep')
where sep' = T.replace "\\t" "\t" (T.replace "\\n" "\n" sep)

-- | Query build information
queryCmd :: [String] -> GlobalOpts -> IO ()
queryCmd selectors go = withBuildConfig go $ queryBuildInfo $ map T.pack selectors

0 comments on commit e875c04

Please sign in to comment.