From baf7dca591bb2af70affdce4a5383522e3d2ef3d Mon Sep 17 00:00:00 2001 From: Michael Snoyman Date: Thu, 19 Mar 2015 07:51:42 +0200 Subject: [PATCH 01/18] Upper bound for #479 --- build-constraints.yaml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/build-constraints.yaml b/build-constraints.yaml index 8191928a..bc5ea9d3 100644 --- a/build-constraints.yaml +++ b/build-constraints.yaml @@ -794,6 +794,9 @@ packages: # https://github.com/ekmett/linear/issues/70 - linear < 1.18 + # https://github.com/fpco/stackage/issues/479 + - QuickCheck < 2.8 + # Package flags are applied to individual packages, and override the values of # global-flags package-flags: From 08c674509fe4370a080221fed299bec2cb927ba8 Mon Sep 17 00:00:00 2001 From: Michael Snoyman Date: Thu, 19 Mar 2015 07:55:57 +0200 Subject: [PATCH 02/18] Another upper bound on #440 --- build-constraints.yaml | 1 + 1 file changed, 1 insertion(+) diff --git a/build-constraints.yaml b/build-constraints.yaml index bc5ea9d3..9907bce6 100644 --- a/build-constraints.yaml +++ b/build-constraints.yaml @@ -771,6 +771,7 @@ packages: - th-orphans < 0.9 - file-location < 0.4.7 - th-desugar < 1.5.1 + - singletons < 1.1.1 # https://github.com/fpco/stackage/issues/442 - blaze-builder < 0.4 From c71cbd72decac6d427214a902f6fa64921190e8c Mon Sep 17 00:00:00 2001 From: Michael Sloan Date: Wed, 18 Mar 2015 23:59:58 -0700 Subject: [PATCH 03/18] Add executable-hash --- build-constraints.yaml | 1 + 1 file changed, 1 insertion(+) diff --git a/build-constraints.yaml b/build-constraints.yaml index 9907bce6..f14892a8 100644 --- a/build-constraints.yaml +++ b/build-constraints.yaml @@ -67,6 +67,7 @@ packages: - csv-conduit - diagrams-cairo - dimensional + - executable-hash - executable-path - fgl - fixed-list From e8304baaf9b29a8f623f0f1d0f86c38dd8635203 Mon Sep 17 00:00:00 2001 From: ___ Date: Thu, 19 Mar 2015 14:34:41 +0000 Subject: [PATCH 04/18] Add jose-jwt library --- build-constraints.yaml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/build-constraints.yaml b/build-constraints.yaml index f14892a8..6a9c58a7 100644 --- a/build-constraints.yaml +++ b/build-constraints.yaml @@ -743,6 +743,9 @@ packages: "Adam C. Foltzer acfoltzer@galois.com @acfoltzer": - gitrev + "Luke Taylor tekul.hs@gmail.com @tekul": + - jose-jwt + "Stackage upper bounds": # Force a specific version that's compatible with transformers 0.3 From 38fd5a2b4a5124d9479f6cc4f2489919625cf44f Mon Sep 17 00:00:00 2001 From: Michael Snoyman Date: Thu, 19 Mar 2015 17:34:40 +0200 Subject: [PATCH 05/18] Expected test failure jose-jwt #482 --- build-constraints.yaml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/build-constraints.yaml b/build-constraints.yaml index 6a9c58a7..05926055 100644 --- a/build-constraints.yaml +++ b/build-constraints.yaml @@ -1087,6 +1087,9 @@ expected-test-failures: # Requires locally running services - network-anonymous-i2p + # https://github.com/fpco/stackage/pull/482#issuecomment-83635207 + - jose-jwt + # Haddocks which are expected to fail. Same concept as expected test failures. expected-haddock-failures: # https://github.com/acw/bytestring-progress/issues/4 From a54f2711c57ef26db24e213db1f495ba97bc5c5f Mon Sep 17 00:00:00 2001 From: Michael Snoyman Date: Thu, 19 Mar 2015 19:11:58 +0200 Subject: [PATCH 06/18] Disable doctest for jose-jwt --- build-constraints.yaml | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/build-constraints.yaml b/build-constraints.yaml index 05926055..d969cf0d 100644 --- a/build-constraints.yaml +++ b/build-constraints.yaml @@ -857,6 +857,10 @@ package-flags: two-point-one: true two-point-two: false + # https://github.com/fpco/stackage/pull/482#issuecomment-83635207 + jose-jwt: + doctest: false + # By skipping a test suite, we do not pull in the build dependencies skipped-tests: - ReadArgs # old version of hspec @@ -1087,9 +1091,6 @@ expected-test-failures: # Requires locally running services - network-anonymous-i2p - # https://github.com/fpco/stackage/pull/482#issuecomment-83635207 - - jose-jwt - # Haddocks which are expected to fail. Same concept as expected test failures. expected-haddock-failures: # https://github.com/acw/bytestring-progress/issues/4 From 2b3e44bbffc32dfc4dcc708ef7962c7584354943 Mon Sep 17 00:00:00 2001 From: Michael Snoyman Date: Fri, 20 Mar 2015 08:02:42 +0200 Subject: [PATCH 07/18] Upper bound for #483 --- build-constraints.yaml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/build-constraints.yaml b/build-constraints.yaml index d969cf0d..96d76ef2 100644 --- a/build-constraints.yaml +++ b/build-constraints.yaml @@ -802,6 +802,9 @@ packages: # https://github.com/fpco/stackage/issues/479 - QuickCheck < 2.8 + # https://github.com/fpco/stackage/issues/483 + - rethinkdb-client-driver < 0.0.15 + # Package flags are applied to individual packages, and override the values of # global-flags package-flags: From 452687cd61bbb26f72887c5d44de0f513fad8e4e Mon Sep 17 00:00:00 2001 From: Michael Snoyman Date: Sun, 22 Mar 2015 09:28:48 +0200 Subject: [PATCH 08/18] Upper bound for #484 --- build-constraints.yaml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/build-constraints.yaml b/build-constraints.yaml index 96d76ef2..8657ff32 100644 --- a/build-constraints.yaml +++ b/build-constraints.yaml @@ -805,6 +805,9 @@ packages: # https://github.com/fpco/stackage/issues/483 - rethinkdb-client-driver < 0.0.15 + # https://github.com/fpco/stackage/issues/484 + - opaleye < 0.3.1.1 + # Package flags are applied to individual packages, and override the values of # global-flags package-flags: From 5dd8ca466c93c83b8e79e91e361417ef19dbc3d7 Mon Sep 17 00:00:00 2001 From: Michael Snoyman Date: Sun, 22 Mar 2015 12:35:33 +0200 Subject: [PATCH 09/18] Upper bound for #485 --- build-constraints.yaml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/build-constraints.yaml b/build-constraints.yaml index 8657ff32..a0d0652b 100644 --- a/build-constraints.yaml +++ b/build-constraints.yaml @@ -808,6 +808,9 @@ packages: # https://github.com/fpco/stackage/issues/484 - opaleye < 0.3.1.1 + # https://github.com/fpco/stackage/issues/485 + - parsec < 3.1.9 + # Package flags are applied to individual packages, and override the values of # global-flags package-flags: From 8f95d1879cc32c8180fd304283817d18bab19f1b Mon Sep 17 00:00:00 2001 From: Michael Snoyman Date: Sun, 22 Mar 2015 12:58:07 +0200 Subject: [PATCH 10/18] Remove upper bounds and close #484 --- build-constraints.yaml | 3 --- 1 file changed, 3 deletions(-) diff --git a/build-constraints.yaml b/build-constraints.yaml index a0d0652b..7596251a 100644 --- a/build-constraints.yaml +++ b/build-constraints.yaml @@ -805,9 +805,6 @@ packages: # https://github.com/fpco/stackage/issues/483 - rethinkdb-client-driver < 0.0.15 - # https://github.com/fpco/stackage/issues/484 - - opaleye < 0.3.1.1 - # https://github.com/fpco/stackage/issues/485 - parsec < 3.1.9 From 1891c1bfa79910555aeed6f105672acf8296d642 Mon Sep 17 00:00:00 2001 From: Michael Snoyman Date: Sun, 22 Mar 2015 13:25:31 +0200 Subject: [PATCH 11/18] Separate out stackage-curator --- .gitignore | 9 - ChangeLog.md | 64 --- Dockerfile | 25 - README.md | 12 +- Setup.hs | 2 - Stackage/BuildConstraints.hs | 234 --------- Stackage/BuildPlan.hs | 214 -------- Stackage/CheckBuildPlan.hs | 162 ------ Stackage/CompleteBuild.hs | 337 ------------ Stackage/CorePackages.hs | 53 -- Stackage/GhcPkg.hs | 104 ---- Stackage/GithubPings.hs | 36 -- Stackage/InstallBuild.hs | 102 ---- Stackage/PackageDescription.hs | 200 ------- Stackage/PackageIndex.hs | 127 ----- Stackage/PerformBuild.hs | 560 -------------------- Stackage/Prelude.hs | 116 ---- Stackage/ServerBundle.hs | 271 ---------- Stackage/UpdateBuildPlan.hs | 54 -- Stackage/Upload.hs | 272 ---------- app/stackage.hs | 210 -------- build-constraints.yaml | 1 + cabal.config | 847 ------------------------------ debian-bootstrap.sh | 71 --- stackage.cabal | 105 ---- test/Spec.hs | 1 - test/Stackage/BuildPlanSpec.hs | 143 ----- test/Stackage/CorePackagesSpec.hs | 19 - test/Stackage/PackageIndexSpec.hs | 21 - test/test-build-constraints.yaml | 20 - 30 files changed, 9 insertions(+), 4383 deletions(-) delete mode 100644 ChangeLog.md delete mode 100644 Dockerfile delete mode 100644 Setup.hs delete mode 100644 Stackage/BuildConstraints.hs delete mode 100644 Stackage/BuildPlan.hs delete mode 100644 Stackage/CheckBuildPlan.hs delete mode 100644 Stackage/CompleteBuild.hs delete mode 100644 Stackage/CorePackages.hs delete mode 100644 Stackage/GhcPkg.hs delete mode 100644 Stackage/GithubPings.hs delete mode 100644 Stackage/InstallBuild.hs delete mode 100644 Stackage/PackageDescription.hs delete mode 100644 Stackage/PackageIndex.hs delete mode 100644 Stackage/PerformBuild.hs delete mode 100644 Stackage/Prelude.hs delete mode 100644 Stackage/ServerBundle.hs delete mode 100644 Stackage/UpdateBuildPlan.hs delete mode 100644 Stackage/Upload.hs delete mode 100644 app/stackage.hs delete mode 100644 cabal.config delete mode 100755 debian-bootstrap.sh delete mode 100644 stackage.cabal delete mode 100644 test/Spec.hs delete mode 100644 test/Stackage/BuildPlanSpec.hs delete mode 100644 test/Stackage/CorePackagesSpec.hs delete mode 100644 test/Stackage/PackageIndexSpec.hs delete mode 100644 test/test-build-constraints.yaml diff --git a/.gitignore b/.gitignore index a153cdeb..6b60ace9 100644 --- a/.gitignore +++ b/.gitignore @@ -1,13 +1,4 @@ -dist -*.o -*.hi -*.chi -*.chs.h -*.swp /builds/ /logs/ -/.cabal-sandbox/ -cabal.sandbox.config nightly-*.yaml lts-*.yaml -/tarballs/ diff --git a/ChangeLog.md b/ChangeLog.md deleted file mode 100644 index d168d7e0..00000000 --- a/ChangeLog.md +++ /dev/null @@ -1,64 +0,0 @@ -## 0.6.1 - -* Switch to V2 upload by default -* --skip-hoogle option - -## 0.6.0 - -* Upload bundle V2 stuff - -## 0.5.2 - -* Upload LTS to Hackage with the name LTSHaskell - -## 0.5.1 - -* `loadBuildConstraints` -* More command line options - -## 0.5.0 - -* Print "Still Alive" while checking, to avoid Travis timeouts -* Include `stackage upload-nightly` command -* Optional plan checking - -## 0.4.0 - -* Command line uses optparse-applicative with additional options -* Library profiling support during build -* Remove cfGlobalFlags (just use package-specific flags) - -## 0.3.1 - -* Added `justCheck` and `stackage check` command line. - -## 0.3.0.1 - -Pre-fetch all packages from Hackage to catch Hackage downtime early. - -## 0.3.0.0 - -* Return progress URL from uploadBundle - -## 0.2.1.4 - -Generate a `core` file in bundles. - -## 0.2.1.1 - -Run postBuild earlier to avoid problems from broken doc uploads. - -## 0.2.1.0 - -* Use TLS manager (to download from Github) - -## 0.2.0.0 - -* Minor fixes -* `pbGlobalInstall` - -## 0.1.0.0 - -First version of Stackage which is made available as its own package. The -codebase has been completely rewritten at this point, to be ready for generated -both Stackage Nightly and LTS Haskell distributions. diff --git a/Dockerfile b/Dockerfile deleted file mode 100644 index c3956908..00000000 --- a/Dockerfile +++ /dev/null @@ -1,25 +0,0 @@ -FROM ubuntu:12.04 - -ENV HOME /home/stackage -ENV LANG en_US.UTF-8 - -RUN mkdir /home/stackage -p -RUN locale-gen en_US.UTF-8 - -RUN DEBIAN_FRONTEND=noninteractive apt-get update -RUN DEBIAN_FRONTEND=noninteractive apt-get install -y software-properties-common python-software-properties -RUN DEBIAN_FRONTEND=noninteractive add-apt-repository ppa:hvr/ghc -y - -ADD debian-bootstrap.sh /tmp/debian-bootstrap.sh -RUN DEBIAN_FRONTEND=noninteractive bash /tmp/debian-bootstrap.sh -RUN rm /tmp/debian-bootstrap.sh - -RUN DEBIAN_FRONTEND=noninteractive apt-get install -y cabal-install-1.20 ghc-7.8.4 alex-3.1.3 happy-1.19.4 - -ENV PATH /home/stackage/.cabal/bin:/usr/local/sbin:/usr/local/bin:/opt/ghc/7.8.4/bin:/opt/cabal/1.20/bin:/opt/alex/3.1.3/bin:/opt/happy/1.19.4/bin:/usr/sbin:/usr/bin:/sbin:/bin - -RUN cabal update -ADD . /tmp/stackage -RUN cd /tmp/stackage && cabal install . hscolour cabal-install --constraint "Cabal < 1.22" && cp $HOME/.cabal/bin/* /usr/local/bin && rm -rf $HOME/.cabal $HOME/.ghc /tmp/stackage - -RUN cd /home/stackage && cabal update && stackage check diff --git a/README.md b/README.md index 82a9802d..848c9744 100644 --- a/README.md +++ b/README.md @@ -7,10 +7,14 @@ __NOTE__ This repository is for package authors to get their code into Stackage. If you simply want to use Stackage as an end user, please follow the instructions on [http://www.stackage.org/](http://www.stackage.org). -A note about the codebase: the goal is to minimize dependencies and have -the maximum range of supported compiler versions. Therefore, we avoid -anything "complicated." For example, instead of using the text package, -we use Strings everywhere. +The Stackage project consists of multiple repositories. This repository +contains the metadata on packages to be included in future builds and some +project information. In addition, we have the following repositories: + +* [stackage-server](https://github.com/fpco/stackage-server) +* [stackage-curator](https://github.com/fpco/stackage-curator) +* [stackage-types](https://github.com/fpco/stackage-types) +* [lts-haskell](https://github.com/fpco/lts-haskell) Get your package included ------------------------- diff --git a/Setup.hs b/Setup.hs deleted file mode 100644 index 9a994af6..00000000 --- a/Setup.hs +++ /dev/null @@ -1,2 +0,0 @@ -import Distribution.Simple -main = defaultMain diff --git a/Stackage/BuildConstraints.hs b/Stackage/BuildConstraints.hs deleted file mode 100644 index c4ce1ceb..00000000 --- a/Stackage/BuildConstraints.hs +++ /dev/null @@ -1,234 +0,0 @@ -{-# LANGUAGE NoImplicitPrelude #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE RecordWildCards #-} -{-# LANGUAGE TupleSections #-} --- | The constraints on package selection for a new build plan. -module Stackage.BuildConstraints - ( BuildConstraints (..) - , PackageConstraints (..) - , TestState (..) - , SystemInfo (..) - , getSystemInfo - , defaultBuildConstraints - , toBC - , BuildConstraintsSource (..) - , loadBuildConstraints - ) where - -import Control.Monad.Writer.Strict (execWriter, tell) -import Data.Aeson -import qualified Data.Map as Map -import Data.Yaml (decodeEither', decodeFileEither) -import Distribution.Package (Dependency (..)) -import Distribution.System (Arch, OS) -import qualified Distribution.System -import Distribution.Version (anyVersion) -import Filesystem (isFile) -import Network.HTTP.Client (Manager, httpLbs, responseBody, Request) -import Stackage.CorePackages -import Stackage.Prelude - -data TestState = ExpectSuccess - | ExpectFailure - | Don'tBuild -- ^ when the test suite will pull in things we don't want - deriving (Show, Eq, Ord, Bounded, Enum) - -testStateToText :: TestState -> Text -testStateToText ExpectSuccess = "expect-success" -testStateToText ExpectFailure = "expect-failure" -testStateToText Don'tBuild = "do-not-build" - -instance ToJSON TestState where - toJSON = toJSON . testStateToText -instance FromJSON TestState where - parseJSON = withText "TestState" $ \t -> - case lookup t states of - Nothing -> fail $ "Invalid state: " ++ unpack t - Just v -> return v - where - states = asHashMap $ mapFromList - $ map (\x -> (testStateToText x, x)) [minBound..maxBound] - -data SystemInfo = SystemInfo - { siGhcVersion :: Version - , siOS :: OS - , siArch :: Arch - , siCorePackages :: Map PackageName Version - , siCoreExecutables :: Set ExeName - } - deriving (Show, Eq, Ord) -instance ToJSON SystemInfo where - toJSON SystemInfo {..} = object - [ "ghc-version" .= display siGhcVersion - , "os" .= display siOS - , "arch" .= display siArch - , "core-packages" .= Map.mapKeysWith const unPackageName (map display siCorePackages) - , "core-executables" .= siCoreExecutables - ] -instance FromJSON SystemInfo where - parseJSON = withObject "SystemInfo" $ \o -> do - let helper name = (o .: name) >>= either (fail . show) return . simpleParse - siGhcVersion <- helper "ghc-version" - siOS <- helper "os" - siArch <- helper "arch" - siCorePackages <- (o .: "core-packages") >>= goPackages - siCoreExecutables <- o .: "core-executables" - return SystemInfo {..} - where - goPackages = either (fail . show) return - . mapM simpleParse - . Map.mapKeysWith const mkPackageName - -data BuildConstraints = BuildConstraints - { bcPackages :: Set PackageName - -- ^ This does not include core packages. - , bcPackageConstraints :: PackageName -> PackageConstraints - - , bcSystemInfo :: SystemInfo - - , bcGithubUsers :: Map Text (Set Text) - -- ^ map an account to set of pingees - } - -data PackageConstraints = PackageConstraints - { pcVersionRange :: VersionRange - , pcMaintainer :: Maybe Maintainer - , pcTests :: TestState - , pcHaddocks :: TestState - , pcBuildBenchmarks :: Bool - , pcFlagOverrides :: Map FlagName Bool - , pcEnableLibProfile :: Bool - } - deriving (Show, Eq) -instance ToJSON PackageConstraints where - toJSON PackageConstraints {..} = object $ addMaintainer - [ "version-range" .= display pcVersionRange - , "tests" .= pcTests - , "haddocks" .= pcHaddocks - , "build-benchmarks" .= pcBuildBenchmarks - , "flags" .= Map.mapKeysWith const unFlagName pcFlagOverrides - , "library-profiling" .= pcEnableLibProfile - ] - where - addMaintainer = maybe id (\m -> (("maintainer" .= m):)) pcMaintainer -instance FromJSON PackageConstraints where - parseJSON = withObject "PackageConstraints" $ \o -> do - pcVersionRange <- (o .: "version-range") - >>= either (fail . show) return . simpleParse - pcTests <- o .: "tests" - pcHaddocks <- o .: "haddocks" - pcBuildBenchmarks <- o .: "build-benchmarks" - pcFlagOverrides <- Map.mapKeysWith const mkFlagName <$> o .: "flags" - pcMaintainer <- o .:? "maintainer" - pcEnableLibProfile <- fmap (fromMaybe True) (o .:? "library-profiling") - return PackageConstraints {..} - --- | The proposed plan from the requirements provided by contributors. --- --- Checks the current directory for a build-constraints.yaml file and uses it --- if present. If not, downloads from Github. -defaultBuildConstraints :: Manager -> IO BuildConstraints -defaultBuildConstraints = loadBuildConstraints BCSDefault - -data BuildConstraintsSource - = BCSDefault - | BCSFile FilePath - | BCSWeb Request - deriving (Show) - -loadBuildConstraints :: BuildConstraintsSource -> Manager -> IO BuildConstraints -loadBuildConstraints bcs man = do - case bcs of - BCSDefault -> do - e <- isFile fp0 - if e - then loadFile fp0 - else loadReq req0 - BCSFile fp -> loadFile fp - BCSWeb req -> loadReq req - where - fp0 = "build-constraints.yaml" - req0 = "https://raw.githubusercontent.com/fpco/stackage/master/build-constraints.yaml" - - loadFile fp = decodeFileEither (fpToString fp) >>= either throwIO toBC - loadReq req = httpLbs req man >>= - either throwIO toBC . decodeEither' . toStrict . responseBody - - -getSystemInfo :: IO SystemInfo -getSystemInfo = do - siCorePackages <- getCorePackages - siCoreExecutables <- getCoreExecutables - siGhcVersion <- getGhcVersion - return SystemInfo {..} - where - -- FIXME consider not hard-coding the next two values - siOS = Distribution.System.Linux - siArch = Distribution.System.X86_64 - -data ConstraintFile = ConstraintFile - { cfPackageFlags :: Map PackageName (Map FlagName Bool) - , cfSkippedTests :: Set PackageName - , cfExpectedTestFailures :: Set PackageName - , cfExpectedHaddockFailures :: Set PackageName - , cfSkippedBenchmarks :: Set PackageName - , cfPackages :: Map Maintainer (Vector Dependency) - , cfGithubUsers :: Map Text (Set Text) - , cfSkippedLibProfiling :: Set PackageName - } - -instance FromJSON ConstraintFile where - parseJSON = withObject "ConstraintFile" $ \o -> do - cfPackageFlags <- (goPackageMap . fmap goFlagMap) <$> o .: "package-flags" - cfSkippedTests <- getPackages o "skipped-tests" - cfExpectedTestFailures <- getPackages o "expected-test-failures" - cfExpectedHaddockFailures <- getPackages o "expected-haddock-failures" - cfSkippedBenchmarks <- getPackages o "skipped-benchmarks" - cfSkippedLibProfiling <- getPackages o "skipped-profiling" - cfPackages <- o .: "packages" - >>= mapM (mapM toDep) - . Map.mapKeysWith const Maintainer - cfGithubUsers <- o .: "github-users" - return ConstraintFile {..} - where - goFlagMap = Map.mapKeysWith const FlagName - goPackageMap = Map.mapKeysWith const PackageName - getPackages o name = (setFromList . map PackageName) <$> o .: name - - toDep :: Monad m => Text -> m Dependency - toDep = either (fail . show) return . simpleParse - -toBC :: ConstraintFile -> IO BuildConstraints -toBC ConstraintFile {..} = do - bcSystemInfo <- getSystemInfo - return BuildConstraints {..} - where - combine (maintainer, range1) (_, range2) = - (maintainer, intersectVersionRanges range1 range2) - revmap = unionsWith combine $ ($ []) $ execWriter - $ forM_ (mapToList cfPackages) - $ \(maintainer, deps) -> forM_ deps - $ \(Dependency name range) -> - tell (singletonMap name (maintainer, range):) - - bcPackages = Map.keysSet revmap - - bcPackageConstraints name = - PackageConstraints {..} - where - mpair = lookup name revmap - pcMaintainer = fmap fst mpair - pcVersionRange = maybe anyVersion snd mpair - pcEnableLibProfile = not (name `member` cfSkippedLibProfiling) - pcTests - | name `member` cfSkippedTests = Don'tBuild - | name `member` cfExpectedTestFailures = ExpectFailure - | otherwise = ExpectSuccess - pcBuildBenchmarks = name `notMember` cfSkippedBenchmarks - pcHaddocks - | name `member` cfExpectedHaddockFailures = ExpectFailure - - | otherwise = ExpectSuccess - pcFlagOverrides = fromMaybe mempty $ lookup name cfPackageFlags - - bcGithubUsers = cfGithubUsers diff --git a/Stackage/BuildPlan.hs b/Stackage/BuildPlan.hs deleted file mode 100644 index b8bc5376..00000000 --- a/Stackage/BuildPlan.hs +++ /dev/null @@ -1,214 +0,0 @@ -{-# LANGUAGE DeriveDataTypeable #-} -{-# LANGUAGE DeriveFoldable #-} -{-# LANGUAGE DeriveFunctor #-} -{-# LANGUAGE DeriveTraversable #-} -{-# LANGUAGE NoImplicitPrelude #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE RecordWildCards #-} -{-# LANGUAGE TupleSections #-} -{-# LANGUAGE TypeFamilies #-} --- | Representation of a concrete build plan, and how to generate a new one --- based on constraints. -module Stackage.BuildPlan - ( BuildPlan (..) - , PackagePlan (..) - , newBuildPlan - , makeToolMap - , getLatestAllowedPlans - ) where - -import Control.Monad.State.Strict (execState, get, put) -import Data.Aeson -import qualified Data.Map as Map -import qualified Data.Set as Set -import qualified Distribution.Compiler -import Distribution.PackageDescription -import Stackage.BuildConstraints -import Stackage.GithubPings -import Stackage.PackageDescription -import Stackage.PackageIndex -import Stackage.Prelude - -data BuildPlan = BuildPlan - { bpSystemInfo :: SystemInfo - , bpTools :: Vector (PackageName, Version) - , bpPackages :: Map PackageName PackagePlan - , bpGithubUsers :: Map Text (Set Text) - } - deriving (Show, Eq) - -instance ToJSON BuildPlan where - toJSON BuildPlan {..} = object - [ "system-info" .= bpSystemInfo - , "tools" .= map goTool bpTools - , "packages" .= Map.mapKeysWith const unPackageName bpPackages - , "github-users" .= bpGithubUsers - ] - where - goTool (k, v) = object - [ "name" .= display k - , "version" .= display v - ] -instance FromJSON BuildPlan where - parseJSON = withObject "BuildPlan" $ \o -> do - bpSystemInfo <- o .: "system-info" - bpTools <- (o .: "tools") >>= mapM goTool - bpPackages <- Map.mapKeysWith const mkPackageName <$> (o .: "packages") - bpGithubUsers <- o .:? "github-users" .!= mempty - return BuildPlan {..} - where - goTool = withObject "Tool" $ \o -> (,) - <$> ((o .: "name") >>= - either (fail . show) return . simpleParse . asText) - <*> ((o .: "version") >>= - either (fail . show) return . simpleParse . asText) - -data PackagePlan = PackagePlan - { ppVersion :: Version - , ppGithubPings :: Set Text - , ppUsers :: Set PackageName - , ppConstraints :: PackageConstraints - , ppDesc :: SimpleDesc - } - deriving (Show, Eq) - -instance ToJSON PackagePlan where - toJSON PackagePlan {..} = object - [ "version" .= asText (display ppVersion) - , "github-pings" .= ppGithubPings - , "users" .= map unPackageName (unpack ppUsers) - , "constraints" .= ppConstraints - , "description" .= ppDesc - ] -instance FromJSON PackagePlan where - parseJSON = withObject "PackageBuild" $ \o -> do - ppVersion <- o .: "version" - >>= either (fail . show) return - . simpleParse . asText - ppGithubPings <- o .:? "github-pings" .!= mempty - ppUsers <- Set.map PackageName <$> (o .:? "users" .!= mempty) - ppConstraints <- o .: "constraints" - ppDesc <- o .: "description" - return PackagePlan {..} - --- | Make a build plan given these package set and build constraints. -newBuildPlan :: MonadIO m => Map PackageName PackagePlan -> BuildConstraints -> m BuildPlan -newBuildPlan packagesOrig bc@BuildConstraints {..} = liftIO $ do - let toolMap = makeToolMap packagesOrig - packages = populateUsers $ removeUnincluded bc toolMap packagesOrig - toolNames :: [ExeName] - toolNames = concatMap (Map.keys . sdTools . ppDesc) packages - tools <- topologicalSortTools toolMap $ mapFromList $ do - exeName <- toolNames - guard $ exeName `notMember` siCoreExecutables - packageName <- maybe mempty setToList $ lookup exeName toolMap - packagePlan <- maybeToList $ lookup packageName packagesOrig - return (packageName, packagePlan) - -- FIXME topologically sort packages? maybe just leave that to the build phase - return BuildPlan - { bpSystemInfo = bcSystemInfo - , bpTools = tools - , bpPackages = packages - , bpGithubUsers = bcGithubUsers - } - where - SystemInfo {..} = bcSystemInfo - -makeToolMap :: Map PackageName PackagePlan - -> Map ExeName (Set PackageName) -makeToolMap = - unionsWith (++) . map go . mapToList - where - go (packageName, pp) = - foldMap go' $ sdProvidedExes $ ppDesc pp - where - go' exeName = singletonMap exeName (singletonSet packageName) - -topologicalSortTools :: MonadThrow m - => Map ExeName (Set PackageName) - -> Map PackageName PackagePlan - -> m (Vector (PackageName, Version)) -topologicalSortTools toolMap = topologicalSort - ppVersion - (concatMap (fromMaybe mempty . flip lookup toolMap) . Map.keys . sdTools . ppDesc) - --- | Include only packages which are dependencies of the required packages and --- their build tools. -removeUnincluded :: BuildConstraints - -> Map ExeName (Set PackageName) - -> Map PackageName PackagePlan - -> Map PackageName PackagePlan -removeUnincluded BuildConstraints {..} toolMap orig = - mapFromList $ filter (\(x, _) -> x `member` included) $ mapToList orig - where - SystemInfo {..} = bcSystemInfo - - included :: Set PackageName - included = flip execState mempty $ mapM_ add bcPackages - - add name = do - inc <- get - when (name `notMember` inc) $ do - put $ insertSet name inc - case lookup name orig of - Nothing -> return () - Just pb -> do - mapM_ add $ Map.keys $ sdPackages $ ppDesc pb - forM_ (Map.keys $ sdTools $ ppDesc pb) $ - \exeName -> when (exeName `notMember` siCoreExecutables) - $ mapM_ add $ fromMaybe mempty $ lookup exeName toolMap - -populateUsers :: Map PackageName PackagePlan - -> Map PackageName PackagePlan -populateUsers orig = - mapWithKey go orig - where - go name pb = pb { ppUsers = foldMap (go2 name) (mapToList orig) } - - go2 dep (user, pb) - | dep `member` sdPackages (ppDesc pb) = singletonSet user - | otherwise = mempty - --- | Check whether the given package/version combo meets the constraints --- currently in place. -isAllowed :: BuildConstraints - -> PackageName -> Version -> Bool -isAllowed bc = \name version -> - case lookup name $ siCorePackages $ bcSystemInfo bc of - Just _ -> False -- never reinstall a core package - Nothing -> withinRange version $ pcVersionRange $ bcPackageConstraints bc name - -mkPackagePlan :: MonadThrow m - => BuildConstraints - -> GenericPackageDescription - -> m PackagePlan -mkPackagePlan bc gpd = do - ppDesc <- toSimpleDesc CheckCond {..} gpd - return PackagePlan {..} - where - PackageIdentifier name ppVersion = package $ packageDescription gpd - ppGithubPings = getGithubPings bc gpd - ppConstraints = bcPackageConstraints bc name - ppUsers = mempty -- must be filled in later - - ccPackageName = name - ccOS = siOS - ccArch = siArch - ccCompilerFlavor = Distribution.Compiler.GHC - ccCompilerVersion = siGhcVersion - ccFlags = flags - ccIncludeTests = pcTests ppConstraints /= Don'tBuild - ccIncludeBenchmarks = pcBuildBenchmarks ppConstraints - - SystemInfo {..} = bcSystemInfo bc - - overrides = pcFlagOverrides ppConstraints - getFlag MkFlag {..} = - (flagName, fromMaybe flagDefault $ lookup flagName overrides) - flags = mapFromList $ map getFlag $ genPackageFlags gpd - -getLatestAllowedPlans :: MonadIO m => BuildConstraints -> m (Map PackageName PackagePlan) -getLatestAllowedPlans bc = - getLatestDescriptions - (isAllowed bc) - (mkPackagePlan bc) diff --git a/Stackage/CheckBuildPlan.hs b/Stackage/CheckBuildPlan.hs deleted file mode 100644 index 74bf3b83..00000000 --- a/Stackage/CheckBuildPlan.hs +++ /dev/null @@ -1,162 +0,0 @@ -{-# LANGUAGE TupleSections #-} -{-# LANGUAGE DeriveDataTypeable #-} -{-# LANGUAGE GeneralizedNewtypeDeriving #-} -{-# LANGUAGE NoImplicitPrelude #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE RecordWildCards #-} -{-# LANGUAGE ViewPatterns #-} --- | Confirm that a build plan has a consistent set of dependencies. -module Stackage.CheckBuildPlan - ( checkBuildPlan - , BadBuildPlan - ) where - -import Control.Monad.Writer.Strict (Writer, execWriter, tell) -import qualified Data.Map.Strict as M -import qualified Data.Text as T -import Stackage.BuildConstraints -import Stackage.BuildPlan -import Stackage.PackageDescription -import Stackage.Prelude - --- | Check the build plan for missing deps, wrong versions, etc. -checkBuildPlan :: (MonadThrow m) => BuildPlan -> m () -checkBuildPlan BuildPlan {..} - | null errs' = return () - | otherwise = throwM errs - where - allPackages = map (,mempty) (siCorePackages bpSystemInfo) ++ - map (ppVersion &&& M.keys . M.filter libAndExe . sdPackages . ppDesc) bpPackages - errs@(BadBuildPlan errs') = - execWriter $ mapM_ (checkDeps allPackages) $ mapToList bpPackages - -- Only looking at libraries and executables, benchmarks and tests - -- are allowed to create cycles (e.g. test-framework depends on - -- text, which uses test-framework in its test-suite). - libAndExe (DepInfo cs _) = any (flip elem [CompLibrary,CompExecutable]) cs - --- | For a given package name and plan, check that its dependencies are: --- --- 1. Existent (existing in the provided package map) --- 2. Within version range --- 3. Check for dependency cycles. -checkDeps :: Map PackageName (Version,[PackageName]) - -> (PackageName, PackagePlan) - -> Writer BadBuildPlan () -checkDeps allPackages (user, pb) = - mapM_ go $ mapToList $ sdPackages $ ppDesc pb - where - go (dep, diRange -> range) = - case lookup dep allPackages of - Nothing -> tell $ BadBuildPlan $ singletonMap (dep, Nothing) errMap - Just (version,deps) - | version `withinRange` range -> - occursCheck allPackages - (\d v -> - tell $ BadBuildPlan $ singletonMap - (d,v) - errMap) - dep - deps - [] - | otherwise -> tell $ BadBuildPlan $ singletonMap - (dep, Just version) - errMap - where - errMap = singletonMap pu range - pu = PkgUser - { puName = user - , puVersion = ppVersion pb - , puMaintainer = pcMaintainer $ ppConstraints pb - , puGithubPings = ppGithubPings pb - } - --- | Check whether the package(s) occurs within its own dependency --- tree. -occursCheck - :: Monad m - => Map PackageName (Version,[PackageName]) - -- ^ All packages. - -> (PackageName -> Maybe Version -> m ()) - -- ^ Report an erroneous package. - -> PackageName - -- ^ Starting package to check for cycles in. - -> [PackageName] - -- ^ Dependencies of the package. - -> [PackageName] - -- ^ Previously seen packages up the dependency tree. - -> m () -occursCheck allPackages reportError = - go - where - go pkg deps seen = - case find (flip elem seen) deps of - Just cyclic -> - reportError cyclic $ - fmap fst (lookup cyclic allPackages) - Nothing -> - forM_ deps $ - \pkg' -> - case lookup pkg' allPackages of - Just (_v,deps') - | pkg' /= pkg -> go pkg' deps' seen' - _ -> return () - where seen' = pkg : seen - -data PkgUser = PkgUser - { puName :: PackageName - , puVersion :: Version - , puMaintainer :: Maybe Maintainer - , puGithubPings :: Set Text - } - deriving (Eq, Ord) - -pkgUserShow1 :: PkgUser -> Text -pkgUserShow1 PkgUser {..} = concat - [ display puName - , "-" - , display puVersion - ] - -pkgUserShow2 :: PkgUser -> Text -pkgUserShow2 PkgUser {..} = unwords - $ (maybe "No maintainer" unMaintainer puMaintainer ++ ".") - : map (cons '@') (setToList puGithubPings) - -newtype BadBuildPlan = - BadBuildPlan (Map (PackageName, Maybe Version) (Map PkgUser VersionRange)) - deriving Typeable -instance Exception BadBuildPlan -instance Show BadBuildPlan where - show (BadBuildPlan errs) = - unpack $ concatMap go $ mapToList errs - where - go ((dep, mdepVer), users) = unlines - $ "" - : showDepVer dep mdepVer - : map showUser (mapToList users) - - showDepVer :: PackageName -> Maybe Version -> Text - showDepVer dep Nothing = display dep ++ " (not present) depended on by:" - showDepVer dep (Just version) = concat - [ display dep - , "-" - , display version - , " depended on by:" - ] - - showUser :: (PkgUser, VersionRange) -> Text - showUser (pu, range) = concat - [ "- " - , pkgUserShow1 pu - , " (" - -- add a space after < to avoid confusing Markdown processors (like - -- Github's issue tracker) - , T.replace "<" "< " $ display range - , "). " - , pkgUserShow2 pu - ] - -instance Monoid BadBuildPlan where - mempty = BadBuildPlan mempty - mappend (BadBuildPlan x) (BadBuildPlan y) = - BadBuildPlan $ unionWith (unionWith intersectVersionRanges) x y diff --git a/Stackage/CompleteBuild.hs b/Stackage/CompleteBuild.hs deleted file mode 100644 index ee4996d6..00000000 --- a/Stackage/CompleteBuild.hs +++ /dev/null @@ -1,337 +0,0 @@ -{-# LANGUAGE NoImplicitPrelude #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE RecordWildCards #-} -module Stackage.CompleteBuild - ( BuildType (..) - , BumpType (..) - , BuildFlags (..) - , completeBuild - , justCheck - , justUploadNightly - , getStackageAuthToken - ) where - -import Control.Concurrent (threadDelay) -import Control.Concurrent.Async (withAsync) -import Data.Default.Class (def) -import Data.Semigroup (Max (..), Option (..)) -import Data.Text.Read (decimal) -import Data.Time -import Data.Yaml (decodeFileEither, encodeFile) -import Network.HTTP.Client -import Network.HTTP.Client.TLS (tlsManagerSettings) -import Stackage.BuildConstraints -import Stackage.BuildPlan -import Stackage.CheckBuildPlan -import Stackage.PerformBuild -import Stackage.Prelude -import Stackage.ServerBundle -import Stackage.UpdateBuildPlan -import Stackage.Upload -import System.Environment (lookupEnv) -import System.IO (BufferMode (LineBuffering), hSetBuffering) - --- | Flags passed in from the command line. -data BuildFlags = BuildFlags - { bfEnableTests :: !Bool - , bfEnableHaddock :: !Bool - , bfDoUpload :: !Bool - , bfEnableLibProfile :: !Bool - , bfEnableExecDyn :: !Bool - , bfVerbose :: !Bool - , bfSkipCheck :: !Bool - , bfUploadV1 :: !Bool - , bfServer :: !StackageServer - , bfBuildHoogle :: !Bool - } deriving (Show) - -data BuildType = Nightly | LTS BumpType - deriving (Show, Read, Eq, Ord) - -data BumpType = Major | Minor - deriving (Show, Read, Eq, Ord) - -data Settings = Settings - { plan :: BuildPlan - , planFile :: FilePath - , buildDir :: FilePath - , logDir :: FilePath - , title :: Text -> Text -- ^ GHC version -> title - , slug :: Text - , setArgs :: Text -> UploadBundle -> UploadBundle - , postBuild :: IO () - , distroName :: Text -- ^ distro name on Hackage - , snapshotType :: SnapshotType - , bundleDest :: FilePath - } - -nightlyPlanFile :: Text -- ^ day - -> FilePath -nightlyPlanFile day = fpFromText ("nightly-" ++ day) <.> "yaml" - -nightlySettings :: Text -- ^ day - -> BuildPlan - -> Settings -nightlySettings day plan' = Settings - { planFile = nightlyPlanFile day - , buildDir = fpFromText $ "builds/nightly" - , logDir = fpFromText $ "logs/stackage-nightly-" ++ day - , title = \ghcVer -> concat - [ "Stackage Nightly " - , day - , ", GHC " - , ghcVer - ] - , slug = slug' - , setArgs = \ghcVer ub -> ub { ubNightly = Just ghcVer } - , plan = plan' - , postBuild = return () - , distroName = "Stackage" - , snapshotType = STNightly - , bundleDest = fpFromText $ "stackage-nightly-" ++ day ++ ".bundle" - } - where - slug' = "nightly-" ++ day - -getSettings :: Manager -> BuildType -> IO Settings -getSettings man Nightly = do - day <- tshow . utctDay <$> getCurrentTime - bc <- defaultBuildConstraints man - pkgs <- getLatestAllowedPlans bc - plan' <- newBuildPlan pkgs bc - return $ nightlySettings day plan' -getSettings man (LTS bumpType) = do - Option mlts <- fmap (fmap getMax) $ runResourceT - $ sourceDirectory "." - $$ foldMapC (Option . fmap Max . parseLTSVer . filename) - - (new, plan') <- case bumpType of - Major -> do - let new = - case mlts of - Nothing -> LTSVer 0 0 - Just (LTSVer x _) -> LTSVer (x + 1) 0 - bc <- defaultBuildConstraints man - pkgs <- getLatestAllowedPlans bc - plan' <- newBuildPlan pkgs bc - return (new, plan') - Minor -> do - old <- maybe (error "No LTS plans found in current directory") return mlts - oldplan <- decodeFileEither (fpToString $ renderLTSVer old) - >>= either throwM return - let new = incrLTSVer old - let bc = updateBuildConstraints oldplan - pkgs <- getLatestAllowedPlans bc - plan' <- newBuildPlan pkgs bc - return (new, plan') - - let newfile = renderLTSVer new - - return Settings - { planFile = newfile - , buildDir = fpFromText $ "builds/lts" - , logDir = fpFromText $ "logs/stackage-lts-" ++ tshow new - , title = \ghcVer -> concat - [ "LTS Haskell " - , tshow new - , ", GHC " - , ghcVer - ] - , slug = "lts-" ++ tshow new - , setArgs = \_ ub -> ub { ubLTS = Just $ tshow new } - , plan = plan' - , postBuild = do - let git args = withCheckedProcess - (proc "git" args) $ \ClosedStream Inherited Inherited -> - return () - putStrLn "Committing new LTS file to Git" - git ["add", fpToString newfile] - git ["commit", "-m", "Added new LTS release: " ++ show new] - putStrLn "Pushing to Git repository" - git ["push"] - , distroName = "LTSHaskell" - , snapshotType = - case new of - LTSVer x y -> STLTS x y - , bundleDest = fpFromText $ "stackage-lts-" ++ tshow new ++ ".bundle" - } - -data LTSVer = LTSVer !Int !Int - deriving (Eq, Ord) -instance Show LTSVer where - show (LTSVer x y) = concat [show x, ".", show y] -incrLTSVer :: LTSVer -> LTSVer -incrLTSVer (LTSVer x y) = LTSVer x (y + 1) - -parseLTSVer :: FilePath -> Maybe LTSVer -parseLTSVer fp = do - w <- stripPrefix "lts-" $ fpToText fp - x <- stripSuffix ".yaml" w - Right (major, y) <- Just $ decimal x - z <- stripPrefix "." y - Right (minor, "") <- Just $ decimal z - return $ LTSVer major minor -renderLTSVer :: LTSVer -> FilePath -renderLTSVer lts = fpFromText $ concat - [ "lts-" - , tshow lts - , ".yaml" - ] - --- | Just print a message saying "still alive" every minute, to appease Travis. -stillAlive :: IO () -> IO () -stillAlive inner = - withAsync (printer 1) $ const inner - where - printer i = forever $ do - threadDelay 60000000 - putStrLn $ "Still alive: " ++ tshow i - printer $! i + 1 - --- | Generate and check a new build plan, but do not execute it. --- --- Since 0.3.1 -justCheck :: IO () -justCheck = stillAlive $ withManager tlsManagerSettings $ \man -> do - putStrLn "Loading build constraints" - bc <- defaultBuildConstraints man - - putStrLn "Creating build plan" - plans <- getLatestAllowedPlans bc - plan <- newBuildPlan plans bc - - putStrLn $ "Writing build plan to check-plan.yaml" - encodeFile "check-plan.yaml" plan - - putStrLn "Checking plan" - checkBuildPlan plan - - putStrLn "Plan seems valid!" - -getPerformBuild :: BuildFlags -> Settings -> PerformBuild -getPerformBuild buildFlags Settings {..} = PerformBuild - { pbPlan = plan - , pbInstallDest = buildDir - , pbLogDir = logDir - , pbLog = hPut stdout - , pbJobs = 8 - , pbGlobalInstall = False - , pbEnableTests = bfEnableTests buildFlags - , pbEnableHaddock = bfEnableHaddock buildFlags - , pbEnableLibProfiling = bfEnableLibProfile buildFlags - , pbEnableExecDyn = bfEnableExecDyn buildFlags - , pbVerbose = bfVerbose buildFlags - , pbAllowNewer = bfSkipCheck buildFlags - , pbBuildHoogle = bfBuildHoogle buildFlags - } - --- | Make a complete plan, build, test and upload bundle, docs and --- distro. -completeBuild :: BuildType -> BuildFlags -> IO () -completeBuild buildType buildFlags = withManager tlsManagerSettings $ \man -> do - hSetBuffering stdout LineBuffering - - putStrLn $ "Loading settings for: " ++ tshow buildType - settings@Settings {..} <- getSettings man buildType - - putStrLn $ "Writing build plan to: " ++ fpToText planFile - encodeFile (fpToString planFile) plan - - if bfSkipCheck buildFlags - then putStrLn "Skipping build plan check" - else do - putStrLn "Checking build plan" - checkBuildPlan plan - - putStrLn "Performing build" - let pb = getPerformBuild buildFlags settings - performBuild pb >>= mapM_ putStrLn - - putStrLn $ "Creating bundle (v2) at: " ++ fpToText bundleDest - createBundleV2 CreateBundleV2 - { cb2Plan = plan - , cb2Type = snapshotType - , cb2DocsDir = pbDocDir pb - , cb2Dest = bundleDest - } - - when (bfDoUpload buildFlags) $ - finallyUpload - (not $ bfUploadV1 buildFlags) - (bfServer buildFlags) - settings - man - -justUploadNightly - :: Text -- ^ nightly date - -> IO () -justUploadNightly day = do - plan <- decodeFileEither (fpToString $ nightlyPlanFile day) - >>= either throwM return - withManager tlsManagerSettings $ finallyUpload False def $ nightlySettings day plan - -getStackageAuthToken :: IO Text -getStackageAuthToken = do - mtoken <- lookupEnv "STACKAGE_AUTH_TOKEN" - case mtoken of - Nothing -> decodeUtf8 <$> readFile "/auth-token" - Just token -> return $ pack token - --- | The final part of the complete build process: uploading a bundle, --- docs and a distro to hackage. -finallyUpload :: Bool -- ^ use v2 upload - -> StackageServer - -> Settings -> Manager -> IO () -finallyUpload useV2 server settings@Settings{..} man = do - putStrLn "Uploading bundle to Stackage Server" - - token <- getStackageAuthToken - - if useV2 - then do - res <- flip uploadBundleV2 man UploadBundleV2 - { ub2Server = server - , ub2AuthToken = token - , ub2Bundle = bundleDest - } - putStrLn $ "New snapshot available at: " ++ res - else do - now <- epochTime - let ghcVer = display $ siGhcVersion $ bpSystemInfo plan - (ident, mloc) <- flip uploadBundle man $ setArgs ghcVer def - { ubContents = serverBundle now (title ghcVer) slug plan - , ubAuthToken = token - } - putStrLn $ "New ident: " ++ unSnapshotIdent ident - forM_ mloc $ \loc -> - putStrLn $ "Track progress at: " ++ loc - - putStrLn "Uploading docs to Stackage Server" - res1 <- tryAny $ uploadDocs UploadDocs - { udServer = def - , udAuthToken = token - , udDocs = pbDocDir pb - , udSnapshot = ident - } man - putStrLn $ "Doc upload response: " ++ tshow res1 - - putStrLn "Uploading doc map" - tryAny (uploadDocMap UploadDocMap - { udmServer = def - , udmAuthToken = token - , udmSnapshot = ident - , udmDocDir = pbDocDir pb - , udmPlan = plan - } man) >>= print - - postBuild `catchAny` print - - ecreds <- tryIO $ readFile "/hackage-creds" - case map encodeUtf8 $ words $ decodeUtf8 $ either (const "") id ecreds of - [username, password] -> do - putStrLn "Uploading as Hackage distro" - res2 <- uploadHackageDistroNamed distroName plan username password man - putStrLn $ "Distro upload response: " ++ tshow res2 - _ -> putStrLn "No creds found, skipping Hackage distro upload" - where - pb = getPerformBuild (error "finallyUpload.buildFlags") settings diff --git a/Stackage/CorePackages.hs b/Stackage/CorePackages.hs deleted file mode 100644 index 896ff002..00000000 --- a/Stackage/CorePackages.hs +++ /dev/null @@ -1,53 +0,0 @@ -{-# LANGUAGE NoImplicitPrelude #-} -{-# LANGUAGE OverloadedStrings #-} -module Stackage.CorePackages - ( getCorePackages - , getCoreExecutables - , getGhcVersion - ) where - -import qualified Data.Text as T -import Filesystem (listDirectory) -import Stackage.Prelude -import System.Directory (findExecutable) - --- | Get a @Map@ of all of the core packages. Core packages are defined as --- packages which ship with GHC itself. --- --- Precondition: GHC global package database has only core packages, and GHC --- ships with just a single version of each packages. -getCorePackages :: IO (Map PackageName Version) -getCorePackages = - withCheckedProcess cp $ \ClosedStream src Inherited -> - src $$ decodeUtf8C =$ linesUnboundedC =$ foldMapMC parsePackage - where - cp = proc "ghc-pkg" ["--no-user-package-conf", "list"] - parsePackage t - | ":" `isInfixOf` t = return mempty - | Just p <- stripSuffix "-" p' = singletonMap - <$> simpleParse p - <*> simpleParse v - | otherwise = return mempty - where - (p', v) = T.breakOnEnd "-" $ dropParens $ T.strip t - - dropParens s - | length s > 2 && headEx s == '(' && lastEx s == ')' = - initEx $ tailEx s - | otherwise = s - --- | A list of executables that are shipped with GHC. -getCoreExecutables :: IO (Set ExeName) -getCoreExecutables = do - mfp <- findExecutable "ghc" - dir <- - case mfp of - Nothing -> error "No ghc executable found on PATH" - Just fp -> return $ directory $ fpFromString fp - (setFromList . map (ExeName . fpToText . filename)) <$> listDirectory dir - -getGhcVersion :: IO Version -getGhcVersion = do - withCheckedProcess (proc "ghc" ["--numeric-version"]) $ - \ClosedStream src Inherited -> - (src $$ decodeUtf8C =$ foldC) >>= simpleParse diff --git a/Stackage/GhcPkg.hs b/Stackage/GhcPkg.hs deleted file mode 100644 index 27b7f9e1..00000000 --- a/Stackage/GhcPkg.hs +++ /dev/null @@ -1,104 +0,0 @@ -{-# LANGUAGE NoImplicitPrelude #-} -{-# LANGUAGE OverloadedStrings #-} --- | General commands related to ghc-pkg. - -module Stackage.GhcPkg - ( setupPackageDatabase - ) where - -import Data.Conduit -import qualified Data.Conduit.List as CL -import Data.Conduit.Process -import qualified Data.Conduit.Text as CT -import Data.Maybe -import Data.Text (Text) -import qualified Data.Text as T -import Distribution.Compat.ReadP -import Distribution.Package -import Distribution.Text (parse) -import Filesystem.Path.CurrentOS (FilePath) -import qualified Filesystem.Path.CurrentOS as FP -import Data.Map (Map) -import Data.Version (Version) -import Stackage.Prelude -import Filesystem (removeTree) - -setupPackageDatabase - :: Maybe FilePath -- ^ database location, Nothing if using global DB - -> FilePath -- ^ documentation root - -> (ByteString -> IO ()) -- ^ logging - -> Map PackageName Version -- ^ packages and versions to be installed - -> (PackageIdentifier -> IO ()) -- ^ callback to be used when unregistering a package - -> IO (Set PackageName) -- ^ packages remaining in the database after cleanup -setupPackageDatabase mdb docDir log' toInstall onUnregister = do - registered1 <- getRegisteredPackages flags - forM_ registered1 $ \pi@(PackageIdentifier name version) -> - case lookup name toInstall of - Just version' | version /= version' -> unregisterPackage log' onUnregister docDir flags pi - _ -> return () - broken <- getBrokenPackages flags - forM_ broken $ unregisterPackage log' onUnregister docDir flags - foldMap (\(PackageIdentifier name _) -> singletonSet name) - <$> getRegisteredPackages flags - where - flags = ghcPkgFlags mdb - -ghcPkgFlags :: Maybe FilePath -> [String] -ghcPkgFlags mdb = - "--no-user-package-db" : - case mdb of - Nothing -> ["--global"] - Just fp -> ["--package-db=" ++ fpToString fp] - --- | Get broken packages. -getBrokenPackages :: [String] -> IO [PackageIdentifier] -getBrokenPackages flags = do - (_,ps) <- sourceProcessWithConsumer - (proc - "ghc-pkg" - ("check" : "--simple-output" : flags)) - (CT.decodeUtf8 $= CT.lines $= CL.consume) - return (mapMaybe parsePackageIdent (T.words (T.unlines ps))) - --- | Get available packages. -getRegisteredPackages :: [String] -> IO [PackageIdentifier] -getRegisteredPackages flags = do - (_,ps) <- sourceProcessWithConsumer - (proc - "ghc-pkg" - ("list" : "--simple-output" : flags)) - (CT.decodeUtf8 $= CT.lines $= CL.consume) - return (mapMaybe parsePackageIdent (T.words (T.unlines ps))) - --- | Parse a package identifier: foo-1.2.3 -parsePackageIdent :: Text -> Maybe PackageIdentifier -parsePackageIdent = fmap fst . - listToMaybe . - filter (null . snd) . - readP_to_S parse . T.unpack - --- | Unregister a package. -unregisterPackage :: (ByteString -> IO ()) -- ^ log func - -> (PackageIdentifier -> IO ()) -- ^ callback to be used when unregistering a package - -> FilePath -- ^ doc directory - -> [String] -> PackageIdentifier -> IO () -unregisterPackage log' onUnregister docDir flags ident@(PackageIdentifier name _) = do - log' $ "Unregistering " ++ encodeUtf8 (display ident) ++ "\n" - onUnregister ident - - -- Delete libraries - sourceProcessWithConsumer - (proc "ghc-pkg" ("describe" : flags ++ [unpack $ display ident])) - (CT.decodeUtf8 - $= CT.lines - $= CL.mapMaybe parseLibraryDir - $= CL.mapM_ (void . tryIO . removeTree)) - - void (readProcessWithExitCode - "ghc-pkg" - ("unregister": flags ++ ["--force", unpack $ display name]) - "") - - void $ tryIO $ removeTree $ docDir fpFromText (display ident) - where - parseLibraryDir = fmap fpFromText . stripPrefix "library-dirs: " diff --git a/Stackage/GithubPings.hs b/Stackage/GithubPings.hs deleted file mode 100644 index bb7369f4..00000000 --- a/Stackage/GithubPings.hs +++ /dev/null @@ -1,36 +0,0 @@ -{-# LANGUAGE NoImplicitPrelude #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE ViewPatterns #-} -module Stackage.GithubPings - ( getGithubPings - ) where - -import Distribution.PackageDescription -import Stackage.BuildConstraints -import Stackage.Prelude - --- | Determine accounts to be pinged on Github based on various metadata in the --- package description. -getGithubPings :: BuildConstraints -- ^ for mapping to pingees - -> GenericPackageDescription -> Set Text -getGithubPings bc gpd = - foldMap (\(pack -> name) -> fromMaybe (singletonSet name) (lookup name (bcGithubUsers bc))) $ - goHomepage (homepage $ packageDescription gpd) ++ - concatMap goRepo (sourceRepos $ packageDescription gpd) - where - goHomepage t = do - prefix <- - [ "http://github.com/" - , "https://github.com/" - , "git://github.com/" - , "git@github.com:" - ] - t' <- maybeToList $ stripPrefix prefix t - let t'' = takeWhile (/= '/') t' - guard $ not $ null t'' - return t'' - - goRepo sr = - case (repoType sr, repoLocation sr) of - (Just Git, Just s) -> goHomepage s - _ -> [] diff --git a/Stackage/InstallBuild.hs b/Stackage/InstallBuild.hs deleted file mode 100644 index 2f896e35..00000000 --- a/Stackage/InstallBuild.hs +++ /dev/null @@ -1,102 +0,0 @@ -{-# LANGUAGE DeriveDataTypeable #-} -{-# LANGUAGE NoImplicitPrelude #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE RecordWildCards #-} -{-# LANGUAGE ScopedTypeVariables #-} -module Stackage.InstallBuild - ( InstallFlags (..) - , BuildPlanSource (..) - , installBuild - ) where - -import qualified Codec.Archive.Tar as Tar -import qualified Codec.Compression.GZip as GZip -import qualified Data.Yaml as Yaml -import Network.HTTP.Client -import Network.HTTP.Client.TLS (tlsManagerSettings) -import Stackage.BuildPlan -import Stackage.CheckBuildPlan -import Stackage.PerformBuild -import Stackage.Prelude -import System.IO (BufferMode (LineBuffering), hSetBuffering) - --- | Flags passed in from the command line. -data InstallFlags = InstallFlags - { ifPlanSource :: !BuildPlanSource - , ifInstallDest :: !FilePath - , ifLogDir :: !(Maybe FilePath) - , ifJobs :: !Int - , ifGlobalInstall :: !Bool - , ifEnableTests :: !Bool - , ifEnableHaddock :: !Bool - , ifEnableLibProfiling :: !Bool - , ifEnableExecDyn :: !Bool - , ifVerbose :: !Bool - , ifSkipCheck :: !Bool - , ifBuildHoogle :: !Bool - } deriving (Show) - --- | Source for build plan. -data BuildPlanSource = BPSBundleWeb String - | BPSFile FilePath - deriving (Show) - -getPerformBuild :: BuildPlan -> InstallFlags -> PerformBuild -getPerformBuild plan InstallFlags{..} = - PerformBuild - { pbPlan = plan - , pbInstallDest = ifInstallDest - , pbLogDir = fromMaybe (ifInstallDest "logs") ifLogDir - , pbLog = hPut stdout - , pbJobs = ifJobs - , pbGlobalInstall = ifGlobalInstall - , pbEnableTests = ifEnableTests - , pbEnableHaddock = ifEnableHaddock - , pbEnableLibProfiling = ifEnableLibProfiling - , pbEnableExecDyn = ifEnableExecDyn - , pbVerbose = ifVerbose - , pbAllowNewer = ifSkipCheck - , pbBuildHoogle = ifBuildHoogle - } - --- | Install stackage from an existing build plan. -installBuild :: InstallFlags -> IO () -installBuild installFlags@InstallFlags{..} = do - hSetBuffering stdout LineBuffering - - putStrLn $ "Loading build plan" - plan <- case ifPlanSource of - BPSBundleWeb url -> withManager tlsManagerSettings $ \man -> do - req <- parseUrl url - res <- httpLbs req man - planBSL <- getPlanEntry $ Tar.read $ GZip.decompress (responseBody res) - decodeBuildPlan planBSL - BPSFile path -> Yaml.decodeFileEither (fpToString path) >>= either throwM return - - if ifSkipCheck - then putStrLn "Skipping build plan check" - else do - putStrLn "Checking build plan" - checkBuildPlan plan - - putStrLn "Performing build" - performBuild (getPerformBuild plan installFlags) >>= mapM_ putStrLn - - where - getPlanEntry Tar.Done = throwIO NoBuildPlanException - getPlanEntry (Tar.Fail e) = throwIO e - getPlanEntry (Tar.Next entry entries) - | Tar.entryPath entry == "build-plan.yaml" = - case Tar.entryContent entry of - Tar.NormalFile bs _ -> return bs - _ -> throwIO NoBuildPlanException - | otherwise = getPlanEntry entries - - decodeBuildPlan = - either throwIO return . Yaml.decodeEither' . toStrict - -data InstallBuildException = NoBuildPlanException - deriving (Typeable) -instance Exception InstallBuildException -instance Show InstallBuildException where - show NoBuildPlanException = "Bundle has missing or invalid build-plan.yaml" diff --git a/Stackage/PackageDescription.hs b/Stackage/PackageDescription.hs deleted file mode 100644 index 24263701..00000000 --- a/Stackage/PackageDescription.hs +++ /dev/null @@ -1,200 +0,0 @@ -{-# LANGUAGE DeriveDataTypeable #-} -{-# LANGUAGE DeriveFoldable #-} -{-# LANGUAGE DeriveFunctor #-} -{-# LANGUAGE DeriveTraversable #-} -{-# LANGUAGE FlexibleContexts #-} -{-# LANGUAGE NoImplicitPrelude #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE RecordWildCards #-} -{-# LANGUAGE TypeFamilies #-} --- | Manipulate @GenericPackageDescription@ from Cabal into something more --- useful for us. -module Stackage.PackageDescription - ( SimpleDesc (..) - , toSimpleDesc - , CheckCond (..) - , Component (..) - , DepInfo (..) - ) where - -import Control.Monad.Writer.Strict (MonadWriter, execWriterT, - tell) -import Data.Aeson -import qualified Data.Map as Map -import Distribution.Compiler (CompilerFlavor) -import Distribution.Package (Dependency (..)) -import Distribution.PackageDescription -import Distribution.System (Arch, OS) -import Stackage.Prelude - -data Component = CompLibrary - | CompExecutable - | CompTestSuite - | CompBenchmark - deriving (Show, Read, Eq, Ord, Enum, Bounded) - -compToText :: Component -> Text -compToText CompLibrary = "library" -compToText CompExecutable = "executable" -compToText CompTestSuite = "test-suite" -compToText CompBenchmark = "benchmark" - -instance ToJSON Component where - toJSON = toJSON . compToText -instance FromJSON Component where - parseJSON = withText "Component" $ \t -> maybe - (fail $ "Invalid component: " ++ unpack t) - return - (lookup t comps) - where - comps = asHashMap $ mapFromList $ map (compToText &&& id) [minBound..maxBound] - -data DepInfo = DepInfo - { diComponents :: Set Component - , diRange :: VersionRange - } - deriving (Show, Eq) - -instance Semigroup DepInfo where - DepInfo a x <> DepInfo b y = DepInfo - (a <> b) - (intersectVersionRanges x y) -instance ToJSON DepInfo where - toJSON DepInfo {..} = object - [ "components" .= diComponents - , "range" .= display diRange - ] -instance FromJSON DepInfo where - parseJSON = withObject "DepInfo" $ \o -> do - diComponents <- o .: "components" - diRange <- o .: "range" >>= either (fail . show) return . simpleParse - return DepInfo {..} - --- | A simplified package description that tracks: --- --- * Package dependencies --- --- * Build tool dependencies --- --- * Provided executables --- --- It has fully resolved all conditionals -data SimpleDesc = SimpleDesc - { sdPackages :: Map PackageName DepInfo - , sdTools :: Map ExeName DepInfo - , sdProvidedExes :: Set ExeName - , sdModules :: Set Text - -- ^ modules exported by the library - } - deriving (Show, Eq) -instance Monoid SimpleDesc where - mempty = SimpleDesc mempty mempty mempty mempty - mappend (SimpleDesc a b c d) (SimpleDesc w x y z) = SimpleDesc - (unionWith (<>) a w) - (unionWith (<>) b x) - (c ++ y) - (d ++ z) -instance ToJSON SimpleDesc where - toJSON SimpleDesc {..} = object - [ "packages" .= Map.mapKeysWith const unPackageName sdPackages - , "tools" .= Map.mapKeysWith const unExeName sdTools - , "provided-exes" .= sdProvidedExes - , "modules" .= sdModules - ] -instance FromJSON SimpleDesc where - parseJSON = withObject "SimpleDesc" $ \o -> do - sdPackages <- Map.mapKeysWith const mkPackageName <$> (o .: "packages") - sdTools <- Map.mapKeysWith const ExeName <$> (o .: "tools") - sdProvidedExes <- o .: "provided-exes" - sdModules <- o .: "modules" - return SimpleDesc {..} - --- | Convert a 'GenericPackageDescription' into a 'SimpleDesc' by following the --- constraints in the provided 'CheckCond'. -toSimpleDesc :: MonadThrow m - => CheckCond - -> GenericPackageDescription - -> m SimpleDesc -toSimpleDesc cc gpd = execWriterT $ do - forM_ (condLibrary gpd) $ tellTree cc CompLibrary libBuildInfo getModules - forM_ (condExecutables gpd) $ tellTree cc CompExecutable buildInfo noModules . snd - tell mempty { sdProvidedExes = setFromList - $ map (fromString . fst) - $ condExecutables gpd - } - when (ccIncludeTests cc) $ forM_ (condTestSuites gpd) - $ tellTree cc CompTestSuite testBuildInfo noModules . snd - when (ccIncludeBenchmarks cc) $ forM_ (condBenchmarks gpd) - $ tellTree cc CompBenchmark benchmarkBuildInfo noModules . snd - where - noModules = const mempty - getModules = setFromList . map display . exposedModules - --- | Convert a single CondTree to a 'SimpleDesc'. -tellTree :: (MonadWriter SimpleDesc m, MonadThrow m) - => CheckCond - -> Component - -> (a -> BuildInfo) - -> (a -> Set Text) -- ^ get module names - -> CondTree ConfVar [Dependency] a - -> m () -tellTree cc component getBI getModules = - loop - where - loop (CondNode dat deps comps) = do - tell mempty - { sdPackages = unionsWith (<>) $ flip map deps - $ \(Dependency x y) -> singletonMap x DepInfo - { diComponents = singletonSet component - , diRange = simplifyVersionRange y - } - , sdTools = unionsWith (<>) $ flip map (buildTools $ getBI dat) - $ \(Dependency name range) -> singletonMap - -- In practice, cabal files refer to the exe name, not the - -- package name. - (ExeName $ unPackageName name) - DepInfo - { diComponents = singletonSet component - , diRange = simplifyVersionRange range - } - , sdModules = getModules dat - } - forM_ comps $ \(cond, ontrue, onfalse) -> do - b <- checkCond cc cond - if b - then loop ontrue - else maybe (return ()) loop onfalse - --- | Resolve a condition to a boolean based on the provided 'CheckCond'. -checkCond :: MonadThrow m => CheckCond -> Condition ConfVar -> m Bool -checkCond CheckCond {..} cond0 = - go cond0 - where - go (Var (OS os)) = return $ os == ccOS - go (Var (Arch arch)) = return $ arch == ccArch - go (Var (Flag flag)) = - case lookup flag ccFlags of - Nothing -> throwM $ FlagNotDefined ccPackageName flag cond0 - Just b -> return b - go (Var (Impl flavor range)) = return - $ flavor == ccCompilerFlavor - && ccCompilerVersion `withinRange` range - go (Lit b) = return b - go (CNot c) = not `liftM` go c - go (CAnd x y) = (&&) `liftM` go x `ap` go y - go (COr x y) = (||) `liftM` go x `ap` go y - -data CheckCondException = FlagNotDefined PackageName FlagName (Condition ConfVar) - deriving (Show, Typeable) -instance Exception CheckCondException - -data CheckCond = CheckCond - { ccPackageName :: PackageName -- for debugging only - , ccOS :: OS - , ccArch :: Arch - , ccFlags :: Map FlagName Bool - , ccCompilerFlavor :: CompilerFlavor - , ccCompilerVersion :: Version - , ccIncludeTests :: Bool - , ccIncludeBenchmarks :: Bool - } diff --git a/Stackage/PackageIndex.hs b/Stackage/PackageIndex.hs deleted file mode 100644 index 6b4c8087..00000000 --- a/Stackage/PackageIndex.hs +++ /dev/null @@ -1,127 +0,0 @@ -{-# LANGUAGE DeriveDataTypeable #-} -{-# LANGUAGE FlexibleContexts #-} -{-# LANGUAGE NoImplicitPrelude #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE RankNTypes #-} -{-# LANGUAGE ViewPatterns #-} --- | Dealing with the 00-index file and all its cabal files. -module Stackage.PackageIndex - ( sourcePackageIndex - , UnparsedCabalFile (..) - , getLatestDescriptions - ) where - -import qualified Codec.Archive.Tar as Tar -import Data.Conduit.Lazy (MonadActive, - lazyConsume) -import qualified Data.Text as T -import Distribution.PackageDescription (package, - packageDescription) -import Distribution.PackageDescription.Parse (ParseResult (..), - parsePackageDescription) -import Distribution.ParseUtils (PError) -import Stackage.Prelude -import System.Directory (getAppUserDataDirectory) - --- | Name of the 00-index.tar downloaded from Hackage. -getPackageIndexPath :: MonadIO m => m FilePath -getPackageIndexPath = liftIO $ do - c <- getCabalRoot - configLines <- runResourceT $ sourceFile (c "config") - $$ decodeUtf8C - =$ linesUnboundedC - =$ concatMapC getRemoteCache - =$ sinkList - case configLines of - [x] -> return $ x "hackage.haskell.org" "00-index.tar" - [] -> error $ "No remote-repo-cache found in Cabal config file" - _ -> error $ "Multiple remote-repo-cache entries found in Cabal config file" - where - getCabalRoot :: IO FilePath - getCabalRoot = fpFromString <$> getAppUserDataDirectory "cabal" - - getRemoteCache s = do - ("remote-repo-cache", stripPrefix ":" -> Just v) <- Just $ break (== ':') s - Just $ fpFromText $ T.strip v - --- | A cabal file with name and version parsed from the filepath, and the --- package description itself ready to be parsed. It's left in unparsed form --- for efficiency. -data UnparsedCabalFile = UnparsedCabalFile - { ucfName :: PackageName - , ucfVersion :: Version - , ucfParse :: forall m. MonadThrow m => m GenericPackageDescription - } - --- | Stream all of the cabal files from the 00-index tar file. -sourcePackageIndex :: (MonadThrow m, MonadResource m, MonadActive m, MonadBaseControl IO m) - => Producer m UnparsedCabalFile -sourcePackageIndex = do - fp <- getPackageIndexPath - -- yay for the tar package. Use lazyConsume instead of readFile to get some - -- kind of resource protection - lbs <- lift $ fromChunks <$> lazyConsume (sourceFile fp) - loop (Tar.read lbs) - where - loop (Tar.Next e es) = goE e >> loop es - loop Tar.Done = return () - loop (Tar.Fail e) = throwM e - - goE e - | Just front <- stripSuffix ".cabal" $ pack $ Tar.entryPath e - , Tar.NormalFile lbs _size <- Tar.entryContent e = do - (name, version) <- parseNameVersion front - yield UnparsedCabalFile - { ucfName = name - , ucfVersion = version - , ucfParse = goContent (Tar.entryPath e) name version lbs - } - | otherwise = return () - - goContent fp name version lbs = - case parsePackageDescription $ unpack $ decodeUtf8 lbs of - ParseFailed e -> throwM $ CabalParseException (fpFromString fp) e - ParseOk _warnings gpd -> do - let pd = packageDescription gpd - PackageIdentifier name' version' = package pd - when (name /= name' || version /= version') $ - throwM $ MismatchedNameVersion (fpFromString fp) - name name' version version' - return gpd - - parseNameVersion t1 = do - let (p', t2) = break (== '/') $ T.replace "\\" "/" t1 - p <- simpleParse p' - t3 <- maybe (throwM $ InvalidCabalPath t1 "no slash") return - $ stripPrefix "/" t2 - let (v', t4) = break (== '/') t3 - v <- simpleParse v' - when (t4 /= cons '/' p') $ throwM $ InvalidCabalPath t1 $ "Expected at end: " ++ p' - return (p, v) - -data InvalidCabalPath = InvalidCabalPath Text Text - deriving (Show, Typeable) -instance Exception InvalidCabalPath - -data CabalParseException = CabalParseException FilePath PError - | MismatchedNameVersion FilePath PackageName PackageName Version Version - deriving (Show, Typeable) -instance Exception CabalParseException - --- | Get all of the latest descriptions for name/version pairs matching the --- given criterion. -getLatestDescriptions :: MonadIO m - => (PackageName -> Version -> Bool) - -> (GenericPackageDescription -> IO desc) - -> m (Map PackageName desc) -getLatestDescriptions f parseDesc = liftIO $ do - m <- runResourceT $ sourcePackageIndex $$ filterC f' =$ foldlC add mempty - forM m $ \ucf -> liftIO $ ucfParse ucf >>= parseDesc - where - f' ucf = f (ucfName ucf) (ucfVersion ucf) - add m ucf = - case lookup name m of - Just ucf' | ucfVersion ucf < ucfVersion ucf' -> m - _ -> insertMap name ucf m - where - name = ucfName ucf diff --git a/Stackage/PerformBuild.hs b/Stackage/PerformBuild.hs deleted file mode 100644 index 06c1edc6..00000000 --- a/Stackage/PerformBuild.hs +++ /dev/null @@ -1,560 +0,0 @@ --- | Perform an actual build, generate a binary package database and a --- documentation directory in the process. -{-# LANGUAGE CPP #-} -{-# LANGUAGE DeriveDataTypeable #-} -{-# LANGUAGE NoImplicitPrelude #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE RecordWildCards #-} -module Stackage.PerformBuild - ( performBuild - , PerformBuild (..) - , BuildException (..) - , pbDocDir - ) where - -import Control.Concurrent.Async (async) -import Control.Concurrent.STM.TSem -import Control.Monad.Writer.Strict (execWriter, tell) -import qualified Data.Map as Map -import Data.NonNull (fromNullable) -import Filesystem (canonicalizePath, createTree, - getWorkingDirectory, isDirectory, - removeTree, rename, isFile, removeFile) -import Filesystem.Path (parent) -import qualified Filesystem.Path as F -import Stackage.BuildConstraints -import Stackage.BuildPlan -import Stackage.GhcPkg -import Stackage.PackageDescription -import Stackage.Prelude hiding (pi) -import System.Directory (findExecutable) -import System.Environment (getEnvironment) -import System.IO (IOMode (WriteMode), - openBinaryFile) -import System.IO.Temp (withSystemTempDirectory) - -data BuildException = BuildException (Map PackageName BuildFailure) [Text] - deriving Typeable -instance Exception BuildException -instance Show BuildException where - show (BuildException m warnings) = - unlines $ map go (mapToList m) ++ map unpack warnings - where - go (PackageName name, bf) = concat - [ name - , ": " - , show bf - ] - -data BuildFailure = DependencyFailed PackageName - | DependencyMissing PackageName - | ToolMissing ExeName - | NotImplemented - | BuildFailureException SomeException - deriving (Show, Typeable) -instance Exception BuildFailure - -data PerformBuild = PerformBuild - { pbPlan :: BuildPlan - , pbInstallDest :: FilePath - , pbLog :: ByteString -> IO () - , pbLogDir :: FilePath - , pbJobs :: Int - , pbGlobalInstall :: Bool - -- ^ Register packages in the global database - , pbEnableTests :: Bool - , pbEnableHaddock :: Bool - , pbEnableLibProfiling :: Bool - , pbEnableExecDyn :: Bool - , pbVerbose :: Bool - , pbAllowNewer :: Bool - -- ^ Pass --allow-newer to cabal configure - , pbBuildHoogle :: Bool - -- ^ Should we build Hoogle database? - -- - -- May be disabled due to: https://ghc.haskell.org/trac/ghc/ticket/9921 - } - -data PackageInfo = PackageInfo - { piPlan :: PackagePlan - , piName :: PackageName - , piResult :: TMVar Bool - } - -waitForDeps :: Map ExeName (Set PackageName) - -> Map PackageName PackageInfo - -> Set Component - -> BuildPlan - -> PackageInfo - -> IO a - -> IO a -waitForDeps toolMap packageMap activeComps bp pi action = do - atomically $ do - mapM_ checkPackage $ Map.keys $ filterUnused $ sdPackages $ ppDesc $ piPlan pi - forM_ (Map.keys $ filterUnused $ sdTools $ ppDesc $ piPlan pi) $ \exe -> do - case lookup exe toolMap >>= fromNullable . map checkPackage . setToList of - Nothing - | isCoreExe exe -> return () - -- https://github.com/jgm/zip-archive/issues/23 - -- - | otherwise -> throwSTM $ ToolMissing exe - | otherwise -> return () - Just packages -> ofoldl1' (<|>) packages - action - where - filterUnused :: Ord key => Map key DepInfo -> Map key DepInfo - filterUnused = - mapFromList . filter (go . snd) . mapToList - where - go = not . null . intersection activeComps . diComponents - - checkPackage package | package == piName pi = return () - checkPackage package = - case lookup package packageMap of - Nothing - | isCore package -> return () - | otherwise -> throwSTM $ DependencyMissing package - Just dep -> do - res <- readTMVar $ piResult dep - unless res $ throwSTM $ DependencyFailed package - - isCore = (`member` siCorePackages (bpSystemInfo bp)) - isCoreExe = (`member` siCoreExecutables (bpSystemInfo bp)) - -withCounter :: TVar Int -> IO a -> IO a -withCounter counter = bracket_ - (atomically $ modifyTVar counter (+ 1)) - (atomically $ modifyTVar counter (subtract 1)) - -withTSem :: TSem -> IO a -> IO a -withTSem sem = bracket_ (atomically $ waitTSem sem) (atomically $ signalTSem sem) - --- | Returns @Nothing@ if installing to a global database -pbDatabase :: PerformBuild -> Maybe FilePath -pbDatabase pb - | pbGlobalInstall pb = Nothing - | otherwise = Just $ pbInstallDest pb "pkgdb" - -pbBinDir, pbLibDir, pbDataDir, pbDocDir :: PerformBuild -> FilePath -pbBinDir pb = pbInstallDest pb "bin" -pbLibDir pb = pbInstallDest pb "lib" -pbDataDir pb = pbInstallDest pb "share" -pbDocDir pb = pbInstallDest pb "doc" - --- | Directory keeping previous result info -pbPrevResDir :: PerformBuild -> FilePath -pbPrevResDir pb = pbInstallDest pb "prevres" - -performBuild :: PerformBuild -> IO [Text] -performBuild pb = do - cwd <- getWorkingDirectory - performBuild' pb - { pbInstallDest = cwd pbInstallDest pb - , pbLogDir = cwd pbLogDir pb - } - -performBuild' :: PerformBuild -> IO [Text] -performBuild' pb@PerformBuild {..} = withBuildDir $ \builddir -> do - -- First make sure to fetch all of the dependencies... just in case Hackage - -- has an outage. Don't feel like wasting hours of CPU time. - pbLog $ encodeUtf8 "Pre-fetching all packages\n" - let toDownload = flip map (mapToList $ bpPackages pbPlan) - $ \(name, plan) -> unpack $ concat - [ display name - , "-" - , display $ ppVersion plan - ] - withCheckedProcess - (proc "cabal" - $ "fetch" - : "--no-dependencies" - : toDownload) - $ \ClosedStream Inherited Inherited -> return () - - let removeTree' fp = whenM (isDirectory fp) (removeTree fp) - removeTree' pbLogDir - - forM_ (pbDatabase pb) $ \db -> - unlessM (isFile $ db "package.cache") $ do - createTree $ parent db - withCheckedProcess (proc "ghc-pkg" ["init", fpToString db]) - $ \ClosedStream Inherited Inherited -> return () - pbLog $ encodeUtf8 "Copying built-in Haddocks\n" - copyBuiltInHaddocks (pbDocDir pb) - - sem <- atomically $ newTSem pbJobs - active <- newTVarIO (0 :: Int) - let toolMap = makeToolMap $ bpPackages pbPlan - packageMap <- fmap fold $ forM (mapToList $ bpPackages pbPlan) - $ \(name, plan) -> do - let piPlan = plan - piName = name - piResult <- newEmptyTMVarIO - return $ singletonMap name PackageInfo {..} - - errsVar <- newTVarIO mempty - warningsVar <- newTVarIO id - mutex <- newMVar () - env <- getEnvironment - haddockFiles <- newTVarIO mempty - - registeredPackages <- setupPackageDatabase - (pbDatabase pb) - (pbDocDir pb) - pbLog - (ppVersion <$> bpPackages pbPlan) - (deletePreviousResults pb) - - forM_ packageMap $ \pi -> void $ async $ singleBuild pb registeredPackages - SingleBuild - { sbSem = sem - , sbErrsVar = errsVar - , sbWarningsVar = warningsVar - , sbActive = active - , sbToolMap = toolMap - , sbPackageMap = packageMap - , sbBuildDir = builddir - , sbPackageInfo = pi - , sbRegisterMutex = mutex - , sbModifiedEnv = maybe - id - (\db -> (("HASKELL_PACKAGE_SANDBOX", fpToString db):)) - (pbDatabase pb) - (filter allowedEnv $ map fixEnv env) - , sbHaddockFiles = haddockFiles - } - - void $ tryAny $ atomically $ readTVar active >>= checkSTM . (== 0) - - warnings <- ($ []) <$> readTVarIO warningsVar - errs <- readTVarIO errsVar - when (not $ null errs) $ throwM $ BuildException errs warnings - return warnings - where - withBuildDir f = withSystemTempDirectory "stackage-build" (f . fpFromString) - - fixEnv (p, x) - -- Thank you Windows having case-insensitive environment variables... - | toUpper p == "PATH" = (p, fpToString (pbBinDir pb) ++ pathSep : x) - | otherwise = (p, x) - - allowedEnv (k, _) = k `notMember` bannedEnvs - - -- | Separate for the PATH environment variable - pathSep :: Char -#ifdef mingw32_HOST_OS - pathSep = ';' -#else - pathSep = ':' -#endif - --- | Environment variables we don't allow to be passed on to child processes. -bannedEnvs :: Set String -bannedEnvs = setFromList - [ "STACKAGE_AUTH_TOKEN" - ] - -data SingleBuild = SingleBuild - { sbSem :: TSem - , sbErrsVar :: TVar (Map PackageName BuildFailure) - , sbWarningsVar :: TVar ([Text] -> [Text]) - , sbActive :: TVar Int - , sbToolMap :: Map ExeName (Set PackageName) - , sbPackageMap :: Map PackageName PackageInfo - , sbBuildDir :: FilePath - , sbPackageInfo :: PackageInfo - , sbRegisterMutex :: MVar () - , sbModifiedEnv :: [(String, String)] - , sbHaddockFiles :: TVar (Map Text FilePath) -- ^ package-version, .haddock file - } - -singleBuild :: PerformBuild - -> Set PackageName -- ^ registered packages - -> SingleBuild -> IO () -singleBuild pb@PerformBuild {..} registeredPackages SingleBuild {..} = - withCounter sbActive - $ handle updateErrs - $ (`finally` void (atomically $ tryPutTMVar (piResult sbPackageInfo) False)) - $ inner - where - libComps = setFromList [CompLibrary, CompExecutable] - testComps = insertSet CompTestSuite libComps - inner = do - let wfd comps = - waitForDeps sbToolMap sbPackageMap comps pbPlan sbPackageInfo - . withTSem sbSem - withUnpacked <- wfd libComps buildLibrary - - wfd testComps (runTests withUnpacked) - - pname = piName sbPackageInfo - pident = PackageIdentifier pname (ppVersion $ piPlan sbPackageInfo) - name = display pname - namever = concat - [ name - , "-" - , display $ ppVersion $ piPlan sbPackageInfo - ] - - runIn wdir getOutH cmd args = do - outH <- getOutH - withCheckedProcess (cp outH) $ \ClosedStream UseProvidedHandle UseProvidedHandle -> - (return () :: IO ()) - where - cp outH = (proc (unpack $ asText cmd) (map (unpack . asText) args)) - { cwd = Just $ fpToString wdir - , std_out = UseHandle outH - , std_err = UseHandle outH - , env = Just sbModifiedEnv - } - runParent = runIn sbBuildDir - runChild = runIn childDir - childDir = sbBuildDir fpFromText namever - - log' t = do - i <- readTVarIO sbActive - errs <- readTVarIO sbErrsVar - pbLog $ encodeUtf8 $ concat - [ t - , " (pending: " - , tshow i - , ", failures: " - , tshow $ length errs - , ")\n" - ] - libOut = pbLogDir fpFromText namever "build.out" - testOut = pbLogDir fpFromText namever "test.out" - testRunOut = pbLogDir fpFromText namever "test-run.out" - - wf fp inner' = do - ref <- newIORef Nothing - let cleanup = do - mh <- readIORef ref - forM_ mh hClose - getH = do - mh <- readIORef ref - case mh of - Just h -> return h - Nothing -> mask_ $ do - createTree $ parent fp - h <- openBinaryFile (fpToString fp) WriteMode - writeIORef ref $ Just h - return h - - inner' getH `finally` cleanup - - configArgs = ($ []) $ execWriter $ do - when pbAllowNewer $ tell' "--allow-newer" - tell' "--package-db=clear" - tell' "--package-db=global" - forM_ (pbDatabase pb) $ \db -> tell' $ "--package-db=" ++ fpToText db - tell' $ "--libdir=" ++ fpToText (pbLibDir pb) - tell' $ "--bindir=" ++ fpToText (pbBinDir pb) - tell' $ "--datadir=" ++ fpToText (pbDataDir pb) - tell' $ "--docdir=" ++ fpToText (pbDocDir pb) - tell' $ "--flags=" ++ flags - when (pbEnableLibProfiling && pcEnableLibProfile) $ - tell' "--enable-library-profiling" - when pbEnableExecDyn $ tell' "--enable-executable-dynamic" - where - tell' x = tell (x:) - - flags :: Text - flags = unwords $ map go $ mapToList pcFlagOverrides - where - go (name', isOn) = concat - [ if isOn then "" else "-" - , unFlagName name' - ] - - PackageConstraints {..} = ppConstraints $ piPlan sbPackageInfo - - buildLibrary = wf libOut $ \getOutH -> do - let run a b = do when pbVerbose $ log' (unwords (a : b)) - runChild getOutH a b - - isUnpacked <- newIORef False - let withUnpacked inner = do - unlessM (readIORef isUnpacked) $ do - log' $ "Unpacking " ++ namever - runParent getOutH "cabal" ["unpack", namever] - writeIORef isUnpacked True - inner - - isConfiged <- newIORef False - let withConfiged inner = withUnpacked $ do - unlessM (readIORef isConfiged) $ do - log' $ "Configuring " ++ namever - run "cabal" $ "configure" : configArgs - writeIORef isConfiged True - inner - - prevBuildResult <- getPreviousResult pb Build pident - unless (prevBuildResult == PRSuccess) $ withConfiged $ do - assert (pname `notMember` registeredPackages) $ do - deletePreviousResults pb pident - - log' $ "Building " ++ namever - run "cabal" ["build"] - - log' $ "Copying/registering " ++ namever - run "cabal" ["copy"] - withMVar sbRegisterMutex $ const $ - run "cabal" ["register"] - - savePreviousResult pb Build pident True - - -- Even if the tests later fail, we can allow other libraries to build - -- on top of our successful results - -- - -- FIXME do we need to wait to do this until after Haddocks build? - -- otherwise, we could have a race condition and try to build a - -- dependency's haddocks before this finishes - atomically $ putTMVar (piResult sbPackageInfo) True - - prevHaddockResult <- getPreviousResult pb Haddock pident - let needHaddock = pbEnableHaddock - && checkPrevResult prevHaddockResult pcHaddocks - && not (null $ sdModules $ ppDesc $ piPlan sbPackageInfo) - when needHaddock $ withConfiged $ do - log' $ "Haddocks " ++ namever - hfs <- readTVarIO sbHaddockFiles - let hfsOpts = flip map (mapToList hfs) $ \(pkgVer, hf) -> concat - [ "--haddock-options=--read-interface=" - , "../" - , pkgVer - , "/," - , fpToText hf - ] - args = ($ hfsOpts) $ execWriter $ do - let tell' x = tell (x:) - tell' "haddock" - tell' "--hyperlink-source" - tell' "--html" - when pbBuildHoogle $ tell' "--hoogle" - tell' "--html-location=../$pkg-$version/" - - eres <- tryAny $ run "cabal" args - - forM_ eres $ \() -> do - renameOrCopy - (childDir "dist" "doc" "html" fpFromText name) - (pbDocDir pb fpFromText namever) - - enewPath <- tryIO - $ canonicalizePath - $ pbDocDir pb - fpFromText namever - fpFromText name <.> "haddock" - case enewPath of - Left e -> warn $ tshow e - Right newPath -> atomically - $ modifyTVar sbHaddockFiles - $ insertMap namever newPath - - savePreviousResult pb Haddock pident $ either (const False) (const True) eres - case (eres, pcHaddocks) of - (Left e, ExpectSuccess) -> throwM e - (Right (), ExpectFailure) -> warn $ namever ++ ": unexpected Haddock success" - _ -> return () - - return withUnpacked - - runTests withUnpacked = wf testOut $ \getOutH -> do - let run = runChild getOutH - - prevTestResult <- getPreviousResult pb Test pident - let needTest = pbEnableTests - && checkPrevResult prevTestResult pcTests - when needTest $ withUnpacked $ do - log' $ "Test configure " ++ namever - run "cabal" $ "configure" : "--enable-tests" : configArgs - - eres <- tryAny $ do - log' $ "Test build " ++ namever - run "cabal" ["build"] - - log' $ "Test run " ++ namever - run "cabal" ["test", "--log=" ++ fpToText testRunOut] - - savePreviousResult pb Test pident $ either (const False) (const True) eres - case (eres, pcTests) of - (Left e, ExpectSuccess) -> throwM e - (Right (), ExpectFailure) -> warn $ namever ++ ": unexpected test success" - _ -> return () - - warn t = atomically $ modifyTVar sbWarningsVar (. (t:)) - - updateErrs exc = do - log' $ concat - [ display (piName sbPackageInfo) - , ": " - , tshow exc - ] - atomically $ modifyTVar sbErrsVar $ insertMap (piName sbPackageInfo) exc' - where - exc' = - case fromException exc of - Just bf -> bf - Nothing -> BuildFailureException exc - -renameOrCopy :: FilePath -> FilePath -> IO () -renameOrCopy src dest = rename src dest `catchIO` \_ -> copyDir src dest - -copyBuiltInHaddocks :: FilePath -> IO () -copyBuiltInHaddocks docdir = do - mghc <- findExecutable "ghc" - case mghc of - Nothing -> error "GHC not found on PATH" - Just ghc -> do - src <- canonicalizePath - (parent (fpFromString ghc) "../share/doc/ghc/html/libraries") - copyDir src docdir - -------------- Previous results - --- | The previous actions that can be run -data ResultType = Build | Haddock | Test - deriving (Show, Enum, Eq, Ord, Bounded, Read) - --- | The result generated on a previous run -data PrevResult = PRNoResult | PRSuccess | PRFailure - deriving (Show, Enum, Eq, Ord, Bounded, Read) - --- | Check if we should rerun based on a PrevResult and the expected status -checkPrevResult :: PrevResult -> TestState -> Bool -checkPrevResult _ Don'tBuild = False -checkPrevResult PRNoResult _ = True -checkPrevResult PRSuccess _ = False -checkPrevResult PRFailure ExpectSuccess = True -checkPrevResult PRFailure _ = False - -withPRPath :: PerformBuild -> ResultType -> PackageIdentifier -> (FilePath -> IO a) -> IO a -withPRPath pb rt ident inner = do - createTree $ parent fp - inner fp - where - fp = pbPrevResDir pb fpFromString (show rt) fpFromText (display ident) - -successBS, failureBS :: ByteString -successBS = "success" -failureBS = "failure" - -getPreviousResult :: PerformBuild -> ResultType -> PackageIdentifier -> IO PrevResult -getPreviousResult w x y = withPRPath w x y $ \fp -> do - eres <- tryIO $ readFile fp - return $ case eres of - Right bs - | bs == successBS -> PRSuccess - | bs == failureBS -> PRFailure - _ -> PRNoResult - -savePreviousResult :: PerformBuild -> ResultType -> PackageIdentifier -> Bool -> IO () -savePreviousResult pb rt ident res = - withPRPath pb rt ident $ \fp -> writeFile fp $ - if res then successBS else failureBS - -deletePreviousResults :: PerformBuild -> PackageIdentifier -> IO () -deletePreviousResults pb name = - forM_ [minBound..maxBound] $ \rt -> - withPRPath pb rt name $ \fp -> - void $ tryIO $ removeFile fp diff --git a/Stackage/Prelude.hs b/Stackage/Prelude.hs deleted file mode 100644 index 28fff061..00000000 --- a/Stackage/Prelude.hs +++ /dev/null @@ -1,116 +0,0 @@ -{-# LANGUAGE DeriveDataTypeable #-} -{-# LANGUAGE GeneralizedNewtypeDeriving #-} -{-# LANGUAGE NoImplicitPrelude #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE TypeFamilies #-} -module Stackage.Prelude - ( module X - , module Stackage.Prelude - ) where - -import ClassyPrelude.Conduit as X -import Data.Aeson (FromJSON, ToJSON) -import Data.Conduit.Process as X -import qualified Data.Map as Map -import Data.Typeable (TypeRep, typeOf) -import Distribution.Package as X (PackageIdentifier (..), PackageName (PackageName)) -import Distribution.PackageDescription as X (FlagName (..), GenericPackageDescription) -import qualified Distribution.Text as DT -import Distribution.Version as X (Version (..), - VersionRange) -import Distribution.Version as X (withinRange) -import qualified Distribution.Version as C -import Filesystem (createTree) -import Filesystem.Path (parent) -import qualified Filesystem.Path as F - -unPackageName :: PackageName -> Text -unPackageName (PackageName str) = pack str - -unFlagName :: FlagName -> Text -unFlagName (FlagName str) = pack str - -mkPackageName :: Text -> PackageName -mkPackageName = PackageName . unpack - -mkFlagName :: Text -> FlagName -mkFlagName = FlagName . unpack - -display :: DT.Text a => a -> Text -display = fromString . DT.display - -simpleParse :: (MonadThrow m, DT.Text a, Typeable a) => Text -> m a -simpleParse orig = withTypeRep $ \rep -> - case DT.simpleParse str of - Nothing -> throwM (ParseFailedException rep (pack str)) - Just v -> return v - where - str = unpack orig - - withTypeRep :: Typeable a => (TypeRep -> m a) -> m a - withTypeRep f = - res - where - res = f (typeOf (unwrap res)) - - unwrap :: m a -> a - unwrap _ = error "unwrap" - -data ParseFailedException = ParseFailedException TypeRep Text - deriving (Show, Typeable) -instance Exception ParseFailedException - -newtype Maintainer = Maintainer { unMaintainer :: Text } - deriving (Show, Eq, Ord, Hashable, ToJSON, FromJSON, IsString) - --- | Name of an executable. -newtype ExeName = ExeName { unExeName :: Text } - deriving (Show, Eq, Ord, Hashable, ToJSON, FromJSON, IsString) - -intersectVersionRanges :: VersionRange -> VersionRange -> VersionRange -intersectVersionRanges x y = C.simplifyVersionRange $ C.intersectVersionRanges x y - --- | There seems to be a bug in Cabal where serializing and deserializing --- version ranges winds up with different representations. So we have a --- super-simplifier to deal with that. -simplifyVersionRange :: VersionRange -> VersionRange -simplifyVersionRange vr = - fromMaybe (assert False vr') $ simpleParse $ display vr' - where - vr' = C.simplifyVersionRange vr - --- | Topologically sort so that items with dependencies occur after those --- dependencies. -topologicalSort :: (Ord key, Show key, MonadThrow m, Typeable key) - => (value -> finalValue) - -> (value -> Set key) -- ^ deps - -> Map key value - -> m (Vector (key, finalValue)) -topologicalSort toFinal toDeps = - loop id . mapWithKey removeSelfDeps . fmap (toDeps &&& toFinal) - where - removeSelfDeps k (deps, final) = (deleteSet k deps, final) - loop front toProcess | null toProcess = return $ pack $ front [] - loop front toProcess - | null noDeps = throwM $ NoEmptyDeps (map fst toProcess') - | otherwise = loop (front . noDeps') (mapFromList hasDeps) - where - toProcess' = fmap (first removeUnavailable) toProcess - allKeys = Map.keysSet toProcess - removeUnavailable = asSet . setFromList . filter (`member` allKeys) . setToList - (noDeps, hasDeps) = partition (null . fst . snd) $ mapToList toProcess' - noDeps' = (map (second snd) noDeps ++) - -data TopologicalSortException key = NoEmptyDeps (Map key (Set key)) - deriving (Show, Typeable) -instance (Show key, Typeable key) => Exception (TopologicalSortException key) - -copyDir :: FilePath -> FilePath -> IO () -copyDir src dest = - runResourceT $ sourceDirectoryDeep False src $$ mapM_C go - where - src' = src "" - go fp = forM_ (F.stripPrefix src' fp) $ \suffix -> do - let dest' = dest suffix - liftIO $ createTree $ parent dest' - sourceFile fp $$ (sinkFile dest' :: Sink ByteString (ResourceT IO) ()) diff --git a/Stackage/ServerBundle.hs b/Stackage/ServerBundle.hs deleted file mode 100644 index 5aedb090..00000000 --- a/Stackage/ServerBundle.hs +++ /dev/null @@ -1,271 +0,0 @@ --- | Create a bundle to be uploaded to Stackage Server. -{-# LANGUAGE NoImplicitPrelude #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE RecordWildCards #-} -module Stackage.ServerBundle - ( serverBundle - , epochTime - , bpAllPackages - , docsListing - , createBundleV2 - , CreateBundleV2 (..) - , SnapshotType (..) - , writeIndexStyle - , DocMap - , PackageDocs (..) - ) where - -import qualified Codec.Archive.Tar as Tar -import qualified Codec.Archive.Tar.Entry as Tar -import qualified Codec.Compression.GZip as GZip -import qualified Data.Map as M -import Data.Aeson (ToJSON (..), (.=), object, FromJSON (..), (.:), withObject) -import System.IO.Temp (withTempDirectory) -import qualified Data.Yaml as Y -import Filesystem (isFile, getWorkingDirectory, listDirectory, isDirectory, canonicalizePath) -import Foreign.C.Types (CTime (CTime)) -import Stackage.BuildConstraints -import Stackage.BuildPlan -import Stackage.Prelude -import System.IO.Temp (withTempDirectory) -import qualified System.PosixCompat.Time as PC -import qualified Text.XML as X -import Text.XML.Cursor -import System.PosixCompat.Files (createSymbolicLink) - --- | Get current time -epochTime :: IO Tar.EpochTime -epochTime = (\(CTime t) -> fromIntegral t) <$> PC.epochTime - --- | All package/versions in a build plan, including core packages. --- --- Note that this may include packages not available on Hackage. -bpAllPackages :: BuildPlan -> Map PackageName Version -bpAllPackages BuildPlan {..} = - siCorePackages bpSystemInfo ++ map ppVersion bpPackages - -serverBundle :: Tar.EpochTime - -> Text -- ^ title - -> Text -- ^ slug - -> BuildPlan - -> LByteString -serverBundle time title slug bp@BuildPlan {..} = GZip.compress $ Tar.write - [ fe "build-plan.yaml" (fromStrict $ Y.encode bp) - , fe "hackage" hackage - , fe "slug" (fromStrict $ encodeUtf8 slug) - , fe "desc" (fromStrict $ encodeUtf8 title) - , fe "core" corePackagesList - ] - where - fe name contents = - case Tar.toTarPath False name of - Left s -> error s - Right name' -> (Tar.fileEntry name' contents) - { Tar.entryTime = time - } - hackage = builderToLazy $ foldMap goPair $ mapToList packageMap - - -- need to remove some packages that don't exist on Hackage - packageMap = foldr deleteMap (bpAllPackages bp) $ map PackageName - [ "bin-package-db" - , "ghc" - , "rts" - ] - - goPair (name, version) = - toBuilder (display name) ++ - toBuilder (asText "-") ++ - toBuilder (display version) ++ - toBuilder (asText "\n") - - corePackagesList = - builderToLazy $ toBuilder $ unlines $ - map (\(PackageName name) -> name) - (M.keys $ siCorePackages bpSystemInfo) - --- | Package name is key -type DocMap = Map Text PackageDocs -data PackageDocs = PackageDocs - { pdVersion :: Text - , pdModules :: Map Text [Text] - -- ^ module name, path - } -instance ToJSON PackageDocs where - toJSON PackageDocs {..} = object - [ "version" .= pdVersion - , "modules" .= pdModules - ] -instance FromJSON PackageDocs where - parseJSON = withObject "PackageDocs" $ \o -> PackageDocs - <$> o .: "version" - <*> o .: "modules" - -docsListing :: BuildPlan - -> FilePath -- ^ docs directory - -> IO DocMap -docsListing bp docsDir = - fmap fold $ mapM go $ mapToList $ bpAllPackages bp - where - go :: (PackageName, Version) -> IO DocMap - go (package, version) = do -- handleAny (const $ return mempty) $ do - let dirname = fpFromText (concat - [ display package - , "-" - , display version - ]) - indexFP = (docsDir dirname "index.html") - ie <- isFile indexFP - if ie - then do - doc <- flip X.readFile indexFP X.def - { X.psDecodeEntities = X.decodeHtmlEntities - } - let cursor = fromDocument doc - getPair x = take 1 $ do - href <- attribute "href" x - let name = concat $ x $// content - guard $ not $ null name - return (href, name) - pairs = cursor $// attributeIs "class" "module" - &/ laxElement "a" >=> getPair - m <- fmap fold $ forM pairs $ \(href, name) -> do - let suffix = dirname fpFromText href - e <- isFile $ docsDir suffix - return $ if e - then asMap $ singletonMap name [fpToText dirname, href] - else mempty - return $ singletonMap (display package) $ PackageDocs - { pdVersion = display version - , pdModules = m - } - else return mempty - -data SnapshotType = STNightly - | STLTS !Int !Int -- ^ major, minor - deriving (Show, Read, Eq, Ord) - -instance ToJSON SnapshotType where - toJSON STNightly = object - [ "type" .= asText "nightly" - ] - toJSON (STLTS major minor) = object - [ "type" .= asText "lts" - , "major" .= major - , "minor" .= minor - ] -instance FromJSON SnapshotType where - parseJSON = withObject "SnapshotType" $ \o -> do - t <- o .: "type" - case asText t of - "nightly" -> return STNightly - "lts" -> STLTS - <$> o .: "major" - <*> o .: "minor" - _ -> fail $ "Unknown type for SnapshotType: " ++ unpack t - -data CreateBundleV2 = CreateBundleV2 - { cb2Plan :: BuildPlan - , cb2Type :: SnapshotType - , cb2DocsDir :: FilePath - , cb2Dest :: FilePath - } - --- | Create a V2 bundle, which contains the build plan, metadata, docs, and doc --- map. -createBundleV2 :: CreateBundleV2 -> IO () -createBundleV2 CreateBundleV2 {..} = do - docsDir <- canonicalizePath cb2DocsDir - docMap <- docsListing cb2Plan cb2DocsDir - - Y.encodeFile (fpToString $ docsDir "build-plan.yaml") cb2Plan - Y.encodeFile (fpToString $ docsDir "build-type.yaml") cb2Type - Y.encodeFile (fpToString $ docsDir "docs-map.yaml") docMap - void $ writeIndexStyle Nothing cb2DocsDir - - currentDir <- getWorkingDirectory - files <- listDirectory docsDir - - let args = "cfJ" - : fpToString (currentDir cb2Dest) - : "--dereference" - : map (fpToString . filename) files - cp = (proc "tar" args) { cwd = Just $ fpToString docsDir } - withCheckedProcess cp $ \ClosedStream Inherited Inherited -> return () - -writeIndexStyle :: Maybe Text -- ^ snapshot id - -> FilePath -- ^ docs dir - -> IO [String] -writeIndexStyle msnapid dir = do - dirs <- fmap sort - $ runResourceT - $ sourceDirectory dir - $$ filterMC (liftIO . isDirectory) - =$ mapC (fpToString . filename) - =$ sinkList - writeFile (dir "index.html") $ mkIndex - (unpack <$> msnapid) - dirs - writeFile (dir "style.css") styleCss - return dirs - -mkIndex :: Maybe String -> [String] -> String -mkIndex msnapid dirs = concat - [ "\nHaddocks index" - , "" - , "" - , "" - , "" - , "
" - , "
" - , "

Haddock documentation index

" - , flip foldMap msnapid $ \snapid -> concat - [ "

Return to snapshot

" - ] - , "
    " - , concatMap toLI dirs - , "
" - ] - where - toLI name = concat - [ "
  • " - , name - , "
  • " - ] - -styleCss :: String -styleCss = concat - [ "@media (min-width: 530px) {" - , "ul { -webkit-column-count: 2; -moz-column-count: 2; column-count: 2 }" - , "}" - , "@media (min-width: 760px) {" - , "ul { -webkit-column-count: 3; -moz-column-count: 3; column-count: 3 }" - , "}" - , "ul {" - , " margin-left: 0;" - , " padding-left: 0;" - , " list-style-type: none;" - , "}" - , "body {" - , " background: #f0f0f0;" - , " font-family: 'Lato', sans-serif;" - , " text-shadow: 1px 1px 1px #ffffff;" - , " font-size: 20px;" - , " line-height: 30px;" - , " padding-bottom: 5em;" - , "}" - , "h1 {" - , " font-weight: normal;" - , " color: #06537d;" - , " font-size: 45px;" - , "}" - , ".return a {" - , " color: #06537d;" - , " font-style: italic;" - , "}" - , ".return {" - , " margin-bottom: 1em;" - , "}"] diff --git a/Stackage/UpdateBuildPlan.hs b/Stackage/UpdateBuildPlan.hs deleted file mode 100644 index 8c67c5ef..00000000 --- a/Stackage/UpdateBuildPlan.hs +++ /dev/null @@ -1,54 +0,0 @@ -{-# LANGUAGE NoImplicitPrelude #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE RecordWildCards #-} --- | Take an existing build plan and bump all packages to the newest version in --- the same major version number. -module Stackage.UpdateBuildPlan - ( updateBuildConstraints - , updateBuildPlan - ) where - -import qualified Data.Map as Map -import Distribution.Version (anyVersion, earlierVersion, - orLaterVersion) -import Stackage.BuildConstraints -import Stackage.BuildPlan -import Stackage.Prelude - -updateBuildPlan :: Map PackageName PackagePlan -> BuildPlan -> IO BuildPlan -updateBuildPlan packagesOrig - = newBuildPlan packagesOrig . updateBuildConstraints - -updateBuildConstraints :: BuildPlan -> BuildConstraints -updateBuildConstraints BuildPlan {..} = - BuildConstraints {..} - where - bcSystemInfo = bpSystemInfo - bcPackages = Map.keysSet bpPackages - bcGithubUsers = bpGithubUsers - - bcPackageConstraints name = PackageConstraints - { pcVersionRange = addBumpRange (maybe anyVersion pcVersionRange moldPC) - , pcMaintainer = moldPC >>= pcMaintainer - , pcTests = maybe ExpectSuccess pcTests moldPC - , pcHaddocks = maybe ExpectSuccess pcHaddocks moldPC - , pcBuildBenchmarks = maybe True pcBuildBenchmarks moldPC - , pcFlagOverrides = maybe mempty pcFlagOverrides moldPC - , pcEnableLibProfile = maybe False pcEnableLibProfile moldPC - } - where - moldBP = lookup name bpPackages - moldPC = ppConstraints <$> moldBP - - addBumpRange oldRange = - case moldBP of - Nothing -> oldRange - Just bp -> intersectVersionRanges oldRange - $ bumpRange $ ppVersion bp - - bumpRange version = intersectVersionRanges - (orLaterVersion version) - (earlierVersion $ bumpVersion version) - bumpVersion (Version (x:y:_) _) = Version [x, y + 1] [] - bumpVersion (Version [x] _) = Version [x, 1] [] - bumpVersion (Version [] _) = assert False $ Version [1, 0] [] diff --git a/Stackage/Upload.hs b/Stackage/Upload.hs deleted file mode 100644 index 64d21094..00000000 --- a/Stackage/Upload.hs +++ /dev/null @@ -1,272 +0,0 @@ --- | Upload to Stackage and Hackage -{-# LANGUAGE GeneralizedNewtypeDeriving #-} -{-# LANGUAGE NoImplicitPrelude #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE RecordWildCards #-} -{-# LANGUAGE TupleSections #-} -module Stackage.Upload - ( UploadBundle (..) - , SnapshotIdent (..) - , uploadBundle - , UploadDocs (..) - , uploadDocs - , uploadHackageDistro - , uploadHackageDistroNamed - , UploadDocMap (..) - , uploadDocMap - , uploadBundleV2 - , UploadBundleV2 (..) - , def - , StackageServer - , unStackageServer - ) where - -import Control.Monad.Writer.Strict (execWriter, tell) -import Data.Default.Class (Default (..)) -import Data.Function (fix) -import Filesystem (isDirectory, isFile) -import Network.HTTP.Client -import qualified Network.HTTP.Client.Conduit as HCC -import Network.HTTP.Client.MultipartFormData -import Stackage.BuildPlan (BuildPlan) -import Stackage.Prelude -import Stackage.ServerBundle (bpAllPackages, docsListing, writeIndexStyle) -import System.IO.Temp (withSystemTempFile) -import qualified System.IO as IO -import qualified Data.Yaml as Y - -newtype StackageServer = StackageServer { unStackageServer :: Text } - deriving (Show, Eq, Ord, Hashable, IsString) -instance Default StackageServer where - def = "http://www.stackage.org" - -data UploadBundle = UploadBundle - { ubServer :: StackageServer - , ubContents :: LByteString - , ubAlias :: Maybe Text - , ubNightly :: Maybe Text -- ^ should be GHC version - , ubLTS :: Maybe Text -- ^ e.g. 2.3 - , ubAuthToken :: Text - } -instance Default UploadBundle where - def = UploadBundle - { ubServer = def - , ubContents = mempty - , ubAlias = Nothing - , ubNightly = Nothing - , ubLTS = Nothing - , ubAuthToken = "no-auth-token-provided" - } - -newtype SnapshotIdent = SnapshotIdent { unSnapshotIdent :: Text } - deriving (Show, Eq, Ord, Hashable, IsString) - -uploadBundle :: UploadBundle -> Manager -> IO (SnapshotIdent, Maybe Text) -uploadBundle UploadBundle {..} man = do - req1 <- parseUrl $ unpack $ unStackageServer ubServer ++ "/upload" - req2 <- formDataBody formData req1 - let req3 = req2 - { method = "PUT" - , requestHeaders = - [ ("Authorization", encodeUtf8 ubAuthToken) - , ("Accept", "application/json") - ] ++ requestHeaders req2 - , redirectCount = 0 - , checkStatus = \_ _ _ -> Nothing - , responseTimeout = Just 300000000 - } - res <- httpLbs req3 man - case lookup "x-stackage-ident" $ responseHeaders res of - Just snapid -> return - ( SnapshotIdent $ decodeUtf8 snapid - , decodeUtf8 <$> lookup "location" (responseHeaders res) - ) - Nothing -> error $ "An error occurred: " ++ show res - where - params = mapMaybe (\(x, y) -> (x, ) <$> y) - [ ("alias", ubAlias) - , ("nightly", ubNightly) - , ("lts", ubLTS) - ] - formData = ($ []) $ execWriter $ do - forM_ params $ \(key, value) -> - tell' $ partBS key $ encodeUtf8 value - tell' $ partFileRequestBody "stackage" "stackage" - $ RequestBodyLBS ubContents - - tell' x = tell (x:) - -data UploadDocs = UploadDocs - { udServer :: StackageServer - , udDocs :: FilePath -- ^ may be a directory or a tarball - , udAuthToken :: Text - , udSnapshot :: SnapshotIdent - } - -uploadDocs :: UploadDocs -> Manager -> IO (Response LByteString) -uploadDocs (UploadDocs (StackageServer host) fp0 token ident) man = do - fe <- isFile fp0 - if fe - then uploadDocsFile $ fpToString fp0 - else do - de <- isDirectory fp0 - if de - then uploadDocsDir - else error $ "Path not found: " ++ fpToString fp0 - where - uploadDocsDir = withSystemTempFile "haddocks.tar.xz" $ \fp h -> do - hClose h - dirs <- writeIndexStyle (Just $ unSnapshotIdent ident) fp0 - let cp = (proc "tar" $ "cJf" : fp : "index.html" : "style.css" : dirs) - { cwd = Just $ fpToString fp0 - } - withCheckedProcess cp $ \Inherited Inherited Inherited -> return () - uploadDocsFile fp - uploadDocsFile fp = do - req1 <- parseUrl $ unpack $ concat - [ host - , "/upload-haddock/" - , unSnapshotIdent ident - ] - let formData = - [ partFileSource "tarball" fp - ] - req2 <- formDataBody formData req1 - let req3 = req2 - { method = "PUT" - , requestHeaders = - [ ("Authorization", encodeUtf8 token) - , ("Accept", "application/json") - ] ++ requestHeaders req2 - , redirectCount = 0 - , checkStatus = \_ _ _ -> Nothing - , responseTimeout = Just 300000000 - } - httpLbs req3 man - -uploadHackageDistro :: BuildPlan - -> ByteString -- ^ Hackage username - -> ByteString -- ^ Hackage password - -> Manager - -> IO (Response LByteString) -uploadHackageDistro = uploadHackageDistroNamed "Stackage" - -uploadHackageDistroNamed - :: Text -- ^ distro name - -> BuildPlan - -> ByteString -- ^ Hackage username - -> ByteString -- ^ Hackage password - -> Manager - -> IO (Response LByteString) -uploadHackageDistroNamed name bp username password manager = do - req1 <- parseUrl $ concat - [ "http://hackage.haskell.org/distro/" - , unpack name - , "/packages.csv" - ] - let req2 = req1 - { requestHeaders = [("Content-Type", "text/csv")] - , requestBody = RequestBodyLBS csv - , checkStatus = \_ _ _ -> Nothing - , method = "PUT" - } - httpLbs (applyBasicAuth username password req2) manager - where - csv = encodeUtf8 - $ builderToLazy - $ mconcat - $ intersperse "\n" - $ map go - $ mapToList - $ bpAllPackages bp - go (name, version) = - "\"" ++ - (toBuilder $ display name) ++ - "\",\"" ++ - (toBuilder $ display version) ++ - "\",\"http://www.stackage.org/package/" ++ - (toBuilder $ display name) ++ - "\"" - -data UploadDocMap = UploadDocMap - { udmServer :: StackageServer - , udmAuthToken :: Text - , udmSnapshot :: SnapshotIdent - , udmDocDir :: FilePath - , udmPlan :: BuildPlan - } - -uploadDocMap :: UploadDocMap -> Manager -> IO (Response LByteString) -uploadDocMap UploadDocMap {..} man = do - docmap <- docsListing udmPlan udmDocDir - req1 <- parseUrl $ unpack $ unStackageServer udmServer ++ "/upload-doc-map" - req2 <- formDataBody (formData $ Y.encode docmap) req1 - let req3 = req2 - { method = "PUT" - , requestHeaders = - [ ("Authorization", encodeUtf8 udmAuthToken) - , ("Accept", "application/json") - ] ++ requestHeaders req2 - , redirectCount = 0 - , checkStatus = \_ _ _ -> Nothing - , responseTimeout = Just 300000000 - } - httpLbs req3 man - where - formData docmap = - [ partBS "snapshot" (encodeUtf8 $ unSnapshotIdent udmSnapshot) - , partFileRequestBody "docmap" "docmap" $ RequestBodyBS docmap - ] - -data UploadBundleV2 = UploadBundleV2 - { ub2Server :: StackageServer - , ub2AuthToken :: Text - , ub2Bundle :: FilePath - } - -uploadBundleV2 :: UploadBundleV2 -> Manager -> IO Text -uploadBundleV2 UploadBundleV2 {..} man = IO.withBinaryFile (fpToString ub2Bundle) IO.ReadMode $ \h -> do - size <- IO.hFileSize h - putStrLn $ "Bundle size: " ++ tshow size - req1 <- parseUrl $ unpack $ unStackageServer ub2Server ++ "/upload2" - let req2 = req1 - { method = "PUT" - , requestHeaders = - [ ("Authorization", encodeUtf8 ub2AuthToken) - , ("Accept", "application/json") - , ("Content-Type", "application/x-tar") - ] - , requestBody = HCC.requestBodySource (fromIntegral size) - $ sourceHandle h $= printProgress size - } - sink = decodeUtf8C =$ fix (\loop -> do - mx <- peekC - case mx of - Nothing -> error $ "uploadBundleV2: premature end of stream" - Just _ -> do - l <- lineC $ takeCE 4096 =$ foldC - let (cmd, msg') = break (== ':') l - msg = dropWhile (== ' ') $ dropWhile (== ':') msg' - case cmd of - "CONT" -> do - putStrLn msg - loop - "FAILURE" -> error $ "uploadBundleV2 failed: " ++ unpack msg - "SUCCESS" -> return msg - _ -> error $ "uploadBundleV2: unknown command " ++ unpack cmd - ) - withResponse req2 man $ \res -> HCC.bodyReaderSource (responseBody res) $$ sink - where - printProgress total = - loop 0 0 - where - loop sent lastPercent = - await >>= maybe (putStrLn "Upload complete") go - where - go bs = do - yield bs - let sent' = sent + fromIntegral (length bs) - percent = sent' * 100 `div` total - when (percent /= lastPercent) - $ putStrLn $ "Upload progress: " ++ tshow percent ++ "%" - loop sent' percent diff --git a/app/stackage.hs b/app/stackage.hs deleted file mode 100644 index d2618da2..00000000 --- a/app/stackage.hs +++ /dev/null @@ -1,210 +0,0 @@ -{-# LANGUAGE TupleSections #-} - -module Main where - -import Control.Monad -import Data.Monoid -import Data.String (fromString) -import Data.Version -import Options.Applicative -import Filesystem.Path.CurrentOS (decodeString) -import Paths_stackage (version) -import Stackage.CompleteBuild -import Stackage.Upload -import Stackage.InstallBuild -import Network.HTTP.Client (withManager) -import Network.HTTP.Client.TLS (tlsManagerSettings) -import qualified Data.Text as T - -main :: IO () -main = - join $ - execParser $ - info - (helpOption <*> versionOption <*> config) - (header "Stackage" <> - fullDesc) - where - helpOption = - abortOption ShowHelpText $ - long "help" <> - help "Show this help text" - versionOption = - infoOption - ("stackage version " ++ showVersion version) - (long "version" <> - help "Show stackage version") - config = - subparser $ - mconcat - [ cmnd - (uncurry completeBuild) - (fmap (Nightly, ) buildFlags) - "nightly" - "Build, test and upload the Nightly snapshot" - , cmnd - (uncurry completeBuild) - (fmap (LTS Major, ) buildFlags) - "lts-major" - "Build, test and upload the LTS (major) snapshot" - , cmnd - (uncurry completeBuild) - (fmap (LTS Minor, ) buildFlags) - "lts-minor" - "Build, test and upload the LTS (minor) snapshot" - , cmnd - justUploadNightly - nightlyUploadFlags - "upload-nightly" - "Upload an already-built nightly snapshot" - , cmnd - (const justCheck) - (pure ()) - "check" - "Just check that the build plan is ok" - , cmnd - installBuild - installFlags - "install" - "Install a snapshot from an existing build plan" - , cmnd - uploadv2 - uploadv2Flags - "upload2" - "Upload a pre-existing v2 bundle" - ] - - cmnd exec parse name desc = - command name $ - info - (fmap exec (parse <**> helpOption)) - (progDesc desc) - - buildFlags = - BuildFlags <$> - fmap - not - (switch - (long "skip-tests" <> - help "Skip build and running the test suites")) <*> - fmap - not - (switch - (long "skip-haddock" <> - help "Skip generating haddock documentation")) <*> - fmap - not - (switch - (long "skip-upload" <> - help "Skip uploading bundle, docs, etc.")) <*> - switch - (long "enable-library-profiling" <> - help "Enable profiling when building") <*> - switch - (long "enable-executable-dynamic" <> - help "Enable dynamic executables when building") <*> - switch - (long "verbose" <> short 'v' <> - help "Output verbose detail about the build steps") <*> - switch - (long "skip-check" <> - help "Skip the check phase, and pass --allow-newer to cabal configure") <*> - switch - (long "upload-v1" <> - help "Use the V1 upload code") <*> - (fmap fromString (strOption - (long "server-url" <> - metavar "SERVER-URL" <> - showDefault <> value (T.unpack $ unStackageServer def) <> - help "Server to upload bundle to"))) <*> - fmap - not - (switch - (long "skip-hoogle" <> - help "Skip generating Hoogle input files")) - - nightlyUploadFlags = fromString <$> strArgument - (metavar "DATE" <> - help "Date, in YYYY-MM-DD format") - - installFlags = - InstallFlags <$> - (fmap - BPSBundleWeb - (strOption - (long "bundle" <> - metavar "URL" <> - help "Stackage bundle containing build plan")) <|> - fmap - (BPSFile . decodeString) - (strOption - (long "build-plan" <> - metavar "PATH" <> - help "Build-plan YAML file"))) <*> - fmap - decodeString - (strArgument - (metavar "DESTINATION-PATH" <> - help "Destination directory path")) <*> - (fmap - (Just . decodeString) - (strOption - (long "log-dir" <> - metavar "PATH" <> - help "Location of log files (default DESTINATION-PATH/logs)")) <|> - pure Nothing) <*> - option - auto - (long "jobs" <> - metavar "NUMBER" <> - showDefault <> value 8 <> - help "Number of threads") <*> - switch - (long "global" <> - help "Install in global package database") <*> - fmap - not - (switch - (long "skip-tests" <> - help "Skip build and running the test suites")) <*> - fmap - not - (switch - (long "skip-haddock" <> - help "Skip generating haddock documentation")) <*> - switch - (long "enable-library-profiling" <> - help "Enable profiling when building") <*> - switch - (long "enable-executable-dynamic" <> - help "Enable dynamic executables when building") <*> - switch - (long "verbose" <> short 'v' <> - help "Output verbose detail about the build steps") <*> - switch - (long "skip-check" <> - help "Skip the check phase, and pass --allow-newer to cabal configure") <*> - fmap - not - (switch - (long "skip-hoogle" <> - help "Skip generating Hoogle input files")) - - uploadv2 (path, url) = withManager tlsManagerSettings $ \man -> do - token <- getStackageAuthToken - res <- flip uploadBundleV2 man UploadBundleV2 - { ub2AuthToken = token - , ub2Server = fromString url - , ub2Bundle = decodeString path - } - putStrLn $ "New URL: " ++ T.unpack res - - uploadv2Flags = (,) - <$> (strArgument - (metavar "BUNDLE-PATH" <> - help "Bundle path")) - <*> strOption - (long "server-url" <> - metavar "SERVER-URL" <> - showDefault <> value (T.unpack $ unStackageServer def) <> - help "Server to upload bundle to") diff --git a/build-constraints.yaml b/build-constraints.yaml index 7596251a..206af9e8 100644 --- a/build-constraints.yaml +++ b/build-constraints.yaml @@ -93,6 +93,7 @@ packages: - shelly - smtLib - stackage + - stackage-curator - statistics-linreg - th-expand-syns - thyme diff --git a/cabal.config b/cabal.config deleted file mode 100644 index cc656768..00000000 --- a/cabal.config +++ /dev/null @@ -1,847 +0,0 @@ --- Stackage snapshot from: http://www.stackage.org/snapshot/nightly-2014-12-24 --- Please place this file next to your .cabal file as cabal.config --- To only use tested packages, uncomment the following line: --- remote-repo: stackage-nightly-2014-12-24:http://www.stackage.org/snapshot/nightly-2014-12-24 -constraints: abstract-deque ==0.3, - abstract-par ==0.3.3, - accelerate ==0.15.0.0, - ace ==0.6, - action-permutations ==0.0.0.1, - active ==0.1.0.17, - AC-Vector ==2.3.2, - ad ==4.2.1.1, - adjunctions ==4.2, - aeson ==0.8.0.2, - aeson-pretty ==0.7.2, - aeson-qq ==0.7.4, - aeson-utils ==0.2.2.1, - alarmclock ==0.2.0.5, - alex ==3.1.3, - amqp ==0.10.1, - ansi-terminal ==0.6.2.1, - ansi-wl-pprint ==0.6.7.1, - appar ==0.1.4, - approximate ==0.2.1.1, - arbtt ==0.8.1.4, - arithmoi ==0.4.1.1, - array installed, - arrow-list ==0.6.1.5, - asn1-data ==0.7.1, - asn1-encoding ==0.9.0, - asn1-parse ==0.9.0, - asn1-types ==0.3.0, - async ==2.0.2, - atto-lisp ==0.2.2, - attoparsec ==0.12.1.2, - attoparsec-conduit ==1.1.0, - attoparsec-enumerator ==0.3.3, - attoparsec-expr ==0.1.1.1, - authenticate ==1.3.2.11, - auto-update ==0.1.2.1, - aws ==0.11, - bake ==0.2, - bank-holidays-england ==0.1.0.1, - barecheck ==0.2.0.6, - base16-bytestring ==0.1.1.6, - base64-bytestring ==1.0.0.1, - base-compat ==0.5.0, - base-prelude ==0.1.8, - base-unicode-symbols ==0.2.2.4, - basic-prelude ==0.3.10, - bifunctors ==4.2, - binary installed, - binary-list ==1.0.1.0, - bindings-DSL ==1.0.21, - bioace ==0.0.1, - bioalign ==0.0.5, - biocore ==0.3.1, - biofasta ==0.0.3, - biofastq ==0.1, - biophd ==0.0.5, - biopsl ==0.4, - biosff ==0.3.7.1, - bits ==0.4, - BlastHTTP ==1.0.1, - blastxml ==0.3.2, - blaze-builder ==0.3.3.4, - blaze-builder-enumerator ==0.2.0.6, - blaze-html ==0.7.0.3, - blaze-markup ==0.6.1.1, - blaze-svg ==0.3.4, - blaze-textual ==0.2.0.9, - BlogLiterately ==0.7.1.7, - BlogLiterately-diagrams ==0.1.4.3, - bloodhound ==0.5.0.1, - bmp ==1.2.5.2, - Boolean ==0.2.3, - bool-extras ==0.4.0, - bound ==1.0.4, - BoundedChan ==1.0.3.0, - bson ==0.3.1, - bumper ==0.6.0.2, - byteable ==0.1.1, - bytedump ==1.0, - byteorder ==1.0.4, - bytes ==0.14.1.2, - bytestring installed, - bytestring-builder ==0.10.4.0.1, - bytestring-lexing ==0.4.3.2, - bytestring-mmap ==0.2.2, - bytestring-progress ==1.0.3, - bytestring-trie ==0.2.4, - bzlib ==0.5.0.4, - bzlib-conduit ==0.2.1.3, - c2hs ==0.20.1, - Cabal installed, - cabal-install ==1.18.0.6, - cabal-src ==0.2.5, - cairo ==0.13.0.5, - case-insensitive ==1.2.0.3, - cases ==0.1.2, - cassava ==0.4.2.1, - cautious-file ==1.0.2, - cereal ==0.4.1.0, - cereal-conduit ==0.7.2.3, - certificate ==1.3.9, - charset ==0.3.7, - Chart ==1.3.2, - Chart-diagrams ==1.3.2, - ChasingBottoms ==1.3.0.8, - check-email ==1.0, - checkers ==0.4.1, - chell ==0.4, - chell-quickcheck ==0.2.4, - chunked-data ==0.1.0.1, - cipher-aes ==0.2.9, - cipher-blowfish ==0.0.3, - cipher-camellia ==0.0.2, - cipher-des ==0.0.6, - cipher-rc4 ==0.1.4, - circle-packing ==0.1.0.3, - classy-prelude ==0.10.2, - classy-prelude-conduit ==0.10.2, - classy-prelude-yesod ==0.10.2, - clientsession ==0.9.1.1, - clock ==0.4.1.3, - cmdargs ==0.10.12, - code-builder ==0.1.3, - colour ==2.3.3, - comonad ==4.2.2, - comonads-fd ==4.0, - comonad-transformers ==4.0, - compdata ==0.9, - compensated ==0.6.1, - composition ==1.0.1.0, - compressed ==3.10, - concatenative ==1.0.1, - concurrent-extra ==0.7.0.9, - concurrent-supply ==0.1.7, - cond ==0.4.1.1, - conduit ==1.2.3.1, - conduit-combinators ==0.3.0.5, - conduit-extra ==1.1.5.1, - configurator ==0.3.0.0, - connection ==0.2.3, - constraints ==0.4.1.1, - containers installed, - containers-unicode-symbols ==0.3.1.1, - contravariant ==1.2, - control-monad-free ==0.5.3, - control-monad-loop ==0.1, - convertible ==1.1.0.0, - cookie ==0.4.1.4, - courier ==0.1.0.15, - cpphs ==1.18.6, - cprng-aes ==0.6.1, - cpu ==0.1.2, - criterion ==1.0.2.0, - crypto-api ==0.13.2, - cryptocipher ==0.6.2, - crypto-cipher-tests ==0.0.11, - crypto-cipher-types ==0.0.9, - cryptohash ==0.11.6, - cryptohash-conduit ==0.1.1, - cryptohash-cryptoapi ==0.1.3, - crypto-numbers ==0.2.3, - crypto-pubkey ==0.2.6, - crypto-pubkey-types ==0.4.2.3, - crypto-random ==0.0.8, - crypto-random-api ==0.2.0, - css-text ==0.1.2.1, - csv ==0.1.2, - csv-conduit ==0.6.3, - curl ==1.3.8, - data-accessor ==0.2.2.6, - data-accessor-mtl ==0.2.0.4, - data-binary-ieee754 ==0.4.4, - data-default ==0.5.3, - data-default-class ==0.0.1, - data-default-instances-base ==0.0.1, - data-default-instances-containers ==0.0.1, - data-default-instances-dlist ==0.0.1, - data-default-instances-old-locale ==0.0.1, - data-inttrie ==0.1.0, - data-lens-light ==0.1.2.1, - data-memocombinators ==0.5.1, - data-reify ==0.6, - DAV ==1.0.3, - deepseq installed, - deepseq-generics ==0.1.1.2, - derive ==2.5.18, - diagrams ==1.2, - diagrams-builder ==0.6.0.2, - diagrams-cairo ==1.2.0.4, - diagrams-contrib ==1.1.2.4, - diagrams-core ==1.2.0.4, - diagrams-haddock ==0.2.2.12, - diagrams-lib ==1.2.0.7, - diagrams-postscript ==1.1.0.3, - diagrams-svg ==1.1.0.3, - Diff ==0.3.0, - digest ==0.0.1.2, - digestive-functors ==0.7.1.3, - dimensional ==0.13.0.1, - directory installed, - directory-tree ==0.12.0, - direct-sqlite ==2.3.14, - distributed-process ==0.5.3, - distributed-process-async ==0.2.0, - distributed-process-client-server ==0.1.1, - distributed-process-execution ==0.1.0, - distributed-process-extras ==0.1.1, - distributed-process-simplelocalnet ==0.2.2.0, - distributed-process-supervisor ==0.1.1, - distributed-process-task ==0.1.0, - distributed-static ==0.3.1.0, - distributive ==0.4.4, - djinn-ghc ==0.0.2.2, - djinn-lib ==0.0.1.2, - dlist ==0.7.1, - dlist-instances ==0.1, - doctest ==0.9.11.1, - double-conversion ==2.0.1.0, - dual-tree ==0.2.0.5, - easy-file ==0.2.0, - either ==4.3.2.1, - elm-build-lib ==0.14.0.0, - elm-compiler ==0.14, - elm-core-sources ==1.0.0, - elm-package ==0.2.2, - email-validate ==2.0.1, - enclosed-exceptions ==1.0.1, - entropy ==0.3.4.1, - enumerator ==0.4.20, - eq ==4.0.3, - erf ==2.0.0.0, - errorcall-eq-instance ==0.1.0, - errors ==1.4.7, - ersatz ==0.2.6.1, - esqueleto ==2.1.2.1, - exceptions ==0.6.1, - exception-transformers ==0.3.0.4, - executable-path ==0.0.3, - ex-pool ==0.2, - extensible-exceptions ==0.1.1.4, - extra ==1.0, - failure ==0.2.0.3, - fast-logger ==2.2.3, - fay ==0.21.2.1, - fay-base ==0.19.4.1, - fay-builder ==0.2.0.1, - fay-dom ==0.5, - fay-jquery ==0.6.0.2, - fay-text ==0.3.2, - fay-uri ==0.2.0.0, - fb ==1.0.7, - fb-persistent ==0.3.4, - fclabels ==2.0.2, - FenwickTree ==0.1.1, - fgl ==5.5.0.1, - file-embed ==0.0.7, - file-location ==0.4.5.3, - filemanip ==0.3.6.2, - filepath installed, - fingertree ==0.1.0.0, - fixed ==0.2.1, - fixed-list ==0.1.5, - flexible-defaults ==0.0.1.1, - focus ==0.1.3, - foldl ==1.0.7, - force-layout ==0.3.0.8, - foreign-store ==0.1, - formatting ==6.0.0, - fpco-api ==1.2.0.4, - free ==4.10.0.1, - freenect ==1.2, - frisby ==0.2, - fsnotify ==0.1.0.3, - fuzzcheck ==0.1.1, - gd ==3000.7.3, - generic-aeson ==0.2.0.2, - generic-deriving ==1.6.3, - generics-sop ==0.1.0.4, - ghc-heap-view ==0.5.3, - ghcid ==0.3.3, - ghc-mod ==5.2.1.1, - ghc-mtl ==1.2.1.0, - ghc-paths ==0.1.0.9, - ghc-prim installed, - ghc-syb-utils ==0.2.2, - gio ==0.13.0.3, - git-embed ==0.1.0, - gl ==0.6.2, - glib ==0.13.0.6, - Glob ==0.7.5, - GLURaw ==1.4.0.1, - GLUT ==2.5.1.1, - graph-core ==0.2.1.0, - graphs ==0.5.0.1, - graphviz ==2999.17.0.1, - gravatar ==0.6, - groundhog ==0.7.0.1, - groundhog-mysql ==0.7.0.1, - groundhog-postgresql ==0.7.0.1, - groundhog-sqlite ==0.7.0.1, - groundhog-th ==0.7.0, - groupoids ==4.0, - groups ==0.4.0.0, - gtk ==0.13.3, - gtk2hs-buildtools ==0.13.0.3, - haddock-api ==2.15.0.1, - haddock-library ==1.1.1, - half ==0.2.0.1, - HandsomeSoup ==0.3.5, - happstack-server ==7.3.9, - happy ==1.19.4, - hashable ==1.2.3.1, - hashable-extras ==0.2.0.1, - hashmap ==1.3.0.1, - hashtables ==1.2.0.1, - haskeline installed, - haskell2010 installed, - haskell98 installed, - haskell-lexer ==1.0, - haskell-names ==0.4.1, - haskell-packages ==0.2.4.3, - haskell-src ==1.0.1.6, - haskell-src-exts ==1.16.0.1, - haskell-src-meta ==0.6.0.8, - hasql ==0.4.1, - hasql-backend ==0.2.2, - hasql-postgres ==0.9.1, - hastache ==0.6.1, - HaTeX ==3.16.0.0, - HaXml ==1.24.1, - haxr ==3000.10.3.1, - HCodecs ==0.5, - hdaemonize ==0.5.0.0, - hdevtools ==0.1.0.6, - heaps ==0.3.1, - hebrew-time ==0.1.1, - heist ==0.14.0.1, - here ==1.2.6, - heredoc ==0.2.0.0, - highlighting-kate ==0.5.11.1, - hinotify ==0.3.7, - hint ==0.4.2.1, - histogram-fill ==0.8.3.0, - hit ==0.6.2, - hjsmin ==0.1.4.7, - hledger ==0.23.3, - hledger-lib ==0.23.3, - hlibgit2 ==0.18.0.13, - hlint ==1.9.13, - hmatrix ==0.16.1.2, - hmatrix-gsl ==0.16.0.2, - holy-project ==0.1.1.1, - hoogle ==4.2.36, - hoopl installed, - hOpenPGP ==1.11, - hopenpgp-tools ==0.13, - hostname ==1.0, - hostname-validate ==1.0.0, - hourglass ==0.2.6, - hpc installed, - hPDB ==1.2.0, - hPDB-examples ==1.1.2, - hs-bibutils ==5.5, - hscolour ==1.20.3, - hse-cpp ==0.1, - hslogger ==1.2.6, - hslua ==0.3.13, - hspec ==2.1.2, - hspec2 ==0.6.1, - hspec-core ==2.1.2, - hspec-discover ==2.1.2, - hspec-expectations ==0.6.1, - hspec-meta ==2.0.0, - hspec-wai ==0.6.2, - hspec-wai-json ==0.6.0, - HStringTemplate ==0.7.3, - hsyslog ==2.0, - HTF ==0.12.2.3, - html ==1.0.1.2, - html-conduit ==1.1.1.1, - HTTP ==4000.2.19, - http-client ==0.4.6.1, - http-client-tls ==0.2.2, - http-conduit ==2.1.5, - http-date ==0.0.4, - http-reverse-proxy ==0.4.1.2, - http-types ==0.8.5, - HUnit ==1.2.5.2, - hweblib ==0.6.3, - hxt ==9.3.1.10, - hxt-charproperties ==9.2.0.0, - hxt-http ==9.1.5, - hxt-pickle-utils ==0.1.0.2, - hxt-regex-xmlschema ==9.2.0, - hxt-relaxng ==9.1.5.1, - hxt-unicode ==9.0.2.2, - hybrid-vectors ==0.1.2, - hyphenation ==0.4, - idna ==0.3.0, - ieee754 ==0.7.4, - imagesize-conduit ==1.0.0.4, - immortal ==0.2, - incremental-parser ==0.2.3.3, - indents ==0.3.3, - ini ==0.2.2, - integer-gmp installed, - integration ==0.2.0.1, - interpolate ==0.1.0, - interpolatedstring-perl6 ==0.9.0, - intervals ==0.7.0.1, - io-choice ==0.0.5, - io-manager ==0.1.0.2, - io-memoize ==1.1.1.0, - iproute ==1.3.1, - iterable ==3.0, - ixset ==1.0.6, - js-flot ==0.8.3, - js-jquery ==1.11.1, - json-schema ==0.7.3.0, - JuicyPixels ==3.1.7.1, - JuicyPixels-repa ==0.7, - kan-extensions ==4.1.1, - kdt ==0.2.2, - keter ==1.3.7.1, - keys ==3.10.1, - kure ==2.4.10, - language-c ==0.4.7, - language-ecmascript ==0.16.2, - language-glsl ==0.1.1, - language-haskell-extract ==0.2.4, - language-java ==0.2.7, - language-javascript ==0.5.13, - lazy-csv ==0.5, - lca ==0.2.4, - lens ==4.6.0.1, - lens-aeson ==1.0.0.3, - lens-family-th ==0.4.0.0, - lhs2tex ==1.18.1, - libgit ==0.3.0, - libnotify ==0.1.1.0, - lifted-async ==0.2.0.2, - lifted-base ==0.2.3.3, - linear ==1.15.5, - linear-accelerate ==0.2, - list-t ==0.3.1, - loch-th ==0.2.1, - log-domain ==0.9.3, - logfloat ==0.12.1, - logict ==0.6.0.2, - loop ==0.2.0, - lucid ==2.5, - machines ==0.4.1, - mandrill ==0.1.1.0, - map-syntax ==0.2, - markdown ==0.1.13, - markdown-unlit ==0.2.0.1, - math-functions ==0.1.5.2, - matrix ==0.3.4.0, - MaybeT ==0.1.2, - MemoTrie ==0.6.2, - mersenne-random-pure64 ==0.2.0.4, - messagepack ==0.3.0, - messagepack-rpc ==0.1.0.3, - mime-mail ==0.4.6.2, - mime-mail-ses ==0.3.2.1, - mime-types ==0.1.0.5, - missing-foreign ==0.1.1, - MissingH ==1.3.0.1, - mmap ==0.5.9, - mmorph ==1.0.4, - MonadCatchIO-transformers ==0.3.1.3, - monad-control ==0.3.3.0, - monad-coroutine ==0.8.0.1, - monadcryptorandom ==0.6.1, - monad-extras ==0.5.9, - monadic-arrays ==0.2.1.3, - monad-journal ==0.6.0.2, - monad-logger ==0.3.11.1, - monad-loops ==0.4.2.1, - monad-par ==0.3.4.7, - monad-parallel ==0.7.1.3, - monad-par-extras ==0.3.3, - monad-primitive ==0.1, - monad-products ==4.0.0.1, - MonadPrompt ==1.0.0.5, - MonadRandom ==0.3.0.1, - monad-st ==0.2.4, - monads-tf ==0.1.0.2, - mongoDB ==2.0.3, - monoid-extras ==0.3.3.5, - monoid-subclasses ==0.3.6.2, - mono-traversable ==0.7.0, - mtl ==2.1.3.1, - mtlparse ==0.1.2, - mtl-prelude ==1.0.1, - multimap ==1.2.1, - multipart ==0.1.2, - MusicBrainz ==0.2.2, - mwc-random ==0.13.2.2, - mysql ==0.1.1.7, - mysql-simple ==0.2.2.4, - nanospec ==0.2.0, - nats ==1, - neat-interpolation ==0.2.2, - nettle ==0.1.0, - network ==2.6.0.2, - network-conduit-tls ==1.1.0.2, - network-info ==0.2.0.5, - network-multicast ==0.0.11, - network-simple ==0.4.0.2, - network-transport ==0.4.1.0, - network-transport-tcp ==0.4.1, - network-transport-tests ==0.2.1.0, - network-uri ==2.6.0.1, - newtype ==0.2, - nsis ==0.2.4, - numbers ==3000.2.0.1, - numeric-extras ==0.0.3, - NumInstances ==1.4, - numtype ==1.1, - Octree ==0.5.3, - old-locale installed, - old-time installed, - OneTuple ==0.2.1, - opaleye ==0.3, - OpenGL ==2.9.2.0, - OpenGLRaw ==1.5.0.0, - openpgp-asciiarmor ==0.1, - operational ==0.2.3.2, - options ==1.2.1, - optparse-applicative ==0.11.0.1, - osdkeys ==0.0, - pandoc ==1.13.2, - pandoc-citeproc ==0.6, - pandoc-types ==1.12.4.1, - pango ==0.13.0.4, - parallel ==3.2.0.5, - parallel-io ==0.3.3, - parseargs ==0.1.5.2, - parsec ==3.1.7, - parsers ==0.12.1.1, - partial-handler ==0.1.0, - path-pieces ==0.1.5, - patience ==0.1.1, - pcre-light ==0.4.0.3, - pdfinfo ==1.5.1, - pem ==0.2.2, - persistent ==2.1.1.3, - persistent-mongoDB ==2.1.2, - persistent-mysql ==2.1.2, - persistent-postgresql ==2.1.2, - persistent-sqlite ==2.1.1.2, - persistent-template ==2.1.0.1, - phantom-state ==0.2.0.2, - pipes ==4.1.4, - pipes-concurrency ==2.0.2, - pipes-parse ==3.0.2, - placeholders ==0.1, - pointed ==4.1.1, - polyparse ==1.9, - pool-conduit ==0.1.2.3, - postgresql-binary ==0.5.0, - postgresql-libpq ==0.9.0.1, - postgresql-simple ==0.4.8.0, - pqueue ==1.2.1, - prefix-units ==0.1.0.2, - prelude-extras ==0.4, - present ==2.2, - pretty installed, - prettyclass ==1.0.0.0, - pretty-class ==1.0.1.1, - pretty-show ==1.6.8, - primes ==0.2.1.0, - primitive ==0.5.4.0, - process installed, - process-conduit ==1.2.0.1, - process-extras ==0.2.0, - product-profunctors ==0.6, - profunctor-extras ==4.0, - profunctors ==4.3.2, - project-template ==0.1.4.2, - publicsuffixlist ==0.1, - punycode ==2.0, - pure-io ==0.2.1, - pureMD5 ==2.1.2.1, - pwstore-fast ==2.4.4, - quandl-api ==0.2.0.0, - QuasiText ==0.1.2.5, - QuickCheck ==2.7.6, - quickcheck-assertions ==0.1.1, - quickcheck-instances ==0.3.9, - quickcheck-io ==0.1.1, - quickpull ==0.4.0.0, - rainbow ==0.20.0.4, - rainbow-tests ==0.20.0.4, - random ==1.0.1.1, - random-fu ==0.2.6.1, - random-shuffle ==0.0.4, - random-source ==0.3.0.6, - rank1dynamic ==0.2.0.1, - raw-strings-qq ==1.0.2, - ReadArgs ==1.2.2, - reducers ==3.10.3, - reflection ==1.5.1, - regex-applicative ==0.3.0.3, - regex-base ==0.93.2, - regex-compat ==0.95.1, - regex-pcre-builtin ==0.94.4.8.8.35, - regex-posix ==0.95.2, - regexpr ==0.5.4, - regex-tdfa ==1.2.0, - regex-tdfa-rc ==1.1.8.3, - regular ==0.3.4.3, - regular-xmlpickler ==0.2, - rematch ==0.2.0.0, - repa ==3.3.1.2, - repa-algorithms ==3.3.1.2, - repa-devil ==0.3.2.2, - repa-io ==3.3.1.2, - reroute ==0.2.2.1, - resource-pool ==0.2.3.2, - resourcet ==1.1.3.3, - rest-client ==0.4.0.2, - rest-core ==0.33.1.2, - rest-gen ==0.16.1.3, - rest-happstack ==0.2.10.3, - rest-snap ==0.1.17.14, - rest-stringmap ==0.2.0.2, - rest-types ==1.11.1.1, - rest-wai ==0.1.0.4, - rev-state ==0.1, - rfc5051 ==0.1.0.3, - runmemo ==1.0.0.1, - rvar ==0.2.0.2, - safe ==0.3.8, - safecopy ==0.8.3, - scientific ==0.3.3.3, - scotty ==0.9.0, - scrobble ==0.2.1.1, - securemem ==0.1.4, - semigroupoid-extras ==4.0, - semigroupoids ==4.2, - semigroups ==0.16.0.1, - sendfile ==0.7.9, - seqloc ==0.6, - setenv ==0.1.1.2, - SHA ==1.6.4.1, - shake ==0.14.2, - shake-language-c ==0.6.3, - shakespeare ==2.0.2.1, - shakespeare-i18n ==1.1.0, - shakespeare-text ==1.1.0, - shell-conduit ==4.5, - shelly ==1.5.6, - silently ==1.2.4.1, - simple-reflect ==0.3.2, - simple-sendfile ==0.2.18, - singletons ==1.0, - siphash ==1.0.3, - skein ==1.0.9.2, - slave-thread ==0.1.5, - smallcheck ==1.1.1, - smtLib ==1.0.7, - snap ==0.13.3.2, - snap-core ==0.9.6.4, - snaplet-fay ==0.3.3.8, - snap-server ==0.9.4.6, - socks ==0.5.4, - sodium ==0.11.0.2, - sourcemap ==0.1.3.0, - speculation ==1.5.0.1, - sphinx ==0.6.0.1, - split ==0.2.2, - Spock ==0.7.5.1, - spoon ==0.3.1, - sqlite-simple ==0.4.8.0, - stateref ==0.3, - statestack ==0.2.0.3, - statistics ==0.13.2.1, - statistics-linreg ==0.3, - stm ==2.4.4, - stm-chans ==3.0.0.2, - stm-conduit ==2.5.2, - stm-containers ==0.2.7, - stm-stats ==0.2.0.0, - storable-complex ==0.2.1, - storable-endian ==0.2.5, - streaming-commons ==0.1.8, - streams ==3.2, - strict ==0.3.2, - stringable ==0.1.3, - stringbuilder ==0.5.0, - stringprep ==1.0.0, - stringsearch ==0.3.6.5, - stylish-haskell ==0.5.11.0, - SVGFonts ==1.4.0.3, - syb ==0.4.2, - syb-with-class ==0.6.1.5, - system-canonicalpath ==0.2.0.0, - system-fileio ==0.3.16, - system-filepath ==0.4.13, - system-posix-redirect ==1.1.0.1, - tabular ==0.2.2.5, - tagged ==0.7.3, - tagshare ==0.0, - tagsoup ==0.13.3, - tagstream-conduit ==0.5.5.3, - tar ==0.4.0.1, - tardis ==0.3.0.0, - tasty ==0.10.1, - tasty-ant-xml ==1.0.1, - tasty-golden ==2.2.2.4, - tasty-hunit ==0.9.0.1, - tasty-quickcheck ==0.8.3.2, - tasty-smallcheck ==0.8.0.1, - tasty-th ==0.1.3, - template-haskell installed, - temporary ==1.2.0.3, - temporary-rc ==1.2.0.3, - terminal-progress-bar ==0.0.1.4, - terminal-size ==0.3.0, - terminfo installed, - test-framework ==0.8.1.0, - test-framework-hunit ==0.3.0.1, - test-framework-quickcheck2 ==0.3.0.3, - test-framework-th ==0.2.4, - testing-feat ==0.4.0.2, - testpack ==2.1.3.0, - texmath ==0.8.0.1, - text ==1.1.1.3, - text-binary ==0.1.0, - text-format ==0.3.1.1, - text-icu ==0.7.0.0, - tf-random ==0.5, - th-desugar ==1.4.2, - th-expand-syns ==0.3.0.4, - th-extras ==0.0.0.2, - th-lift ==0.7, - th-orphans ==0.8.2, - threads ==0.5.1.2, - th-reify-many ==0.1.2, - thyme ==0.3.5.5, - time installed, - time-compat ==0.1.0.3, - time-lens ==0.4.0.1, - timezone-olson ==0.1.6, - timezone-series ==0.1.4, - tls ==1.2.13, - tls-debug ==0.3.4, - tostring ==0.2.1, - transformers installed, - transformers-base ==0.4.3, - transformers-compat ==0.3.3.3, - traverse-with-class ==0.2.0.3, - tree-view ==0.4, - tuple ==0.3.0.2, - type-eq ==0.4.2, - type-list ==0.0.0.0, - udbus ==0.2.1, - unbounded-delays ==0.1.0.8, - union-find ==0.2, - uniplate ==1.6.12, - unix installed, - unix-compat ==0.4.1.3, - unix-time ==0.3.4, - unordered-containers ==0.2.5.1, - uri-encode ==1.5.0.3, - url ==2.1.3, - utf8-light ==0.4.2, - utf8-string ==0.3.8, - uuid ==1.3.7, - vault ==0.3.0.4, - vector ==0.10.12.2, - vector-algorithms ==0.6.0.3, - vector-binary-instances ==0.2.1.0, - vector-instances ==3.3, - vector-space ==0.8.7, - vector-space-points ==0.2, - vector-th-unbox ==0.2.1.0, - vhd ==0.2.2, - void ==0.7, - wai ==3.0.2.1, - wai-app-static ==3.0.0.5, - wai-conduit ==3.0.0.2, - wai-eventsource ==3.0.0, - wai-extra ==3.0.3.1, - wai-logger ==2.2.3, - wai-middleware-static ==0.6.0.1, - wai-websockets ==3.0.0.3, - warp ==3.0.4.1, - warp-tls ==3.0.1.1, - webdriver ==0.6.0.3, - web-fpco ==0.1.1.0, - websockets ==0.9.2.1, - wizards ==1.0.1, - wl-pprint ==1.1, - wl-pprint-extras ==3.5.0.3, - wl-pprint-terminfo ==3.7.1.3, - wl-pprint-text ==1.1.0.2, - word8 ==0.1.1, - X11 ==1.6.1.2, - x509 ==1.5.0.1, - x509-store ==1.5.0, - x509-system ==1.5.0, - x509-validation ==1.5.1, - xenstore ==0.1.1, - xhtml installed, - xml ==1.3.13, - xml-conduit ==1.2.3.1, - xmlgen ==0.6.2.1, - xml-hamlet ==0.4.0.9, - xmlhtml ==0.2.3.3, - xml-types ==0.3.4, - xss-sanitize ==0.3.5.4, - yackage ==0.7.0.6, - yaml ==0.8.10.1, - Yampa ==0.9.6, - YampaSynth ==0.2, - yesod ==1.4.1.3, - yesod-auth ==1.4.1.1, - yesod-auth-deskcom ==1.4.0, - yesod-auth-fb ==1.6.6, - yesod-auth-hashdb ==1.4.1.1, - yesod-bin ==1.4.3.1, - yesod-core ==1.4.7.1, - yesod-eventsource ==1.4.0.1, - yesod-fay ==0.7.0, - yesod-fb ==0.3.4, - yesod-form ==1.4.3.1, - yesod-gitrepo ==0.1.1.0, - yesod-newsfeed ==1.4.0.1, - yesod-persistent ==1.4.0.2, - yesod-sitemap ==1.4.0.1, - yesod-static ==1.4.0.4, - yesod-test ==1.4.2.1, - yesod-text-markdown ==0.1.7, - yesod-websockets ==0.2.1.1, - zeromq4-haskell ==0.6.2, - zip-archive ==0.2.3.5, - zlib ==0.5.4.2, - zlib-bindings ==0.1.1.5, - zlib-enum ==0.2.3.1, - zlib-lens ==0.1 diff --git a/debian-bootstrap.sh b/debian-bootstrap.sh deleted file mode 100755 index 827e8460..00000000 --- a/debian-bootstrap.sh +++ /dev/null @@ -1,71 +0,0 @@ -#!/bin/bash -ex - -# Work in progress: create a list of commands necessary to get Stackage -# up-and-running on a freshly installed Debian-based system (includin Ubuntu). - -# Quick start: -# wget -O - https://raw.github.com/fpco/stackage/master/debian-bootstrap.sh | bash -ex - -# NOTE: Requires that GHC and Cabal are installed and on your PATH. For -# instructions, see: -# http://www.stackage.org/install - -add-apt-repository -y ppa:chris-lea/zeromq -add-apt-repository -y ppa:floe/libtisch -add-apt-repository -y ppa:zoogie/sdl2-snapshots -apt-get update -apt-get install -y \ - build-essential \ - libncurses-dev \ - git \ - wget \ - m4 \ - texlive-full \ - libgmp3c2 \ - libgmp3-dev \ - zlib1g-dev \ - libedit2 \ - libedit-dev \ - freeglut3-dev \ - libglu1-mesa-dev \ - libglib2.0-dev \ - libcairo2-dev \ - libpango1.0-dev \ - libgtk2.0-dev \ - zip \ - libdevil-dev \ - llvm \ - libbz2-dev \ - libjudy-dev \ - libsqlite3-dev \ - libmysqlclient-dev \ - libpq-dev \ - libicu-dev \ - libssl-dev \ - libgsl0-dev \ - libblas-dev \ - liblapack-dev \ - libcurl4-openssl-dev \ - libfreenect-dev \ - libnotify-dev \ - libgd2-xpm-dev \ - libyaml-dev \ - liblzma-dev \ - libsdl2-dev \ - libxss-dev \ - libzmq3-dev - -mkdir /tmp/nettle-build -( -cd /tmp/nettle-build -wget https://ftp.gnu.org/gnu/nettle/nettle-2.7.1.tar.gz -tar zxf nettle-2.7.1.tar.gz -cd nettle-2.7.1 -./configure --prefix=/usr -make -make install - -mkdir -p /usr/lib/x86_64-linux-gnu/ -ln -sfv /usr/lib/libnettle.so.4.7 /usr/lib/x86_64-linux-gnu/libnettle.so.4 -) -rm -rf /tmp/nettle-build diff --git a/stackage.cabal b/stackage.cabal deleted file mode 100644 index d12c172b..00000000 --- a/stackage.cabal +++ /dev/null @@ -1,105 +0,0 @@ -name: stackage -version: 0.6.0.1 -synopsis: "Stable Hackage," tools for creating a vetted set of packages from Hackage. -description: Please see for a description and documentation. -homepage: https://github.com/fpco/stackage -license: MIT -license-file: LICENSE -author: Michael Snoyman -maintainer: michael@fpcomplete.com -category: Distribution -build-type: Simple -cabal-version: >=1.10 -extra-source-files: README.md - ChangeLog.md - test/test-build-constraints.yaml - -library - default-language: Haskell2010 - exposed-modules: Stackage.Prelude - Stackage.BuildConstraints - Stackage.CorePackages - Stackage.PackageIndex - Stackage.BuildPlan - Stackage.CheckBuildPlan - Stackage.UpdateBuildPlan - Stackage.GhcPkg - Stackage.GithubPings - Stackage.InstallBuild - Stackage.PackageDescription - Stackage.ServerBundle - Stackage.Upload - Stackage.PerformBuild - Stackage.CompleteBuild - build-depends: base >= 4 && < 5 - , containers - , Cabal >= 1.14 - , tar >= 0.3 - , zlib - , bytestring - , directory - , filepath - , transformers - , process - , old-locale - , time - , utf8-string - - , conduit-extra - , classy-prelude-conduit - , text - , system-fileio - , system-filepath - , mtl - , aeson - , yaml - , unix-compat - , http-client - , http-conduit - , http-client-tls - , temporary - , data-default-class - , stm - , mono-traversable - , async - , streaming-commons >= 0.1.7.1 - , semigroups - , xml-conduit - , conduit - -executable stackage - default-language: Haskell2010 - hs-source-dirs: app - main-is: stackage.hs - build-depends: base - , stackage - , optparse-applicative >= 0.11 - , system-filepath - , http-client - , http-client-tls - , text - ghc-options: -rtsopts -threaded -with-rtsopts=-N - -test-suite spec - type: exitcode-stdio-1.0 - default-language: Haskell2010 - hs-source-dirs: test - main-is: Spec.hs - other-modules: Stackage.CorePackagesSpec - Stackage.PackageIndexSpec - Stackage.BuildPlanSpec - build-depends: base - , stackage - , hspec - , QuickCheck - , text - , classy-prelude-conduit - , Cabal - , yaml - , containers - , http-client - , http-client-tls - -source-repository head - type: git - location: https://github.com/fpco/stackage diff --git a/test/Spec.hs b/test/Spec.hs deleted file mode 100644 index a824f8c3..00000000 --- a/test/Spec.hs +++ /dev/null @@ -1 +0,0 @@ -{-# OPTIONS_GHC -F -pgmF hspec-discover #-} diff --git a/test/Stackage/BuildPlanSpec.hs b/test/Stackage/BuildPlanSpec.hs deleted file mode 100644 index b87c74d2..00000000 --- a/test/Stackage/BuildPlanSpec.hs +++ /dev/null @@ -1,143 +0,0 @@ -{-# LANGUAGE ScopedTypeVariables #-} -{-# LANGUAGE OverloadedStrings, NoImplicitPrelude #-} -module Stackage.BuildPlanSpec (spec) where - -import qualified Data.Map as Map -import qualified Data.Map.Strict as M -import qualified Data.Set as S -import Data.Yaml -import qualified Data.Yaml as Y -import Distribution.Version -import Network.HTTP.Client -import Network.HTTP.Client.TLS (tlsManagerSettings) -import Stackage.BuildConstraints -import Stackage.BuildPlan -import Stackage.CheckBuildPlan -import Stackage.PackageDescription -import Stackage.Prelude -import Stackage.UpdateBuildPlan -import Test.Hspec - -spec :: Spec -spec = do - it "simple package set" $ check testBuildConstraints $ makePackageSet - [("foo", [0, 0, 0], [("bar", thisV [0, 0, 0])]) - ,("bar", [0, 0, 0], [])] - it "bad version range on depdendency fails" $ badBuildPlan $ makePackageSet - [("foo", [0, 0, 0], [("bar", thisV [1, 1, 0])]) - ,("bar", [0, 0, 0], [])] - it "nonexistent package fails to check" $ badBuildPlan $ makePackageSet - [("foo", [0, 0, 0], [("nonexistent", thisV [0, 0, 0])]) - ,("bar", [0, 0, 0], [])] - it "mutual cycles fail to check" $ badBuildPlan $ makePackageSet - [("foo", [0, 0, 0], [("bar", thisV [0, 0, 0])]) - ,("bar", [0, 0, 0], [("foo", thisV [0, 0, 0])])] - it "nested cycles fail to check" $ badBuildPlan $ makePackageSet - [("foo", [0, 0, 0], [("bar", thisV [0, 0, 0])]) - ,("bar", [0, 0, 0], [("mu", thisV [0, 0, 0])]) - ,("mu", [0, 0, 0], [("foo", thisV [0, 0, 0])])] - {- Shouldn't be testing this actually - it "default package set checks ok" $ - check defaultBuildConstraints getLatestAllowedPlans - -} - --- | Checking should be considered a bad build plan. -badBuildPlan :: (BuildConstraints -> IO (Map PackageName PackagePlan)) - -> void - -> IO () -badBuildPlan m _ = do - mu <- try (check testBuildConstraints m) - case mu of - Left (_ :: BadBuildPlan) -> - return () - Right () -> - error "Expected bad build plan." - --- | Check build plan with the given package set getter. -check :: (Manager -> IO BuildConstraints) - -> (BuildConstraints -> IO (Map PackageName PackagePlan)) - -> IO () -check readPlanFile getPlans = withManager tlsManagerSettings $ \man -> do - bc <- readPlanFile man - plans <- getPlans bc - bp <- newBuildPlan plans bc - let bs = Y.encode bp - ebp' = Y.decodeEither bs - - bp' <- either error return ebp' - - let allPackages = Map.keysSet (bpPackages bp) ++ Map.keysSet (bpPackages bp') - forM_ allPackages $ \name -> - (name, lookup name (bpPackages bp')) `shouldBe` - (name, lookup name (bpPackages bp)) - bpGithubUsers bp' `shouldBe` bpGithubUsers bp - - when (bp' /= bp) $ error "bp' /= bp" - bp2 <- updateBuildPlan plans bp - when (dropVersionRanges bp2 /= dropVersionRanges bp) $ error "bp2 /= bp" - checkBuildPlan bp - where - dropVersionRanges bp = - bp { bpPackages = map go $ bpPackages bp } - where - go pb = pb { ppConstraints = go' $ ppConstraints pb } - go' pc = pc { pcVersionRange = anyVersion } - --- | Make a package set from a convenient data structure. -makePackageSet - :: [(String,[Int],[(String,VersionRange)])] - -> BuildConstraints - -> IO (Map PackageName PackagePlan) -makePackageSet ps _ = - return $ - M.fromList $ - map - (\(name,ver,deps) -> - ( PackageName name - , dummyPackage ver $ - M.fromList $ - map - (\(dname,dver) -> - ( PackageName dname - , DepInfo {diComponents = S.fromList - [CompLibrary] - ,diRange = dver})) - deps)) - ps - where - dummyPackage v deps = - PackagePlan - {ppVersion = Version v [] - ,ppGithubPings = mempty - ,ppUsers = mempty - ,ppConstraints = - PackageConstraints - {pcVersionRange = anyV - ,pcMaintainer = Nothing - ,pcTests = Don'tBuild - ,pcHaddocks = Don'tBuild - ,pcBuildBenchmarks = False - ,pcFlagOverrides = mempty - ,pcEnableLibProfile = False} - ,ppDesc = - SimpleDesc - {sdPackages = deps - ,sdTools = mempty - ,sdProvidedExes = mempty - ,sdModules = mempty}} - --- | This exact version is required. -thisV :: [Int] -> VersionRange -thisV ver = thisVersion (Version ver []) - --- | Accept any version. -anyV :: VersionRange -anyV = anyVersion - --- | Test plan. -testBuildConstraints :: void -> IO BuildConstraints -testBuildConstraints _ = - decodeFileEither - (fpToString fp) >>= - either throwIO toBC - where fp = "test/test-build-constraints.yaml" diff --git a/test/Stackage/CorePackagesSpec.hs b/test/Stackage/CorePackagesSpec.hs deleted file mode 100644 index ce0c5d10..00000000 --- a/test/Stackage/CorePackagesSpec.hs +++ /dev/null @@ -1,19 +0,0 @@ -{-# LANGUAGE OverloadedStrings, NoImplicitPrelude #-} -module Stackage.CorePackagesSpec (spec) where - -import Stackage.CorePackages -import Stackage.Prelude -import Test.Hspec - -spec :: Spec -spec = do - it "works" $ void getCorePackages - it "contains known core packages" $ do - m <- getCorePackages - forM_ (words "ghc containers base") $ \p -> - m `shouldSatisfy` (member (PackageName p)) - it "getCoreExecutables includes known executables" $ do - s <- getCoreExecutables - s `shouldSatisfy` member "ghc" - s `shouldSatisfy` member "hsc2hs" - s `shouldSatisfy` member "runghc" diff --git a/test/Stackage/PackageIndexSpec.hs b/test/Stackage/PackageIndexSpec.hs deleted file mode 100644 index e0ef97e6..00000000 --- a/test/Stackage/PackageIndexSpec.hs +++ /dev/null @@ -1,21 +0,0 @@ -{-# LANGUAGE OverloadedStrings, NoImplicitPrelude #-} -module Stackage.PackageIndexSpec (spec) where - -import Stackage.PackageIndex -import Stackage.Prelude -import Test.Hspec -import Distribution.Package (packageId) - -spec :: Spec -spec = do - it "works" $ (runResourceT $ sourcePackageIndex $$ sinkNull :: IO ()) - it "getLatestDescriptions gives reasonable results" $ do - let f x y = (display x, display y) `member` asSet (setFromList - [ (asText "base", asText "4.5.0.0") - , ("does-not-exist", "9999999999999999999") - ]) - m <- getLatestDescriptions f return - length m `shouldBe` 1 - p <- simpleParse $ asText "base" - v <- simpleParse $ asText "4.5.0.0" - (pkgVersion . packageId <$> m) `shouldBe` singletonMap p v diff --git a/test/test-build-constraints.yaml b/test/test-build-constraints.yaml deleted file mode 100644 index de831eaf..00000000 --- a/test/test-build-constraints.yaml +++ /dev/null @@ -1,20 +0,0 @@ -packages: - "Test": - - foo - - bar - -global-flags: [] - -skipped-tests: [] -expected-test-failures: [] -expected-haddock-failures: [] -skipped-benchmarks: [] -skipped-profiling: [] - -github-users: - bar: - - demo - -package-flags: - foo: - demo: true From 98075e03c7d7910eb816811dac89ef5f336f1151 Mon Sep 17 00:00:00 2001 From: Michael Snoyman Date: Sun, 22 Mar 2015 14:27:00 +0200 Subject: [PATCH 12/18] Add stackage-types --- build-constraints.yaml | 1 + 1 file changed, 1 insertion(+) diff --git a/build-constraints.yaml b/build-constraints.yaml index 206af9e8..f97471e6 100644 --- a/build-constraints.yaml +++ b/build-constraints.yaml @@ -94,6 +94,7 @@ packages: - smtLib - stackage - stackage-curator + - stackage-types - statistics-linreg - th-expand-syns - thyme From 827cc6e5be4d7206f698de2d5813ba0038cd4de2 Mon Sep 17 00:00:00 2001 From: Michael Snoyman Date: Sun, 22 Mar 2015 14:50:21 +0200 Subject: [PATCH 13/18] Docker no longer available --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 848c9744..b4337f12 100644 --- a/README.md +++ b/README.md @@ -55,7 +55,7 @@ build by running: ### Docker -Note: This method is currently considered experimental. +Note: This method has been disabled for now, but may be enabled again in the future. If you'd like to check a build plan, or perform an entire build, without specially configuring your system, Docker may be a good approach. To check if From 5bdd6de1b0e84e06951a99c9f99dd8e68e82b305 Mon Sep 17 00:00:00 2001 From: Michael Snoyman Date: Sun, 22 Mar 2015 15:23:40 +0200 Subject: [PATCH 14/18] Add some Travis badges --- README.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index b4337f12..bd036c15 100644 --- a/README.md +++ b/README.md @@ -11,9 +11,9 @@ The Stackage project consists of multiple repositories. This repository contains the metadata on packages to be included in future builds and some project information. In addition, we have the following repositories: -* [stackage-server](https://github.com/fpco/stackage-server) -* [stackage-curator](https://github.com/fpco/stackage-curator) -* [stackage-types](https://github.com/fpco/stackage-types) +* [stackage-server](https://github.com/fpco/stackage-server) [![Build Status](https://travis-ci.org/fpco/stackage-server.svg?branch=master)](https://travis-ci.org/fpco/stackage-server) +* [stackage-curator](https://github.com/fpco/stackage-curator) [![Build Status](https://travis-ci.org/fpco/stackage-curator.svg?branch=master)](https://travis-ci.org/fpco/stackage-curator) +* [stackage-types](https://github.com/fpco/stackage-types) [![Build Status](https://travis-ci.org/fpco/stackage-types.svg?branch=master)](https://travis-ci.org/fpco/stackage-types) * [lts-haskell](https://github.com/fpco/lts-haskell) Get your package included From f8856289195e1ac6d1f57c4a98c8f1c17e62ca6e Mon Sep 17 00:00:00 2001 From: Michael Snoyman Date: Sun, 22 Mar 2015 15:25:23 +0200 Subject: [PATCH 15/18] Add another badge --- README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/README.md b/README.md index bd036c15..47f46a1f 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,8 @@ stackage ======== +[![Build Status](https://travis-ci.org/fpco/stackage.svg?branch=master)](https://travis-ci.org/fpco/stackage) + "Stable Hackage," tools for creating a vetted set of packages from Hackage. __NOTE__ This repository is for package authors to get their code into From db6cc51b0683089f705215621f77d2faaee7f338 Mon Sep 17 00:00:00 2001 From: Michael Snoyman Date: Sun, 22 Mar 2015 16:23:35 +0200 Subject: [PATCH 16/18] Use prebuilt stackage-curator executable --- .travis.yml | 11 ++++------- 1 file changed, 4 insertions(+), 7 deletions(-) diff --git a/.travis.yml b/.travis.yml index 7cf659d4..c74fb9e8 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,11 +1,6 @@ env: - CABALVER=1.20 GHCVER=7.8.4 -cache: - directories: - - $HOME/.ghc - - $HOME/.cabal - # Note: the distinction between `before_install` and `install` is not important. before_install: - travis_retry sudo add-apt-repository -y ppa:hvr/ghc @@ -17,8 +12,10 @@ install: - cabal --version - echo "$(ghc --version) [$(ghc --print-project-git-commit-id 2> /dev/null || echo '?')]" - travis_retry cabal update - - cabal install -j + - wget https://s3.amazonaws.com/stackage-travis/stackage-curator.bz2 + - bunzip2 stackage-curator.bz2 + - chmod +x stackage-curator # Here starts the actual work to be performed for the package under test; any command which exits with a non-zero exit code causes the build to fail. script: - - ./dist/build/stackage/stackage check + - ./stackage-curator check From 03c7e123042e61e17eba13f5620ea36aa2d5ede0 Mon Sep 17 00:00:00 2001 From: Michael Snoyman Date: Sun, 22 Mar 2015 16:26:10 +0200 Subject: [PATCH 17/18] Add back Docker stuff --- Dockerfile | 25 ++++++++++++++++ debian-bootstrap.sh | 71 +++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 96 insertions(+) create mode 100644 Dockerfile create mode 100755 debian-bootstrap.sh diff --git a/Dockerfile b/Dockerfile new file mode 100644 index 00000000..e3b09c3b --- /dev/null +++ b/Dockerfile @@ -0,0 +1,25 @@ +FROM ubuntu:12.04 + +ENV HOME /home/stackage +ENV LANG en_US.UTF-8 + +RUN mkdir /home/stackage -p +RUN locale-gen en_US.UTF-8 + +RUN DEBIAN_FRONTEND=noninteractive apt-get update +RUN DEBIAN_FRONTEND=noninteractive apt-get install -y software-properties-common python-software-properties +RUN DEBIAN_FRONTEND=noninteractive add-apt-repository ppa:hvr/ghc -y + +ADD debian-bootstrap.sh /tmp/debian-bootstrap.sh +RUN DEBIAN_FRONTEND=noninteractive bash /tmp/debian-bootstrap.sh +RUN rm /tmp/debian-bootstrap.sh + +RUN DEBIAN_FRONTEND=noninteractive apt-get install -y cabal-install-1.20 ghc-7.8.4 alex-3.1.3 happy-1.19.4 + +ENV PATH /home/stackage/.cabal/bin:/usr/local/sbin:/usr/local/bin:/opt/ghc/7.8.4/bin:/opt/cabal/1.20/bin:/opt/alex/3.1.3/bin:/opt/happy/1.19.4/bin:/usr/sbin:/usr/bin:/sbin:/bin + +RUN cabal update +RUN cabal install hscolour cabal-install --constraint "Cabal < 1.22" && cp $HOME/.cabal/bin/* /usr/local/bin && rm -rf $HOME/.cabal $HOME/.ghc /tmp/stackage +RUN wget https://s3.amazonaws.com/stackage-travis/stackage-curator.bz2 && bunzip2 stackage-curator.bz2 && chmod +x stackage-curator && mv stackage-curator /usr/local/bin + +RUN cd /home/stackage && cabal update && stackage-curator check diff --git a/debian-bootstrap.sh b/debian-bootstrap.sh new file mode 100755 index 00000000..827e8460 --- /dev/null +++ b/debian-bootstrap.sh @@ -0,0 +1,71 @@ +#!/bin/bash -ex + +# Work in progress: create a list of commands necessary to get Stackage +# up-and-running on a freshly installed Debian-based system (includin Ubuntu). + +# Quick start: +# wget -O - https://raw.github.com/fpco/stackage/master/debian-bootstrap.sh | bash -ex + +# NOTE: Requires that GHC and Cabal are installed and on your PATH. For +# instructions, see: +# http://www.stackage.org/install + +add-apt-repository -y ppa:chris-lea/zeromq +add-apt-repository -y ppa:floe/libtisch +add-apt-repository -y ppa:zoogie/sdl2-snapshots +apt-get update +apt-get install -y \ + build-essential \ + libncurses-dev \ + git \ + wget \ + m4 \ + texlive-full \ + libgmp3c2 \ + libgmp3-dev \ + zlib1g-dev \ + libedit2 \ + libedit-dev \ + freeglut3-dev \ + libglu1-mesa-dev \ + libglib2.0-dev \ + libcairo2-dev \ + libpango1.0-dev \ + libgtk2.0-dev \ + zip \ + libdevil-dev \ + llvm \ + libbz2-dev \ + libjudy-dev \ + libsqlite3-dev \ + libmysqlclient-dev \ + libpq-dev \ + libicu-dev \ + libssl-dev \ + libgsl0-dev \ + libblas-dev \ + liblapack-dev \ + libcurl4-openssl-dev \ + libfreenect-dev \ + libnotify-dev \ + libgd2-xpm-dev \ + libyaml-dev \ + liblzma-dev \ + libsdl2-dev \ + libxss-dev \ + libzmq3-dev + +mkdir /tmp/nettle-build +( +cd /tmp/nettle-build +wget https://ftp.gnu.org/gnu/nettle/nettle-2.7.1.tar.gz +tar zxf nettle-2.7.1.tar.gz +cd nettle-2.7.1 +./configure --prefix=/usr +make +make install + +mkdir -p /usr/lib/x86_64-linux-gnu/ +ln -sfv /usr/lib/libnettle.so.4.7 /usr/lib/x86_64-linux-gnu/libnettle.so.4 +) +rm -rf /tmp/nettle-build From e643ebb1866798d5b2ac5f52c1f84b625edc45a8 Mon Sep 17 00:00:00 2001 From: Michael Snoyman Date: Sun, 22 Mar 2015 16:42:34 +0200 Subject: [PATCH 18/18] Fix download path --- .travis.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index c74fb9e8..cf90696a 100644 --- a/.travis.yml +++ b/.travis.yml @@ -12,7 +12,7 @@ install: - cabal --version - echo "$(ghc --version) [$(ghc --print-project-git-commit-id 2> /dev/null || echo '?')]" - travis_retry cabal update - - wget https://s3.amazonaws.com/stackage-travis/stackage-curator.bz2 + - wget https://s3.amazonaws.com/stackage-travis/stackage-curator/stackage-curator.bz2 - bunzip2 stackage-curator.bz2 - chmod +x stackage-curator