on fb7e706 help sign in
stackage/Stackage/ServerFiles.hs
52 lines 1.6 kB history raw
1-- | Create the files necessary for Stackage server.
2module Stackage.ServerFiles
3 ( createHackageFile
4 ) where
6import Stackage.Util
7import Stackage.Types
8import qualified Data.Map as Map
9import Control.Exception (throwIO)
10import qualified Codec.Archive.Tar as Tar
11import qualified Data.ByteString.Lazy as L
12import Control.Arrow (second)
13import Distribution.Text (display)
14import System.IO (Handle, hPutStrLn)
16createHackageFile :: InstallInfo -> Handle -> IO ()
17createHackageFile ii h = do
18 indextargz <- getTarballName
19 indexLBS <- L.readFile indextargz
20 loop $ Tar.read indexLBS
21 where
22 selected = Map.fromList . map toStrs . Map.toList $
23 fmap spiVersion (iiPackages ii)
24 `Map.union` iiOptionalCore ii
25 `Map.union` Map.mapMaybe id (iiCore ii)
27 toStrs (PackageName name, version) = (name, display version)
29 loop Tar.Done = return ()
30 loop (Tar.Fail e) = throwIO e
31 loop (Tar.Next e es) = go e >> loop es
33 go e =
34 case parsePair $ Tar.entryPath e of
35 Nothing -> return ()
36 Just (name, version) ->
37 case Map.lookup name selected of
38 Just version' | version /= version' -> return ()
39 _ -> hPutStrLn h $ concat [name, "-", version]
41parsePair :: String -> Maybe (String, String)
42parsePair s =
43 case splitOn '/' s of
44 [name, version, cabal] | name ++ ".cabal" == cabal -> Just (name, version)
45 _ -> Nothing
47splitOn :: Eq a => a -> [a] -> [[a]]
48splitOn _ [] = []
49splitOn c x =
50 y : splitOn c z
51 where
52 (y, z) = second (drop 1) $ break (== c) x