diff --git a/net-mqtt.cabal b/net-mqtt.cabal
--- a/net-mqtt.cabal
+++ b/net-mqtt.cabal
@@ -5,7 +5,7 @@
 -- see: https://github.com/sol/hpack
 
 name:           net-mqtt
-version:        0.8.2.2
+version:        0.8.2.3
 synopsis:       An MQTT Protocol Implementation.
 description:    Please see the README on GitHub at <https://github.com/dustin/mqtt-hs#readme>
 category:       Network
diff --git a/src/Network/MQTT/Client.hs b/src/Network/MQTT/Client.hs
--- a/src/Network/MQTT/Client.hs
+++ b/src/Network/MQTT/Client.hs
@@ -370,10 +370,7 @@
 waitForClient :: MQTTClient -> IO ()
 waitForClient c@MQTTClient{..} = flip E.finally (stopCallbackThread c) $ do
   void . traverse wait =<< readTVarIO _ct
-  e <- atomically $ stateX c Stopped
-  case e of
-    Nothing -> pure ()
-    Just x  -> E.throwIO x
+  maybe (pure ()) E.throwIO =<< atomically (stateX c Stopped)
 
 stateX :: MQTTClient -> ConnState -> STM (Maybe E.SomeException)
 stateX MQTTClient{..} want = f <$> readTVar _st
@@ -695,7 +692,7 @@
 
 -- | Get the list of properties that were sent from the broker at connect time.
 svrProps :: MQTTClient -> IO [Property]
-svrProps mc = p <$> atomically (connACKSTM mc)
+svrProps = fmap p . atomically . connACKSTM
   where p (ConnACKFlags _ _ props) = props
 
 -- | Get the complete connection ACK packet from the beginning of this session.
@@ -707,7 +704,7 @@
 connACK = atomically . connACKSTM
 
 maxAliases :: MQTTClient -> IO Word16
-maxAliases mc = foldr f 0 <$> svrProps mc
+maxAliases = fmap (foldr f 0) . svrProps
   where
     f (PropTopicAliasMaximum n) _ = n
     f _ o                         = o
diff --git a/src/Network/MQTT/Types.hs b/src/Network/MQTT/Types.hs
--- a/src/Network/MQTT/Types.hs
+++ b/src/Network/MQTT/Types.hs
@@ -349,9 +349,7 @@
                                 <> toByteString prot _willMsg
 
       perhaps :: Maybe BL.ByteString -> BL.ByteString
-      perhaps Nothing  = ""
-      perhaps (Just s) = toByteString prot s
-
+      perhaps = maybe "" (toByteString prot)
 
 data MQTTPkt = ConnPkt ConnectRequest ProtocolLevel
              | ConnACKPkt ConnACKFlags
@@ -660,19 +658,18 @@
 instance ByteMe PubACK where
   toByteString prot (PubACK pid st props) = bsPubSeg prot 0x40 pid st props
 
-parsePubSeg :: A.Parser (PktID, Word8, [Property])
-parsePubSeg = do
+-- Common parser for all of the pub parts for q>0 handling:  (PubACK, PubREC, PubREL, PubCOMP)
+parsePubSeg :: Word8 -> (a -> MQTTPkt) -> (PktID -> Word8 -> [Property] -> a) -> A.Parser MQTTPkt
+parsePubSeg i cona conb = do
+  _ <- A.word8 i
   rl <- parseHdrLen
   mid <- aWord16
   st <- if rl > 2 then A.anyWord8 else pure 0
   props <- if rl > 3 then parseProperties Protocol50 else pure mempty
-  pure (mid, st, props)
+  pure $ cona (conb mid st props)
 
 parsePubACK :: A.Parser MQTTPkt
-parsePubACK = do
-  _ <- A.word8 0x40
-  (mid, st, props) <- parsePubSeg
-  pure $ PubACKPkt (PubACK mid st props)
+parsePubACK = parsePubSeg 0x40 PubACKPkt PubACK
 
 data PubREC = PubREC PktID Word8 [Property] deriving(Eq, Show)
 
@@ -680,10 +677,7 @@
   toByteString prot (PubREC pid st props) = bsPubSeg prot 0x50 pid st props
 
 parsePubREC :: A.Parser MQTTPkt
-parsePubREC = do
-  _ <- A.word8 0x50
-  (mid, st, props) <- parsePubSeg
-  pure $ PubRECPkt (PubREC mid st props)
+parsePubREC = parsePubSeg 0x50 PubRECPkt PubREC
 
 data PubREL = PubREL PktID Word8 [Property] deriving(Eq, Show)
 
@@ -691,10 +685,7 @@
   toByteString prot (PubREL pid st props) = bsPubSeg prot 0x62 pid st props
 
 parsePubREL :: A.Parser MQTTPkt
-parsePubREL = do
-  _ <- A.word8 0x62
-  (mid, st, props) <- parsePubSeg
-  pure $ PubRELPkt (PubREL mid st props)
+parsePubREL = parsePubSeg 0x62 PubRELPkt PubREL
 
 data PubCOMP = PubCOMP PktID Word8 [Property] deriving(Eq, Show)
 
@@ -702,10 +693,7 @@
   toByteString prot (PubCOMP pid st props) = bsPubSeg prot 0x70 pid st props
 
 parsePubCOMP :: A.Parser MQTTPkt
-parsePubCOMP = do
-  _ <- A.word8 0x70
-  (mid, st, props) <- parsePubSeg
-  pure $ PubCOMPPkt (PubCOMP mid st props)
+parsePubCOMP = parsePubSeg 0x70 PubCOMPPkt PubCOMP
 
 -- Common header bits for subscribe, unsubscribe, and the sub acks.
 parseSubHdr :: Word8 -> ProtocolLevel -> A.Parser a -> A.Parser (PktID, [Property], a)
