diff --git a/ChangeLog.md b/ChangeLog.md
--- a/ChangeLog.md
+++ b/ChangeLog.md
@@ -1,3 +1,5 @@
 # Changelog for zoovisitor
 
-## Unreleased changes
+## v0.1.2.0
+
+- Add `zooDeleteAll`
diff --git a/src/ZooKeeper.hs b/src/ZooKeeper.hs
--- a/src/ZooKeeper.hs
+++ b/src/ZooKeeper.hs
@@ -15,6 +15,7 @@
   , zooGetChildren2
   , zooWatchGetChildren2
   , zooDelete
+  , zooDeleteAll
   , zooExists
   , zooWatchExists
   , zooGetAcl
@@ -51,6 +52,7 @@
 import qualified Z.Data.Text.Print        as Text
 import           Z.Data.Vector            (Bytes)
 import qualified Z.Foreign                as Z
+import qualified Z.IO.FileSystem.FilePath as ZF
 import qualified Z.IO.Resource            as Res
 
 import qualified ZooKeeper.Exception      as E
@@ -253,6 +255,15 @@
       cfunc = I.c_hs_zoo_adelete zh path' version
       version = fromMaybe (-1) m_version
    in void $ E.throwZooErrorIfLeft =<< I.withZKAsync csize I.peekRet I.peekData cfunc
+
+-- | Delete a node and all its children in zookeeper.
+--
+-- If fail will throw exceptions, check `zooDeleteAll` and `zooGetChildren` for more details
+zooDeleteAll :: HasCallStack => T.ZHandle -> CBytes -> IO ()
+zooDeleteAll zh path = do
+  T.StringsCompletion (T.StringVector children) <- zooGetChildren zh path
+  mapM_ (zooDeleteAll zh <=< ZF.join path) children
+  zooDelete zh path Nothing
 
 -- | Checks the existence of a node in zookeeper.
 --
diff --git a/test/Spec.hs b/test/Spec.hs
--- a/test/Spec.hs
+++ b/test/Spec.hs
@@ -43,7 +43,7 @@
       dataCompletionValue <$> zooGet zh "/a" `shouldReturn` Nothing
 
   describe "ZooKeeper.zooWatchExists" $ do
-    it "wathch for node to appear" $ do
+    it "watch for node to appear" $ do
       ctx <- newEmptyMVar
       ret <- newEmptyMVar
       _ <- forkIO $ zooWatchExists zh "/b" (ctx `putMVar`) (ret `putMVar`)
@@ -53,6 +53,17 @@
       watcherCtxType ctx' `shouldBe` ZooCreateEvent
       watcherCtxState ctx' `shouldBe` ZooConnectedState
       watcherCtxPath ctx' `shouldBe` Just "/b"
+
+  describe "ZooKeeper.zooDeleteAll" $ do
+    it "test recursively delete" $ do
+      void $ zooCreate zh "/x" Nothing zooOpenAclUnsafe ZooPersistent
+      void $ zooCreate zh "/x/1" Nothing zooOpenAclUnsafe ZooPersistent
+      void $ zooCreate zh "/x/2" Nothing zooOpenAclUnsafe ZooPersistent
+      void $ zooCreate zh "/x/2/1" Nothing zooOpenAclUnsafe ZooPersistent
+      unStrVec . strsCompletionValues <$> zooGetChildren zh "/x" `shouldReturn` ["1", "2"]
+      zooDeleteAll zh "/x" `shouldReturn` ()
+      void $ zooCreate zh "/x" Nothing zooOpenAclUnsafe ZooPersistent
+      zooDeleteAll zh "/x" `shouldReturn` ()
 
   describe "ZooKeeper.zooGetChildren" $ do
     it "test get children" $ do
diff --git a/zoovisitor.cabal b/zoovisitor.cabal
--- a/zoovisitor.cabal
+++ b/zoovisitor.cabal
@@ -1,6 +1,6 @@
 cabal-version:      2.2
 name:               zoovisitor
-version:            0.1.1.1
+version:            0.1.2.0
 synopsis:
   A haskell binding to Apache Zookeeper C library(mt) using Haskell Z project.
 
