diff --git a/CHANGELOG.md b/CHANGELOG.md
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,9 @@
+## Zip 1.5.0
+
+* Added the `packDirRecur'` function.
+
+* Dropped support for GHC 8.4.
+
 ## Zip 1.4.1
 
 * Fixed the build on Mac.
diff --git a/Codec/Archive/Zip.hs b/Codec/Archive/Zip.hs
--- a/Codec/Archive/Zip.hs
+++ b/Codec/Archive/Zip.hs
@@ -113,6 +113,7 @@
   , loadEntry
   , copyEntry
   , packDirRecur
+  , packDirRecur'
     -- ** Modifying entries
   , renameEntry
   , deleteEntry
@@ -458,11 +459,28 @@
      -- directory we pack
   -> FilePath          -- ^ Path to directory to add
   -> ZipArchive ()
-packDirRecur t f path = do
+packDirRecur t f = packDirRecur' t f (const $ return ())
+
+-- | The same as 'packDirRecur' but allows us to perform modifying actions
+-- on the created entities as we go.
+--
+-- @since 1.5.0
+
+packDirRecur'
+  :: CompressionMethod -- ^ Compression method to use
+  -> (FilePath -> ZipArchive EntrySelector)
+     -- ^ How to get 'EntrySelector' from a path relative to the root of the
+     -- directory we pack
+  -> (EntrySelector -> ZipArchive ())
+     -- ^ How to modify an entry after creation
+  -> FilePath -- ^ Path to directory to add
+  -> ZipArchive ()
+packDirRecur' t f patch path = do
   files <- liftIO (listDirRecur path)
   forM_ files $ \x -> do
     s <- f x
     loadEntry t s (path </> x)
+    patch s
 
 -- | Rename an entry in the archive. If the entry does not exist, nothing
 -- will happen.
diff --git a/tests/Main.hs b/tests/Main.hs
--- a/tests/Main.hs
+++ b/tests/Main.hs
@@ -78,7 +78,7 @@
     describe "undoArchiveChanges" undoArchiveChangesSpec
     describe "undoAll"            undoAllSpec
     describe "consistency"        consistencySpec
-    describe "packDirRecur"       packDirRecurSpec
+    describe "packDirRecur'"      packDirRecur'Spec
     describe "unpackInto"         unpackIntoSpec
 
 ----------------------------------------------------------------------------
@@ -671,8 +671,8 @@
       txt' `shouldBe` Just txt
       m' `shouldSatisfy` softEqMap m
 
-packDirRecurSpec :: SpecWith FilePath
-packDirRecurSpec =
+packDirRecur'Spec :: SpecWith FilePath
+packDirRecur'Spec =
   it "packs arbitrary directory recursively" $
     \path -> property $
       forAll (downScale arbitrary) $ \contents ->
@@ -681,12 +681,19 @@
             let item = dir </> unEntrySelector s
             createDirectoryIfMissing True (FP.takeDirectory item)
             B.writeFile item "foo"
-          selectors <-
+          let magicFileAttrs = 123456789
+          entries <-
             createArchive path $ do
-              packDirRecur Store mkEntrySelector dir
+              packDirRecur'
+                Store
+                mkEntrySelector
+                (setExternalFileAttrs magicFileAttrs)
+                dir
               commit
-              M.keysSet <$> getEntries
-          selectors `shouldBe` E.fromList contents
+              getEntries
+          M.keysSet entries `shouldBe` E.fromList contents
+          forM_ (M.elems entries) $ \desc ->
+            edExternalFileAttrs desc `shouldBe` magicFileAttrs
 
 unpackIntoSpec :: SpecWith FilePath
 unpackIntoSpec =
diff --git a/zip.cabal b/zip.cabal
--- a/zip.cabal
+++ b/zip.cabal
@@ -1,7 +1,7 @@
 name:                 zip
-version:              1.4.1
+version:              1.5.0
 cabal-version:        1.18
-tested-with:          GHC==8.4.4, GHC==8.6.5, GHC==8.8.3
+tested-with:          GHC==8.6.5, GHC==8.8.3, GHC==8.10.1
 license:              BSD3
 license-file:         LICENSE.md
 author:               Mark Karpov <markkarpov92@gmail.com>
