hpack 0.28.2 → 0.29.0
raw patch · 14 files changed
+333/−122 lines, 14 filesdep ~CabalPVP ok
version bump matches the API change (PVP)
Dependency ranges changed: Cabal
API changes (from Hackage documentation)
- Hpack.Config: instance (Data.Semigroup.Semigroup cSources, Data.Semigroup.Semigroup cxxSources, Data.Semigroup.Semigroup jsSources) => Data.Semigroup.Semigroup (Hpack.Config.CommonOptions cSources cxxSources jsSources a)
- Hpack.Config: instance (Data.Semigroup.Semigroup cSources, Data.Semigroup.Semigroup cxxSources, Data.Semigroup.Semigroup jsSources, GHC.Base.Monoid cSources, GHC.Base.Monoid cxxSources, GHC.Base.Monoid jsSources) => GHC.Base.Monoid (Hpack.Config.CommonOptions cSources cxxSources jsSources a)
- Hpack.Config: instance Data.Semigroup.Semigroup Hpack.Config.Empty
- Hpack.Config: instance Data.Semigroup.Semigroup Hpack.Config.ExecutableSection
- Hpack.Config: instance Data.Semigroup.Semigroup Hpack.Config.LibrarySection
+ Hpack.Config: [decodeResultCabalVersion] :: DecodeResult -> String
+ Hpack.Config: instance (GHC.Base.Semigroup cSources, GHC.Base.Semigroup cxxSources, GHC.Base.Semigroup jsSources) => GHC.Base.Semigroup (Hpack.Config.CommonOptions cSources cxxSources jsSources a)
+ Hpack.Config: instance (GHC.Base.Semigroup cSources, GHC.Base.Semigroup cxxSources, GHC.Base.Semigroup jsSources, GHC.Base.Monoid cSources, GHC.Base.Monoid cxxSources, GHC.Base.Monoid jsSources) => GHC.Base.Monoid (Hpack.Config.CommonOptions cSources cxxSources jsSources a)
+ Hpack.Config: instance GHC.Base.Semigroup Hpack.Config.Empty
+ Hpack.Config: instance GHC.Base.Semigroup Hpack.Config.ExecutableSection
+ Hpack.Config: instance GHC.Base.Semigroup Hpack.Config.LibrarySection
+ Hpack.Config: verbatimValueToString :: VerbatimValue -> String
- Hpack.Config: DecodeOptions :: FilePath -> Maybe FilePath -> (FilePath -> IO (Either String Value)) -> DecodeOptions
+ Hpack.Config: DecodeOptions :: FilePath -> Maybe FilePath -> FilePath -> IO (Either String Value) -> DecodeOptions
- Hpack.Config: DecodeResult :: Package -> FilePath -> [String] -> DecodeResult
+ Hpack.Config: DecodeResult :: Package -> String -> FilePath -> [String] -> DecodeResult
Files
- CHANGELOG.md +9/−1
- hpack.cabal +11/−8
- src/Hpack.hs +8/−6
- src/Hpack/CabalFile.hs +6/−1
- src/Hpack/Config.hs +119/−2
- src/Hpack/License.hs +48/−0
- src/Hpack/Render.hs +3/−70
- test/EndToEndSpec.hs +57/−5
- test/Helper.hs +2/−0
- test/Hpack/CabalFileSpec.hs +8/−3
- test/Hpack/ConfigSpec.hs +1/−1
- test/Hpack/LicenseSpec.hs +57/−0
- test/Hpack/RenderSpec.hs +4/−24
- test/Hpack/Syntax/GitSpec.hs +0/−1
CHANGELOG.md view
@@ -1,4 +1,12 @@-## next+## Changes in 0.29.0+ - Put the `cabal-version` at the beginning of the generated file. This Is+ required with `cabal-version: 2.1` and higher. (see #292)+ - With `cabal-version: 2.1` or higher omit `>=` when rendering (see #292)+ - Require `cabal-version: 2.2` when SPDX license identifiers are used (see #292)+ - Map cabal-style licenses to SPDX license identifiers when `cabal-version`+ is 2.2 or higher (see #292)++## Changes in 0.28.2 - Exit with `exitFailure` on `AlreadyGeneratedByNewerHpack` or `ExistingCabalFileWasModifiedManually` in `Hpack.printResult`
hpack.cabal view
@@ -1,11 +1,13 @@--- This file has been generated from package.yaml by hpack version 0.27.0.+cabal-version: >= 1.10++-- This file has been generated from package.yaml by hpack version 0.29.0. -- -- see: https://github.com/sol/hpack ----- hash: 5391105d37fea2b976290b95e847c0d2da5ea7e0ef9ae9e5cf8945911dd983a1+-- hash: cfd597be64fbc0242e6c338653cce17e853d1ce5843d07785f81ce0f208ee198 name: hpack-version: 0.28.2+version: 0.29.0 synopsis: An alternative format for Haskell packages description: See README at <https://github.com/sol/hpack#readme> category: Development@@ -15,8 +17,6 @@ license: MIT license-file: LICENSE build-type: Simple-cabal-version: >= 1.10- extra-source-files: CHANGELOG.md @@ -29,7 +29,7 @@ src ghc-options: -Wall build-depends:- Cabal+ Cabal >=2.2 , Glob >=0.9.0 , aeson >=1.2.1.0 , base >=4.9 && <5@@ -63,6 +63,7 @@ Hpack.CabalFile Hpack.Defaults Hpack.Haskell+ Hpack.License Hpack.Options Hpack.Render.Dsl Hpack.Render.Hints@@ -80,7 +81,7 @@ driver ghc-options: -Wall build-depends:- Cabal+ Cabal >=2.2 , Glob >=0.9.0 , aeson >=1.2.1.0 , base >=4.9 && <5@@ -115,7 +116,7 @@ ghc-options: -Wall cpp-options: -DTEST build-depends:- Cabal+ Cabal >=2.2 , Glob >=0.9.0 , HUnit >=1.6.0.0 , QuickCheck@@ -153,6 +154,7 @@ Hpack.ConfigSpec Hpack.DefaultsSpec Hpack.HaskellSpec+ Hpack.LicenseSpec Hpack.OptionsSpec Hpack.Render.DslSpec Hpack.Render.HintsSpec@@ -172,6 +174,7 @@ Hpack.Config Hpack.Defaults Hpack.Haskell+ Hpack.License Hpack.Options Hpack.Render Hpack.Render.Dsl
src/Hpack.hs view
@@ -164,19 +164,21 @@ hpackResultWithVersion :: Version -> Options -> IO Result hpackResultWithVersion v (Options options force toStdout) = do- DecodeResult pkg cabalFile warnings <- readPackageConfig options >>= either die return+ DecodeResult pkg cabalVersion cabalFile warnings <- readPackageConfig options >>= either die return oldCabalFile <- readCabalFile cabalFile- let new = renderPackage (maybe [] cabalFileContents oldCabalFile) pkg let+ body = renderPackage (maybe [] cabalFileContents oldCabalFile) pkg+ withoutHeader = cabalVersion ++ body+ let status = case force of Force -> Generated- NoForce -> maybe Generated (mkStatus (lines new) v) oldCabalFile+ NoForce -> maybe Generated (mkStatus (lines withoutHeader) v) oldCabalFile case status of Generated -> do- let hash = sha256 new+ let hash = sha256 withoutHeader if toStdout- then Utf8.putStr new- else Utf8.writeFile cabalFile (header (decodeOptionsTarget options) v hash ++ new)+ then Utf8.putStr withoutHeader+ else Utf8.writeFile cabalFile (cabalVersion ++ header (decodeOptionsTarget options) v hash ++ body) _ -> return () return Result { resultWarnings = warnings
src/Hpack/CabalFile.hs view
@@ -28,7 +28,12 @@ parse (splitHeader -> (h, c)) = CabalFile (extractVersion h) (extractHash h) c splitHeader :: String -> ([String], [String])- splitHeader = fmap (dropWhile null) . span ("--" `isPrefixOf`) . removeGitConflictMarkers . lines+ splitHeader (removeGitConflictMarkers . lines -> c) =+ case span (not . isComment) c of+ (cabalVersion, xs) -> case span isComment xs of+ (header, body) -> (header, cabalVersion ++ dropWhile null body)++ isComment = ("--" `isPrefixOf`) extractHash :: [String] -> Maybe Hash extractHash = extract "-- hash: " Just
src/Hpack/Config.hs view
@@ -44,6 +44,7 @@ , GhcOption , Verbatim(..) , VerbatimValue(..)+, verbatimValueToString , CustomSetup(..) , Section(..) , Library(..)@@ -71,7 +72,7 @@ ) where import Control.Applicative-import Control.Arrow ((>>>))+import Control.Arrow ((>>>), (&&&)) import Control.Monad import Data.Bifunctor import Data.Bitraversable@@ -91,7 +92,10 @@ import Control.Monad.Trans.Writer import Control.Monad.Trans.Except import Control.Monad.IO.Class+import Data.Version +import Distribution.Pretty (prettyShow)+ import Data.Aeson.Config.Types import Data.Aeson.Config.FromValue hiding (decodeValue) import qualified Data.Aeson.Config.FromValue as Config@@ -102,6 +106,7 @@ import Hpack.Defaults import qualified Hpack.Yaml as Yaml import Hpack.Syntax.Dependency+import Hpack.License package :: String -> String -> Package package name version = Package {@@ -562,6 +567,7 @@ data DecodeResult = DecodeResult { decodeResultPackage :: Package+, decodeResultCabalVersion :: String , decodeResultCabalFile :: FilePath , decodeResultWarnings :: [String] } deriving (Eq, Show)@@ -575,12 +581,123 @@ toPackage userDataDir dir config where addCabalFile :: (Package, [String]) -> DecodeResult- addCabalFile (pkg, warnings) = DecodeResult pkg (takeDirectory_ file </> (packageName pkg ++ ".cabal")) warnings+ addCabalFile (pkg, warnings) = uncurry DecodeResult (cabalVersion pkg) (takeDirectory_ file </> (packageName pkg ++ ".cabal")) warnings takeDirectory_ :: FilePath -> FilePath takeDirectory_ p | takeFileName p == p = "" | otherwise = takeDirectory p++deleteVerbatimField :: String -> [Verbatim] -> [Verbatim]+deleteVerbatimField name = map $ \ case+ literal@VerbatimLiteral {} -> literal+ VerbatimObject o -> VerbatimObject (Map.delete name o)++verbatimValueToString :: VerbatimValue -> String+verbatimValueToString = \ case+ VerbatimString s -> s+ VerbatimNumber n -> scientificToVersion n+ VerbatimBool b -> show b+ VerbatimNull -> ""++cabalVersion :: Package -> (Package, String)+cabalVersion pkg@Package{..} = (+ pkg {+ packageVerbatim = deleteVerbatimField "cabal-version" packageVerbatim+ , packageLicense = formatLicense <$> parsedLicense+ }+ , "cabal-version: " ++ fromMaybe inferredCabalVersion verbatimCabalVersion ++ "\n\n"+ )+ where+ parsedLicense = (fmap prettyShow . parseLicense &&& id) <$> packageLicense++ formatLicense = \ case+ (MustSPDX spdx, _) -> spdx+ (CanSPDX spdx, _) | version >= makeVersion [2,2] -> spdx+ (CanSPDX _, original) -> original+ (DontTouch, original) -> original++ mustSPDX :: Bool+ mustSPDX = maybe False (f . fst) parsedLicense+ where+ f = \case+ DontTouch -> False+ CanSPDX _ -> False+ MustSPDX _ -> True++ verbatimCabalVersion :: Maybe String+ verbatimCabalVersion = listToMaybe (mapMaybe f packageVerbatim)+ where+ f :: Verbatim -> Maybe String+ f = \ case+ VerbatimLiteral _ -> Nothing+ VerbatimObject o -> case Map.lookup "cabal-version" o of+ Just v -> Just (verbatimValueToString v)+ Nothing -> Nothing++ inferredCabalVersion :: String+ inferredCabalVersion+ | version >= makeVersion [2,1] = showVersion version+ | otherwise = (">= " ++) . showVersion $ version++ version = fromMaybe (makeVersion [1,10]) $ maximum [+ packageCabalVersion+ , packageLibrary >>= libraryCabalVersion+ , internalLibsCabalVersion packageInternalLibraries+ , executablesCabalVersion packageExecutables+ , executablesCabalVersion packageTests+ , executablesCabalVersion packageBenchmarks+ ]++ packageCabalVersion :: Maybe Version+ packageCabalVersion = maximum [+ Nothing+ , makeVersion [2,2] <$ guard mustSPDX+ , makeVersion [1,24] <$ packageCustomSetup+ , makeVersion [1,18] <$ guard (not (null packageExtraDocFiles))+ ]++ libraryCabalVersion :: Section Library -> Maybe Version+ libraryCabalVersion sect = maximum [+ makeVersion [1,22] <$ guard hasReexportedModules+ , makeVersion [2,0] <$ guard hasSignatures+ , makeVersion [2,0] <$ guard hasGeneratedModules+ , makeVersion [2,2] <$ guard (hasCxxParams sect)+ ]+ where+ hasReexportedModules = any (not . null . libraryReexportedModules) sect+ hasSignatures = any (not . null . librarySignatures) sect+ hasGeneratedModules = any (not . null . libraryGeneratedModules) sect++ internalLibsCabalVersion :: Map String (Section Library) -> Maybe Version+ internalLibsCabalVersion internalLibraries+ | Map.null internalLibraries = Nothing+ | otherwise = foldr max (Just $ makeVersion [2,0]) versions+ where+ versions = libraryCabalVersion <$> Map.elems internalLibraries++ executablesCabalVersion :: Map String (Section Executable) -> Maybe Version+ executablesCabalVersion = foldr max Nothing . map executableCabalVersion . Map.elems++ executableCabalVersion :: Section Executable -> Maybe Version+ executableCabalVersion sect = maximum [+ makeVersion [2,0] <$ guard (executableHasGeneratedModules sect)+ , makeVersion [2,2] <$ guard (hasCxxParams sect)+ ]++ executableHasGeneratedModules :: Section Executable -> Bool+ executableHasGeneratedModules = any (not . null . executableGeneratedModules)++ hasCxxParams :: Section a -> Bool+ hasCxxParams sect = or [+ check sect+ , any (any check) (sectionConditionals sect)+ ]+ where+ check s = or [+ (not . null . sectionCxxOptions) s+ , (not . null . sectionCxxSources) s+ ] decodeValue :: FromValue a => FilePath -> Value -> Warnings (Errors IO) a decodeValue file value = do
+ src/Hpack/License.hs view
@@ -0,0 +1,48 @@+{-# LANGUAGE DeriveFunctor #-}+module Hpack.License where++import qualified Distribution.License as Cabal+import qualified Distribution.SPDX.License as SPDX+import Distribution.Parsec.Class (eitherParsec)++data License a = DontTouch | CanSPDX a | MustSPDX a+ deriving (Eq, Show, Functor)++parseLicense :: String -> License SPDX.License+parseLicense license = case spdxLicense of+ Right l | isUnknown -> MustSPDX l+ Left _ | isUnknown -> DontTouch+ Right l -> CanSPDX l+ Left _ -> case cabalLicense of+ Right l -> CanSPDX (Cabal.licenseToSPDX l)+ Left _ -> DontTouch+ where+ spdxLicense :: Either String SPDX.License+ spdxLicense = eitherParsec license++ cabalLicense :: Either String Cabal.License+ cabalLicense = eitherParsec license++ isUnknown = license `notElem` knownLicenses++ knownLicenses = [+ "GPL"+ , "GPL-2"+ , "GPL-3"+ , "LGPL"+ , "LGPL-2.1"+ , "LGPL-3"+ , "AGPL"+ , "AGPL-3"+ , "BSD2"+ , "BSD3"+ , "BSD4"+ , "MIT"+ , "ISC"+ , "MPL-2.0"+ , "Apache"+ , "Apache-2.0"+ , "PublicDomain"+ , "AllRightsReserved"+ , "OtherLicense"+ ]
src/Hpack/Render.hs view
@@ -38,13 +38,11 @@ import Data.Char import Data.Maybe import Data.List-import Data.Version import Data.Map.Lazy (Map) import qualified Data.Map.Lazy as Map import Hpack.Util import Hpack.Config-import Hpack.Syntax.Dependency (scientificToVersion) import Hpack.Render.Hints import Hpack.Render.Dsl @@ -112,7 +110,6 @@ files -> ("license-files", formatList files) , ("tested-with", packageTestedWith) , ("build-type", Just (show packageBuildType))- , ("cabal-version", cabalVersion) ] formatList :: [String] -> Maybe String@@ -120,66 +117,6 @@ where separator = let Alignment n = headerFieldsAlignment in ",\n" ++ replicate n ' ' - cabalVersion :: Maybe String- cabalVersion = (">= " ++) . showVersion <$> maximum [- Just (makeVersion [1,10])- , packageCabalVersion- , packageLibrary >>= libraryCabalVersion- , internalLibsCabalVersion packageInternalLibraries- , executablesCabalVersion packageExecutables- , executablesCabalVersion packageTests- , executablesCabalVersion packageBenchmarks- ]- where- packageCabalVersion :: Maybe Version- packageCabalVersion = maximum [- Nothing- , makeVersion [1,24] <$ packageCustomSetup- , makeVersion [1,18] <$ guard (not (null packageExtraDocFiles))- ]-- libraryCabalVersion :: Section Library -> Maybe Version- libraryCabalVersion sect = maximum [- makeVersion [1,22] <$ guard hasReexportedModules- , makeVersion [2,0] <$ guard hasSignatures- , makeVersion [2,0] <$ guard hasGeneratedModules- , makeVersion [2,2] <$ guard (hasCxxParams sect)- ]- where- hasReexportedModules = any (not . null . libraryReexportedModules) sect- hasSignatures = any (not . null . librarySignatures) sect- hasGeneratedModules = any (not . null . libraryGeneratedModules) sect-- internalLibsCabalVersion :: Map String (Section Library) -> Maybe Version- internalLibsCabalVersion internalLibraries- | Map.null internalLibraries = Nothing- | otherwise = foldr max (Just $ makeVersion [2,0]) versions- where- versions = libraryCabalVersion <$> Map.elems internalLibraries-- executablesCabalVersion :: Map String (Section Executable) -> Maybe Version- executablesCabalVersion = foldr max Nothing . map executableCabalVersion . Map.elems-- executableCabalVersion :: Section Executable -> Maybe Version- executableCabalVersion sect = maximum [- makeVersion [2,0] <$ guard (executableHasGeneratedModules sect)- , makeVersion [2,2] <$ guard (hasCxxParams sect)- ]-- executableHasGeneratedModules :: Section Executable -> Bool- executableHasGeneratedModules = any (not . null . executableGeneratedModules)-- hasCxxParams :: Section a -> Bool- hasCxxParams sect = or [- check sect- , any (any check) (sectionConditionals sect)- ]- where- check s = or [- (not . null . sectionCxxOptions) s- , (not . null . sectionCxxSources) s- ]- sortStanzaFields :: [(String, [String])] -> [Element] -> [Element] sortStanzaFields sectionsFieldOrder = go where@@ -336,13 +273,9 @@ renderVerbatimObject :: Map String VerbatimValue -> [Element] renderVerbatimObject = map renderPair . Map.toList where- renderPair (key, value) = case value of- VerbatimString s -> case lines s of- [x] -> Field key (Literal x)- xs -> Field key (LineSeparatedList xs)- VerbatimNumber n -> Field key (Literal $ scientificToVersion n)- VerbatimBool b -> Field key (Literal $ show b)- VerbatimNull -> Field key (Literal "")+ renderPair (key, value) = case lines (verbatimValueToString value) of+ [x] -> Field key (Literal x)+ xs -> Field key (LineSeparatedList xs) renderConditional :: (a -> [Element]) -> Conditional (Section a) -> Element renderConditional renderSectionData (Conditional condition sect mElse) = case mElse of
test/EndToEndSpec.hs view
@@ -299,6 +299,58 @@ version: {} |] `shouldFailWith` "package.yaml: Error while parsing $.version - expected Number or String, encountered Object" + describe "license" $ do+ it "accepts cabal-style licenses" $ do+ [i|+ license: BSD3+ |] `shouldRenderTo` (package [i|+ license: BSD3+ |])++ it "accepts SPDX licenses" $ do+ [i|+ license: BSD-3-Clause+ |] `shouldRenderTo` (package [i|+ license: BSD-3-Clause+ |]) {packageCabalVersion = "2.2"}++ context "with an ambiguous license" $ do+ it "treats it as a cabal-style license" $ do+ [i|+ license: MIT+ |] `shouldRenderTo` (package [i|+ license: MIT+ |])++ context "when cabal-version >= 2.2" $ do+ it "maps license to SPDX license identifier" $ do+ [i|+ license: BSD3+ library:+ cxx-options: -Wall+ |] `shouldRenderTo` (package [i|+ license: BSD-3-Clause+ library+ other-modules:+ Paths_foo+ cxx-options: -Wall+ default-language: Haskell2010+ |]) {packageCabalVersion = "2.2"}++ it "doesn't touch unknown licenses" $ do+ [i|+ license: some-license+ library:+ cxx-options: -Wall+ |] `shouldRenderTo` (package [i|+ license: some-license+ library+ other-modules:+ Paths_foo+ cxx-options: -Wall+ default-language: Haskell2010+ |]) {packageCabalVersion = "2.2"}+ describe "build-type" $ do it "accept Simple" $ do [i|@@ -476,7 +528,7 @@ cxx-options: -Wall |] `shouldRenderTo` (executable_ "foo" [i| cxx-options: -Wall- |]) {packageCabalVersion = ">= 2.2"}+ |]) {packageCabalVersion = "2.2"} describe "cxx-sources" $ before_ (touch "foo.cc" >> touch "cxxbits/bar.cc") $ do it "accepts cxx-sources" $ do@@ -489,7 +541,7 @@ cxx-sources: cxxbits/bar.cc foo.cc- |]) {packageCabalVersion = ">= 2.2"}+ |]) {packageCabalVersion = "2.2"} describe "extra-lib-dirs" $ do it "accepts extra-lib-dirs" $ do@@ -1240,12 +1292,12 @@ run_ userDataDir c old = do mPackage <- readPackageConfig defaultDecodeOptions {decodeOptionsTarget = c, decodeOptionsUserDataDir = Just userDataDir} return $ case mPackage of- Right (DecodeResult pkg _ warnings) ->+ Right (DecodeResult pkg cabalVersion _ warnings) -> let FormattingHints{..} = sniffFormattingHints (lines old) alignment = fromMaybe 0 formattingHintsAlignment settings = formattingHintsRenderSettings- output = Hpack.renderPackageWith settings alignment formattingHintsFieldOrder formattingHintsSectionsFieldOrder pkg+ output = cabalVersion ++ Hpack.renderPackageWith settings alignment formattingHintsFieldOrder formattingHintsSectionsFieldOrder pkg in Right (warnings, output) Left err -> Left err@@ -1349,10 +1401,10 @@ renderPackage :: Package -> String renderPackage Package{..} = unindent [i|+cabal-version: #{packageCabalVersion} name: #{packageName} version: #{packageVersion} build-type: #{packageBuildType}-cabal-version: #{packageCabalVersion} #{unindent packageContent} |]
test/Helper.hs view
@@ -3,6 +3,7 @@ module Helper ( module Test.Hspec , module Test.Mockery.Directory+, module Control.Monad , module Control.Applicative , withTempDirectory , module System.FilePath@@ -12,6 +13,7 @@ import Test.Hspec import Test.Mockery.Directory+import Control.Monad import Control.Applicative import System.Directory (getCurrentDirectory, setCurrentDirectory, canonicalizePath) import Control.Exception
test/Hpack/CabalFileSpec.hs view
@@ -4,7 +4,6 @@ import Helper import Test.QuickCheck import Data.Version (showVersion)-import Control.Monad import Data.String.Interpolate import Data.String.Interpolate.Util @@ -17,12 +16,18 @@ spec = do describe "readCabalFile" $ do let- file = "package.yaml"+ file = "hello.cabal" hash = "some-hash"+ it "includes hash" $ do inTempDirectory $ do- writeFile file $ header file version hash+ writeFile file $ header "package.yaml" version hash readCabalFile file `shouldReturn` Just (CabalFile (Just version) (Just hash) [])++ it "accepts cabal-version at the beginning of the file" $ do+ inTempDirectory $ do+ writeFile file $ ("cabal-version: 2.2\n" ++ header "package.yaml" version hash)+ readCabalFile file `shouldReturn` Just (CabalFile (Just version) (Just hash) ["cabal-version: 2.2"]) describe "extractVersion" $ do it "extracts Hpack version from a cabal file" $ do
test/Hpack/ConfigSpec.hs view
@@ -59,7 +59,7 @@ writeFile (dir </> "package.yaml") content withCurrentDirectory dir beforeAction r <- readPackageConfig (testDecodeOptions $ dir </> "package.yaml")- either expectationFailure (\ (DecodeResult p _ warnings) -> expectation (p, warnings)) r+ either expectationFailure (\ (DecodeResult p _ _ warnings) -> expectation (p, warnings)) r withPackageConfig :: String -> IO () -> (Package -> Expectation) -> Expectation withPackageConfig content beforeAction expectation = withPackage content beforeAction (expectation . fst)
+ test/Hpack/LicenseSpec.hs view
@@ -0,0 +1,57 @@+{-# LANGUAGE QuasiQuotes #-}+module Hpack.LicenseSpec (spec) where++import Helper+import Data.String.Interpolate++import Distribution.Pretty (prettyShow)++import Hpack.License++cabalLicenses :: [(String, License String)]+cabalLicenses = [+ ("GPL", CanSPDX "LicenseRef-GPL")+ , ("GPL-2", CanSPDX "GPL-2.0-only")+ , ("GPL-3", CanSPDX "GPL-3.0-only")++ , ("LGPL", CanSPDX "LicenseRef-LGPL")+ , ("LGPL-2.1", CanSPDX "LGPL-2.1-only")+ , ("LGPL-3", CanSPDX "LGPL-3.0-only")++ , ("AGPL", CanSPDX "LicenseRef-AGPL")+ , ("AGPL-3", CanSPDX "AGPL-3.0-only")+++ , ("BSD2", CanSPDX "BSD-2-Clause")+ , ("BSD3", CanSPDX "BSD-3-Clause")+ , ("BSD4", CanSPDX "BSD-4-Clause")++ , ("MIT", CanSPDX "MIT")+ , ("ISC", CanSPDX "ISC")++ , ("MPL-2.0", CanSPDX "MPL-2.0")++ , ("Apache", CanSPDX "LicenseRef-Apache")+ , ("Apache-2.0", CanSPDX "Apache-2.0")++ , ("PublicDomain", CanSPDX "LicenseRef-PublicDomain")+ , ("OtherLicense", CanSPDX "LicenseRef-OtherLicense")+ , ("AllRightsReserved", CanSPDX "NONE")+ ]++spdxLicenses :: [(String, License String)]+spdxLicenses = [+ ("GPL-2.0-or-later", MustSPDX "GPL-2.0-or-later")+ ]++unknownLicenses :: [(String, License String)]+unknownLicenses = [+ ("some-license", DontTouch)+ ]++spec :: Spec+spec = do+ describe "parseLicense" $ do+ forM_ (cabalLicenses ++ spdxLicenses ++ unknownLicenses) $ \ (license, expected) -> do+ it [i|parses #{license}|] $ do+ prettyShow <$> parseLicense license `shouldBe` expected
test/Hpack/RenderSpec.hs view
@@ -28,7 +28,6 @@ "name: foo" , "version: 0.0.0" , "build-type: Simple"- , "cabal-version: >= 1.10" ] it "aligns fields" $ do@@ -36,7 +35,6 @@ "name: foo" , "version: 0.0.0" , "build-type: Simple"- , "cabal-version: >= 1.10" ] it "includes description" $ do@@ -47,7 +45,6 @@ , " ." , " bar" , "build-type: Simple"- , "cabal-version: >= 1.10" ] it "aligns description" $ do@@ -58,7 +55,6 @@ , " ." , " bar" , "build-type: Simple"- , "cabal-version: >= 1.10" ] it "includes stability" $ do@@ -67,7 +63,6 @@ , "version: 0.0.0" , "stability: experimental" , "build-type: Simple"- , "cabal-version: >= 1.10" ] it "includes license-file" $ do@@ -76,7 +71,6 @@ , "version: 0.0.0" , "license-file: FOO" , "build-type: Simple"- , "cabal-version: >= 1.10" ] it "aligns license-files" $ do@@ -86,7 +80,6 @@ , "license-files: FOO," , " BAR" , "build-type: Simple"- , "cabal-version: >= 1.10" ] it "includes copyright holder" $ do@@ -95,7 +88,6 @@ , "version: 0.0.0" , "copyright: (c) 2015 Simon Hengel" , "build-type: Simple"- , "cabal-version: >= 1.10" ] it "aligns copyright holders" $ do@@ -105,7 +97,6 @@ , "copyright: (c) 2015 Foo," , " (c) 2015 Bar" , "build-type: Simple"- , "cabal-version: >= 1.10" ] it "includes extra-source-files" $ do@@ -113,7 +104,6 @@ "name: foo" , "version: 0.0.0" , "build-type: Simple"- , "cabal-version: >= 1.10" , "extra-source-files:" , " foo" , " bar"@@ -124,7 +114,6 @@ "name: foo" , "version: 0.0.0" , "build-type: Simple"- , "cabal-version: >= 1.10" , "" , "library" , " buildable: False"@@ -137,7 +126,6 @@ "name: foo" , "version: 0.0.0" , "build-type: Simple"- , "cabal-version: >= 1.10" , "" , "library" , " default-language: Haskell2010"@@ -145,19 +133,17 @@ context "when given list of existing fields" $ do it "retains field order" $ do- renderPackageWith defaultRenderSettings 16 ["cabal-version", "version", "name", "build-type"] [] package `shouldBe` unlines [- "cabal-version: >= 1.10"- , "version: 0.0.0"- , "name: foo"+ renderPackageWith defaultRenderSettings 16 ["version", "build-type", "name"] [] package `shouldBe` unlines [+ "version: 0.0.0" , "build-type: Simple"+ , "name: foo" ] it "uses default field order for new fields" $ do- renderPackageWith defaultRenderSettings 16 ["name", "version", "cabal-version"] [] package `shouldBe` unlines [+ renderPackageWith defaultRenderSettings 16 [] [] package `shouldBe` unlines [ "name: foo" , "version: 0.0.0" , "build-type: Simple"- , "cabal-version: >= 1.10" ] it "retains section field order" $ do@@ -165,7 +151,6 @@ "name: foo" , "version: 0.0.0" , "build-type: Simple"- , "cabal-version: >= 1.10" , "" , "executable foo" , " default-language: Haskell2010"@@ -180,7 +165,6 @@ "name: foo" , "version: 0.0.0" , "build-type: Simple"- , "cabal-version: >= 1.10" , "" , "executable foo" , " main-is: Main.hs"@@ -195,7 +179,6 @@ "name: foo" , "version: 0.0.0" , "build-type: Simple"- , "cabal-version: >= 1.10" , "" , "executable foo" , " main-is: Main.hs"@@ -208,7 +191,6 @@ "name: foo" , "version: 0.0.0" , "build-type: Simple"- , "cabal-version: >= 1.10" , "" , "executable foo" , " main-is: Main.hs"@@ -223,7 +205,6 @@ "name: foo" , "version: 0.0.0" , "build-type: Simple"- , "cabal-version: >= 1.10" , "" , "executable foo" , " main-is: Main.hs"@@ -238,7 +219,6 @@ "name: foo" , "version: 0.0.0" , "build-type: Simple"- , "cabal-version: >= 1.10" , "" , "executable foo" , " main-is: Main.hs"
test/Hpack/Syntax/GitSpec.hs view
@@ -3,7 +3,6 @@ import Helper import Data.String.Interpolate-import Control.Monad import Hpack.Syntax.Git