monitorCluster :: STM.AdvSTM (Maybe BaseUrl) -> STM.TVar AppState -> STM.TVar (Maybe CM.Cluster) -> IO ()
monitorCluster urlM stateV clusterV = traverse_ go =<< STM.atomically urlM
  where
    go url = runEitherT (slaveResources url) >>= \case
        Right cluster -> STM.atomically $ do
            STM.writeTVar clusterV (Just cluster)
            state <- STM.readTVar stateV
            let (_, ts) = ES.runState state $ CM.updateSatisfiabilities cluster state
            STM.writeTVar stateV $ ts ^. ES.appState
        Left (ex :: ServantError) -> do
            hPutStrLn stderr $ "Error connecting to health monitor at " ++ show url ++ "; retrying: " ++ show ex
            STM.atomically $ do
                STM.writeTVar clusterV Nothing
                state <- STM.readTVar stateV
                let (_, ts) = ES.runState state $ CM.allSatisfyUnknown state
                STM.writeTVar stateV $ ts ^. ES.appState
monitorCluster :: STM.AdvSTM (Maybe BaseUrl) -> STM.TVar AppState -> STM.TVar (Maybe CM.Cluster) -> IO ()
monitorCluster urlM stateV clusterV = traverse_ go =<< STM.atomically urlM
  where
    go url = runEitherT (slaveResources url) >>= \case
        Right cluster -> STM.atomically $ do
            STM.writeTVar clusterV (Just cluster)
            state <- STM.readTVar stateV
            let (_, ts) = ES.runState state $ CM.updateSatisfiabilities cluster state
            STM.writeTVar stateV $ ts ^. ES.appState
        Left (ex :: ServantError) -> do
            hPutStrLn stderr $ "Error connecting to health monitor at " ++ show url ++ "; retrying: " ++ show ex
            STM.atomically $ do
                STM.writeTVar clusterV Nothing
                state <- STM.readTVar stateV
                let (_, ts) = ES.runState state $ CM.allSatisfyUnknown state
                STM.writeTVar stateV $ ts ^. ES.appState
monitorCluster urlM stateV clusterV = traverse_ go =<< STM.atomically urlM
  where
    go url = runEitherT (slaveResources url) >>= \case
        Right cluster -> STM.atomically $ do
            STM.writeTVar clusterV (Just cluster)
            state <- STM.readTVar stateV
            let (_, ts) = ES.runState state $ CM.updateSatisfiabilities cluster state
            STM.writeTVar stateV $ ts ^. ES.appState
        Left (ex :: ServantError) -> do
            hPutStrLn stderr $ "Error connecting to health monitor at " ++ show url ++ "; retrying: " ++ show ex
            STM.atomically $ do
                STM.writeTVar clusterV Nothing
                state <- STM.readTVar stateV
                let (_, ts) = ES.runState state $ CM.allSatisfyUnknown state
                STM.writeTVar stateV $ ts ^. ES.appState