diff --git a/ChangeLog.md b/ChangeLog.md index 91a61d10..1fd30f25 100644 --- a/ChangeLog.md +++ b/ChangeLog.md @@ -1,7 +1,8 @@ # Changelog for pantry -## v0.9.2.1 +## v0.9.3 +* Add error S-628 (`LocalNoArchiveFileFound`). * Depend on `rio-prettyprint-0.1.7.0`. ## v0.9.2 diff --git a/app/test-pretty-exceptions/Main.hs b/app/test-pretty-exceptions/Main.hs index a89cb038..2d8be7a1 100644 --- a/app/test-pretty-exceptions/Main.hs +++ b/app/test-pretty-exceptions/Main.hs @@ -161,6 +161,7 @@ examples = concat , [ DownloadInvalidSHA256 urlExample (Mismatch sha256Example sha256Example) ] , [ DownloadInvalidSize urlExample (Mismatch fileSizeExample fileSizeExample) ] , [ DownloadTooLarge urlExample (Mismatch fileSizeExample fileSizeExample) ] + , [ LocalNoArchiveFileFound pathAbsFileExample ] , [ LocalInvalidSHA256 pathAbsFileExample (Mismatch sha256Example sha256Example) ] , [ LocalInvalidSize pathAbsFileExample (Mismatch fileSizeExample fileSizeExample) ] , [ UnknownArchiveType archiveLocation diff --git a/int/Pantry/Types.hs b/int/Pantry/Types.hs index ac764d2c..6dd80243 100644 --- a/int/Pantry/Types.hs +++ b/int/Pantry/Types.hs @@ -1080,6 +1080,7 @@ data PantryException | DownloadTooLarge !Text !(Mismatch FileSize) -- ^ Different from 'DownloadInvalidSize' since 'mismatchActual' is -- a lower bound on the size from the server. + | LocalNoArchiveFileFound !(Path Abs File) | LocalInvalidSHA256 !(Path Abs File) !(Mismatch SHA256) | LocalInvalidSize !(Path Abs File) !(Mismatch FileSize) | UnknownArchiveType !ArchiveLocation @@ -1186,8 +1187,9 @@ instance Display PantryException where <> "is not the package name." display (NoLocalPackageDirFound dir) = "Error: [S-395]\n" - <> "Stack looks for packages in the directories configured in\n" - <> "the 'packages' and 'extra-deps' fields defined in your stack.yaml\n" + <> "Stack looks for packages in the directories configured in the\n" + <> "'packages' and 'extra-deps' fields defined in its project-level\n" + <> "configuration file (usually stack.yaml)\n" <> "The current entry points to " <> fromString (toFilePath dir) <> ",\nbut no such directory could be found. If, alternatively, a package\n" @@ -1195,8 +1197,9 @@ instance Display PantryException where <> "specified as an extra-dep." display (NoCabalFileFound dir) = "Error: [S-636]\n" - <> "Stack looks for packages in the directories configured in\n" - <> "the 'packages' and 'extra-deps' fields defined in your stack.yaml\n" + <> "Stack looks for packages in the directories configured in the\n" + <> "'packages' and 'extra-deps' fields defined in its project-level\n" + <> "configuration file (usually stack.yaml)\n" <> "The current entry points to " <> fromString (toFilePath dir) <> ",\nbut no .cabal or package.yaml file could be found there." @@ -1300,6 +1303,14 @@ instance Display PantryException where <> display mismatchExpected <> ", stopped after receiving: " <> display mismatchActual + display (LocalNoArchiveFileFound path) = + "Error: [S-628]\n" + <> "Stack looks for packages in the archive files configured in the\n" + <> "'extra-deps' field defined in its project-level configuration file\n" + <> "(usually stack.yaml)\n" + <> "An entry points to " + <> fromString (toFilePath path) + <> ",\nbut no such archive file could be found." display (LocalInvalidSHA256 path Mismatch {..}) = "Error: [S-834]\n" <> "Mismatched SHA256 hash from " @@ -1541,8 +1552,8 @@ instance Pretty PantryException where , style Shell "packages" , "and" , style Shell "extra-deps" - , flow "fields defined in your" - , style File "stack.yaml" <> "." + , flow "fields defined in its project-level configuration file" + , parens (fillSep ["usually", style File "stack.yaml"]) <> "." , flow "The current entry points to" , pretty dir , flow "but no such directory could be found. If, alternatively, a" @@ -1557,8 +1568,8 @@ instance Pretty PantryException where , style Shell "packages" , "and" , style Shell "extra-deps" - , flow "fields defined in your" - , style File "stack.yaml" <> "." + , flow "fields defined in its project-level configuration file" + , parens (fillSep ["usually", style File "stack.yaml"]) <> "." , flow "The current entry points to" , pretty dir , flow "but no Cabal file or" @@ -1729,6 +1740,19 @@ instance Pretty PantryException where , flow "stopped after receiving:" , fromString . T.unpack $ textDisplay mismatchActual <> "." ] + pretty (LocalNoArchiveFileFound path) = + "[S-628]" + <> line + <> fillSep + [ flow "Stack looks for packages in the archive files configured in" + , "the" + , style Shell "extra-deps" + , flow "field defined in its project-level configuration file" + , parens (fillSep ["usually", style File "stack.yaml"]) <> "." + , flow "An entry points to" + , pretty path + , flow "but no such archive file could be found." + ] pretty (LocalInvalidSHA256 path Mismatch {..}) = "[S-834]" <> line diff --git a/package.yaml b/package.yaml index cdeffa3d..125cf204 100644 --- a/package.yaml +++ b/package.yaml @@ -1,5 +1,5 @@ name: pantry -version: 0.9.2 +version: 0.9.3 synopsis: Content addressable Haskell package management description: Please see the README on GitHub at category: Development diff --git a/pantry.cabal b/pantry.cabal index 51310d88..e2a0349a 100644 --- a/pantry.cabal +++ b/pantry.cabal @@ -5,7 +5,7 @@ cabal-version: 2.0 -- see: https://github.com/sol/hpack name: pantry -version: 0.9.2 +version: 0.9.3 synopsis: Content addressable Haskell package management description: Please see the README on GitHub at category: Development diff --git a/src/Pantry/Archive.hs b/src/Pantry/Archive.hs index d246a8ec..5c89ad15 100644 --- a/src/Pantry/Archive.hs +++ b/src/Pantry/Archive.hs @@ -47,6 +47,7 @@ import Pantry.Types , toRawArchive, toRawPM, unSafeFilePath ) import Path ( toFilePath ) +import Path.IO ( doesFileExist ) import RIO import qualified RIO.ByteString.Lazy as BL import qualified RIO.List as List @@ -236,7 +237,8 @@ checkPackageMetadata pl pm pa = do in if and tests then Right pa else Left err -- | Provide a local file with the contents of the archive, regardless of where --- it comes from. Perform SHA256 and file size validation if downloading. +-- it comes from. If not downloading, checks that the archive file exists. +-- Performs SHA256 and file size validation. withArchiveLoc :: HasLogFunc env => RawArchive @@ -245,6 +247,9 @@ withArchiveLoc :: withArchiveLoc (RawArchive (ALFilePath resolved) msha msize _subdir) f = do let abs' = resolvedAbsolute resolved fp = toFilePath abs' + archiveExists <- doesFileExist abs' + unless archiveExists $ + throwIO $ LocalNoArchiveFileFound abs' (sha, size) <- withBinaryFile fp ReadMode $ \h -> do size <- FileSize . fromIntegral <$> hFileSize h for_ msize $ \size' ->