{-# LANGUAGE RecordWildCards #-}
module Language.PureScript.Ide.Watcher where

import           Prelude                         ()
import           Prelude.Compat

import           Control.Concurrent              (threadDelay)
import           Control.Concurrent.STM
import           Control.Monad
import           Control.Monad.Trans.Except
import qualified Data.Map                        as M
import           Data.Maybe                      (isJust)
import           Language.PureScript.Externs
import           Language.PureScript.Ide.Externs
import           Language.PureScript.Ide.State
import           Language.PureScript.Ide.Types
import           System.FilePath
import           System.FSNotify


reloadFile :: TVar PscIdeState -> FilePath -> IO ()
reloadFile stateVar fp = do
  (Right ef@ExternsFile{..}) <- runExceptT $ readExternFile fp
  reloaded <- atomically $ do
    st <- readTVar stateVar
    if isLoaded efModuleName st
      then
        insertModule' stateVar ef *> pure True
      else
        pure False
  when reloaded $ putStrLn $ "Reloaded File at: " ++ fp
  where
    isLoaded name st = isJust (M.lookup name (externsFiles st))

watcher :: TVar PscIdeState -> FilePath -> IO ()
watcher stateVar fp = withManager $ \mgr -> do
  _ <- watchTree mgr fp
    (\ev -> takeFileName (eventPath ev) == "externs.json")
    (reloadFile stateVar . eventPath)
  forever (threadDelay 10000)