From b20d44c618f370a1998c70dd5708d9bbe4ed1c80 Mon Sep 17 00:00:00 2001 From: Egor Tensin Date: Sun, 26 Mar 2017 19:03:03 +0300 Subject: rename directories --- app/AddPath.hs | 83 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 83 insertions(+) create mode 100644 app/AddPath.hs (limited to 'app/AddPath.hs') diff --git a/app/AddPath.hs b/app/AddPath.hs new file mode 100644 index 0000000..683b82f --- /dev/null +++ b/app/AddPath.hs @@ -0,0 +1,83 @@ +-- | +-- Copyright : (c) 2015 Egor Tensin +-- License : MIT +-- Maintainer : Egor.Tensin@gmail.com +-- Stability : experimental +-- Portability : Windows-only + +module Main (main) where + +import Control.Monad (void, when) +import Control.Monad.Trans.Except (catchE, runExceptT, throwE) +import Data.List (union) +import System.IO.Error (ioError, isDoesNotExistError) + +import Options.Applicative + +import qualified WindowsEnv + +import Utils.Prompt +import Utils.PromptMessage + +data Options = Options + { optName :: WindowsEnv.VarName + , optYes :: Bool + , optGlobal :: Bool + , optPaths :: [WindowsEnv.VarValue] + } deriving (Eq, Show) + +optionParser :: Parser Options +optionParser = Options + <$> optNameDesc + <*> optYesDesc + <*> optGlobalDesc + <*> optPathsDesc + where + optNameDesc = strOption + $ long "name" <> short 'n' + <> metavar "NAME" <> value "PATH" + <> help "Variable name ('PATH' by default)" + optYesDesc = switch + $ long "yes" <> short 'y' + <> help "Skip confirmation prompt" + optGlobalDesc = switch + $ long "global" <> short 'g' + <> help "Add for all users" + optPathsDesc = many $ argument str + $ metavar "PATH" + <> help "Directories to add" + +main :: IO () +main = execParser parser >>= addPath + where + parser = info (helper <*> optionParser) $ + fullDesc <> progDesc "Add directories to your PATH" + +addPath :: Options -> IO () +addPath options = runExceptT doAddPath >>= either ioError return + where + varName = optName options + pathsToAdd = optPaths options + + forAllUsers = optGlobal options + profile + | forAllUsers = WindowsEnv.AllUsers + | otherwise = WindowsEnv.CurrentUser + + skipPrompt = optYes options + + emptyIfMissing e + | isDoesNotExistError e = return "" + | otherwise = throwE e + + doAddPath = do + oldValue <- WindowsEnv.query profile varName `catchE` emptyIfMissing + let oldPaths = WindowsEnv.pathSplit oldValue + let newPaths = oldPaths `union` pathsToAdd + when (length oldPaths /= length newPaths) $ do + let newValue = WindowsEnv.pathJoin newPaths + let promptAnd = if skipPrompt + then withoutPrompt + else withPrompt $ oldNewMessage profile varName oldValue newValue + let engrave = WindowsEnv.engrave profile varName newValue + void $ promptAnd engrave -- cgit v1.2.3