diff --git a/ChangeLog.md b/ChangeLog.md
--- a/ChangeLog.md
+++ b/ChangeLog.md
@@ -6,6 +6,20 @@
 
 # Revision history for haskell-amqp-utils
 
+## 0.6.7.2  -- 2025-07-29
+
+* add cabal bounds
+* add copy-to-hotfolder simple callback script
+* update flake to nixos-25.05
+* update stack.yaml to lts-24.2 (ghc-9.10.2)
+* fix builds.sr.ht openbsd and alpine builds
+* add Dockerfile for static linux binaries (thanks mdom)
+* agitprop:
+  * ignore dotfiles even without -S
+  * only send regular files in hotfolder mode
+  * add --watchcreate (-L) option to get hardlink events
+  * ignore empty files with --watchcreate (-L)
+
 ## 0.6.6.0  -- 2024-12-06
 
 * LineBuffering
diff --git a/Network/AMQP/Utils/Options.hs b/Network/AMQP/Utils/Options.hs
--- a/Network/AMQP/Utils/Options.hs
+++ b/Network/AMQP/Utils/Options.hs
@@ -82,6 +82,7 @@
     , initialScan     :: Bool
     , streamoffset    :: FieldTable
     , delaynack       :: Int
+    , watchCreate     :: Bool
     }
 
 instance Default Args where
@@ -138,6 +139,7 @@
       False
       (FieldTable M.empty)
       0
+      False
 
 -- | all options
 allOptions :: [(String, OptDescr (Args -> Args))]
@@ -475,6 +477,12 @@
         (ReqArg (\s o -> o {delaynack = read s}) "SECONDS")
         ("delay negative acknowledgements (default: " ++
          show (delaynack def) ++ ")"))
+  , ( "a"
+    , Option
+        ['L']
+        ["watchcreate"]
+        (NoArg (\o -> o {watchCreate = not (watchCreate o)}))
+        ("Toggle watching Create (ln) events in hotfolder mode (default: " ++ show (watchCreate def) ++ ")"))
   ]
 
 -- | Options for the executables
diff --git a/README.md b/README.md
--- a/README.md
+++ b/README.md
@@ -11,7 +11,7 @@
 - publisher (`agitprop`)
 - rpc client and worker (`plane` / `arbeite`)
 
-## konsum - an AMQP consumer.
+## konsum - AMQP consumer.
 
 **konsum** [*options*]
 
@@ -78,7 +78,7 @@
 
 Stop with ^C
 
-## agitprop - an AMQP publisher
+## agitprop - AMQP publisher
 
 **agitprop** [*options*]
 
@@ -89,7 +89,8 @@
 optionally only files which match one or several SUFFIXes. Optionally the file
 name is written into a message header named HEADERNAME.  Optionally
 Content-Type and Content-Encoding headers are set via magic retrieved from file
-contents.
+contents. Filenames beginning with a dot (.) are ignored. With -L also files
+created by hardlinking are recognized, empty files are ignored.
 
 Line-by-line mode sends one message per INPUTFILE line.
 
@@ -132,6 +133,7 @@
       -s INT           --heartbeats=INT                   heartbeat interval (0=disable, default: set by server)
       -n NAME          --name=NAME                        connection name, will be shown in RabbitMQ web interface
       -w SECONDS       --connect_timeout=SECONDS          timeout for establishing initial connection (default: 600)
+      -L               --watchcreate                      Toggle watching Create (ln) events in hotfolder mode (default: False)
 
 ### EXAMPLES
 
@@ -147,7 +149,7 @@
 
     agitprop -x amq.topic -F fileName -m -S .txt -S .zip -d -udone -r r1 -f dir1 -r r2 -f dir2
 
-## plane - an AMQP RPC client.
+## plane - AMQP RPC client.
 
 **plane** [*options*]
 
@@ -180,7 +182,7 @@
 
     echo ls | plane -o amqp.example.com -T -k amqp.pem -c amqp.pem -y myexchange -Q rpctest
 
-## arbeite - an AMQP RPC worker.
+## arbeite - AMQP RPC worker.
 
 **arbeite** [*options*]
 
@@ -296,6 +298,8 @@
   - git://woffs.de/git/fd/haskell-amqp-utils.git
   - https://woffs.de/git/fd/haskell-amqp-utils.git
   - https://git.sr.ht/~woffs/haskell-amqp-utils
+  - https://git.disroot.org/woffs/haskell-amqp-utils
+  - [Radicle](https://radicle.xyz): `rad clone rad:zMhy3AsYnY2QHcfQuVGVW9N5RsRJ`
 - Repology: https://repology.org/project/haskell:amqp-utils/packages
 - Hackage: https://hackage.haskell.org/package/amqp-utils
 - Stackage: https://www.stackage.org/package/amqp-utils
diff --git a/agitprop.hs b/agitprop.hs
--- a/agitprop.hs
+++ b/agitprop.hs
@@ -8,7 +8,7 @@
 -- generic AMQP publisher
 import           Control.Concurrent
 import qualified Control.Exception                as X
-import           Control.Monad                    (forM_)
+import           Control.Monad                    (forM_, when)
 import qualified Data.ByteString.Char8            as BS
 import qualified Data.ByteString.Lazy.Char8       as BL
 import qualified Data.Map                         as M
@@ -64,6 +64,7 @@
     then do
       printparam "hotfolder mode" True
       printparam "initial scan" (initialScan args)
+      printparam "watch create events" (watchCreate args)
       if isNothing (moveSentFileTo args)
         then printparam "remove sent file" (removeSentFile args)
         else printparam "move sent file to" (moveSentFileTo args)
@@ -116,17 +117,23 @@
   printparam "hotfolder" folder
   inotify <- initINotify
   wd <-
-   addWatch
-     inotify
-     [CloseWrite, MoveIn]
-     folder
-     (handleEvent (publishOneMsg exchange rkey) (suffix args) folder)
+    addWatch
+      inotify
+      [CloseWrite, MoveIn, Create]
+      folder
+      (handleEvent (publishOneMsg exchange rkey) (suffix args) (watchCreate args) folder)
   hr "BEGIN watching"
   if (initialScan args)
-   then RD.listDirectory folder >>=
-        mapM_ (\fn -> handleFile (publishOneMsg exchange rkey) (suffix args) (folder </> fn))
-   else return ()
-  return (wd,folder)
+    then RD.listDirectory folder
+           >>= mapM_
+                 (\fn ->
+                    handleFile
+                      (publishOneMsg exchange rkey)
+                      (suffix args)
+                      folder
+                      fn)
+    else return ()
+  return (wd, folder)
 #endif
 
 -- | A handler for clean exit
@@ -152,25 +159,38 @@
 #if linux_HOST_OS
 -- | Hotfolder event handler
 handleEvent ::
-     (Maybe RawFilePath -> BL.ByteString -> IO ()) -> [BS.ByteString] -> RawFilePath -> Event -> IO ()
+     (Maybe RawFilePath -> BL.ByteString -> IO ()) -> [BS.ByteString] -> Bool -> RawFilePath -> Event -> IO ()
 -- just handle closewrite and movedin events
-handleEvent func suffixes folder (Closed False (Just fileName) True) =
-  handleFile func suffixes (folder </> fileName)
-handleEvent func suffixes folder (MovedIn False fileName _) =
-  handleFile func suffixes (folder </> fileName)
-handleEvent _ _ _ _ = return ()
+handleEvent func suffixes _ folder (Closed False (Just fileName) True) =
+  handleFile func suffixes folder fileName
+handleEvent func suffixes _ folder (MovedIn False fileName _) =
+  handleFile func suffixes folder fileName
+-- handle create events when requested (detects ln)
+handleEvent func suffixes True folder (Created False fileName) =
+  handleFile func suffixes folder fileName
+handleEvent _ _ _ _ _ = return ()
 
 -- | Hotfolder file handler
 handleFile ::
-     (Maybe RawFilePath -> BL.ByteString -> IO ()) -> [BS.ByteString] -> RawFilePath -> IO ()
-handleFile func suffixes@(_:_) fileName =
-  if (any (flip BS.isSuffixOf fileName) suffixes) && not ("." `BS.isPrefixOf` fileName)
-    then handleFile func [] fileName
-    else return ()
-handleFile func [] fileName =
-  X.catch
-    (readFileRawLazy fileName >>= func (Just fileName))
-    (\e -> printparam "exception while processing" fileName >> printparam "exception in handleFile" (e :: X.IOException))
+     (Maybe RawFilePath -> BL.ByteString -> IO ())
+  -> [BS.ByteString]
+  -> RawFilePath
+  -> RawFilePath
+  -> IO ()
+handleFile func suffixes@(_:_) folder fileName =
+  when
+    (any (flip BS.isSuffixOf fileName) suffixes)
+    (handleFile func [] folder fileName)
+handleFile func [] folder fileName = do
+  fStatus <- F.getFileStatus path
+  when (not ("." `BS.isPrefixOf` fileName) && F.isRegularFile fStatus && F.fileSize fStatus > 0)
+    $ X.catch
+        (readFileRawLazy path >>= func (Just path))
+        (\e ->
+           printparam "exception while processing" fileName
+             >> printparam "exception in handleFile" (e :: X.IOException))
+  where
+    path = folder </> fileName
 #endif
 
 -- | Publish one message with our settings
diff --git a/amqp-utils.cabal b/amqp-utils.cabal
--- a/amqp-utils.cabal
+++ b/amqp-utils.cabal
@@ -4,7 +4,7 @@
 
 name:                amqp-utils
 
-version:             0.6.6.0
+version:             0.6.7.2
 
 synopsis:            AMQP toolset for the command line
 
@@ -37,22 +37,22 @@
 
 executable konsum
   main-is:             konsum.hs
-  build-depends:       base >= 4.6 && <5,
-                       containers,
-                       text,
-                       crypton-connection,
-                       data-default-class,
-                       time,
-                       process,
-                       directory,
-                       bytestring,
-                       utf8-string,
-                       filepath-bytestring,
-                       crypton-x509-system,
-                       network > 2.6,
-                       tls >= 1.7.0,
-                       amqp >= 0.22.2,
-                       unix >= 2.8
+  build-depends:       base >= 4.6 && < 5,
+                       containers >= 0.6 && < 0.8,
+                       text >= 2.0 && < 2.2,
+                       crypton-connection >= 0.3 && < 0.5,
+                       data-default-class >= 0.1 && < 0.3,
+                       time >= 1.12 && < 1.13,
+                       process >= 1.6 && < 1.7,
+                       directory >= 1.3 && < 1.4,
+                       bytestring >= 0.11 && < 0.13,
+                       utf8-string >= 1.0 && < 1.1,
+                       filepath-bytestring >= 1.4 && < 1.6,
+                       crypton-x509-system >= 1.6 && < 1.7,
+                       network > 2.6 && < 3.3,
+                       tls >= 1.7.0 && < 2.2,
+                       amqp >= 0.22.2 && < 0.25,
+                       unix >= 2.8 && < 2.9
 
   ghc-options:         -threaded -Wall
 
@@ -66,26 +66,26 @@
 executable agitprop
   main-is:             agitprop.hs
   build-depends:       base >= 4.6 && <5,
-                       containers,
-                       text,
-                       crypton-connection,
-                       data-default-class,
-                       time,
-                       process,
-                       directory,
-                       filepath,
-                       bytestring,
-                       utf8-string,
-                       rawfilepath,
-                       filepath-bytestring,
-                       crypton-x509-system,
-                       network > 2.6,
-                       tls >= 1.7.0,
-                       amqp >= 0.22.2,
-                       unix >= 2.8,
-                       magic
+                       containers >= 0.6 && < 0.8,
+                       text >= 2.0 && < 2.2,
+                       crypton-connection >= 0.3 && < 0.5,
+                       data-default-class >= 0.1 && < 0.3,
+                       time >= 1.12 && < 1.13,
+                       process >= 1.6 && < 1.7,
+                       directory >= 1.3 && < 1.4,
+                       bytestring >= 0.11 && < 0.13,
+                       utf8-string >= 1.0 && < 1.1,
+                       filepath-bytestring >= 1.4 && < 1.6,
+                       crypton-x509-system >= 1.6 && < 1.7,
+                       network > 2.6 && < 3.3,
+                       tls >= 1.7.0 && < 2.2,
+                       amqp >= 0.22.2 && < 0.25,
+                       unix >= 2.8 && < 2.9,
+                       filepath >= 1.4 && < 1.6,
+                       rawfilepath >= 1.1.1 && < 1.2,
+                       magic >= 1.1 && < 1.2
   if os(linux)
-    build-depends:     hinotify >= 0.3.10
+    build-depends:     hinotify >= 0.3.10 && < 0.5
 
   ghc-options:         -threaded -Wall
 
@@ -99,21 +99,21 @@
 executable plane
   main-is:             plane.hs
   build-depends:       base >=4.6 && <5,
-                       containers,
-                       text,
-                       crypton-connection,
-                       data-default-class,
-                       time,
-                       process,
-                       directory,
-                       bytestring,
-                       utf8-string,
-                       filepath-bytestring,
-                       crypton-x509-system,
-                       network > 2.6,
-                       tls >= 1.7.0,
-                       amqp >=0.22.2,
-                       unix >= 2.8
+                       containers >= 0.6 && < 0.8,
+                       text >= 2.0 && < 2.2,
+                       crypton-connection >= 0.3 && < 0.5,
+                       data-default-class >= 0.1 && < 0.3,
+                       time >= 1.12 && < 1.13,
+                       process >= 1.6 && < 1.7,
+                       directory >= 1.3 && < 1.4,
+                       bytestring >= 0.11 && < 0.13,
+                       utf8-string >= 1.0 && < 1.1,
+                       filepath-bytestring >= 1.4 && < 1.6,
+                       crypton-x509-system >= 1.6 && < 1.7,
+                       network > 2.6 && < 3.3,
+                       tls >= 1.7.0 && < 2.2,
+                       amqp >= 0.22.2 && < 0.25,
+                       unix >= 2.8 && < 2.9
 
   ghc-options:         -threaded -Wall
 
@@ -127,21 +127,21 @@
 executable arbeite
   main-is:             arbeite.hs
   build-depends:       base >= 4.6 && <5,
-                       containers,
-                       text,
-                       crypton-connection,
-                       data-default-class,
-                       time,
-                       process,
-                       directory,
-                       bytestring,
-                       utf8-string,
-                       filepath-bytestring,
-                       crypton-x509-system,
-                       network > 2.6,
-                       tls >= 1.7.0,
-                       amqp >= 0.22.2,
-                       unix >= 2.8
+                       containers >= 0.6 && < 0.8,
+                       text >= 2.0 && < 2.2,
+                       crypton-connection >= 0.3 && < 0.5,
+                       data-default-class >= 0.1 && < 0.3,
+                       time >= 1.12 && < 1.13,
+                       process >= 1.6 && < 1.7,
+                       directory >= 1.3 && < 1.4,
+                       bytestring >= 0.11 && < 0.13,
+                       utf8-string >= 1.0 && < 1.1,
+                       filepath-bytestring >= 1.4 && < 1.6,
+                       crypton-x509-system >= 1.6 && < 1.7,
+                       network > 2.6 && < 3.3,
+                       tls >= 1.7.0 && < 2.2,
+                       amqp >= 0.22.2 && < 0.25,
+                       unix >= 2.8 && < 2.9
 
   ghc-options:         -threaded -Wall
 
