module Hoyo.Command (
runCommand
, modifyBookmarks
, modifyBookmarksM
, runAdd
, runMove
, runList
, runClear
, runDelete
, runRefresh
, runConfig
, runCheck
, runDefaultCommand
, Options (..)
, Command (..)
, AddOptions (..)
, MoveOptions (..)
, ListOptions (..)
, ClearOptions (..)
, DeleteOptions (..)
, RefreshOptions (..)
, ConfigPrintOptions (..)
, ConfigResetOptions (..)
, ConfigSetOptions (..)
, ConfigAddDefaultOptions (..)
, ConfigCommand (..)
, CheckOptions (..)
, HelpOptions (..)
, GlobalOptions (..)
, defaultGlobalOptions
, OverrideOptions (..)
, defaultOverrideOptions
, overrideConfig
, overrideEnv
, verifyOverrides
, combOverride
, MaybeOverride (..)
) where
import Control.Applicative
import Control.Exception (bracket_)
import Control.Monad
import Control.Monad.Except (throwError)
import Control.Monad.IO.Class
import Control.Monad.Reader.Class (ask)
import Data.Bifunctor
import Data.Char (isDigit)
import Data.Function
import Data.List
import qualified Data.Text as T
import Data.Time
import Hoyo.Bookmark
import {-# SOURCE #-} Hoyo.CLI.Parse
import Hoyo.Config
import Hoyo.Internal.Types
import Hoyo.Utils
import Lens.Micro
import Lens.Micro.Extras
import System.Console.ANSI hiding (Reset)
import System.Directory
import System.Exit
import System.IO
import Text.JSON
combOverride :: Bool -> Bool -> MaybeOverride
combOverride :: Bool -> Bool -> MaybeOverride
combOverride Bool
False Bool
False = MaybeOverride
NoOverride
combOverride Bool
True Bool
False = MaybeOverride
OverrideTrue
combOverride Bool
False Bool
True = MaybeOverride
OverrideFalse
combOverride Bool
True Bool
True = MaybeOverride
Conflict
overrideFunc :: MaybeOverride -> (Bool -> Bool)
overrideFunc :: MaybeOverride -> Bool -> Bool
overrideFunc MaybeOverride
NoOverride = Bool -> Bool
forall a. a -> a
id
overrideFunc MaybeOverride
OverrideTrue = Bool -> Bool -> Bool
forall a b. a -> b -> a
const Bool
True
overrideFunc MaybeOverride
OverrideFalse = Bool -> Bool -> Bool
forall a b. a -> b -> a
const Bool
False
overrideFunc MaybeOverride
Conflict = [Char] -> Bool -> Bool
forall a. HasCallStack => [Char] -> a
error [Char]
"override conflict!"
overrideConfig :: OverrideOptions -> Config -> Config
overrideConfig :: OverrideOptions -> Config -> Config
overrideConfig OverrideOptions
opts =
ASetter Config Config Bool Bool
-> (Bool -> Bool) -> Config -> Config
forall s t a b. ASetter s t a b -> (a -> b) -> s -> t
over ASetter Config Config Bool Bool
Lens' Config Bool
failOnError (MaybeOverride -> Bool -> Bool
overrideFunc (MaybeOverride -> Bool -> Bool) -> MaybeOverride -> Bool -> Bool
forall a b. (a -> b) -> a -> b
$ OverrideOptions -> MaybeOverride
overrideFailOnError OverrideOptions
opts)
(Config -> Config) -> (Config -> Config) -> Config -> Config
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ASetter Config Config Bool Bool
-> (Bool -> Bool) -> Config -> Config
forall s t a b. ASetter s t a b -> (a -> b) -> s -> t
over ASetter Config Config Bool Bool
Lens' Config Bool
displayCreationTime (MaybeOverride -> Bool -> Bool
overrideFunc (MaybeOverride -> Bool -> Bool) -> MaybeOverride -> Bool -> Bool
forall a b. (a -> b) -> a -> b
$ OverrideOptions -> MaybeOverride
overrideDisplayCreationTime OverrideOptions
opts)
(Config -> Config) -> (Config -> Config) -> Config -> Config
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ASetter Config Config Bool Bool
-> (Bool -> Bool) -> Config -> Config
forall s t a b. ASetter s t a b -> (a -> b) -> s -> t
over ASetter Config Config Bool Bool
Lens' Config Bool
enableClearing (MaybeOverride -> Bool -> Bool
overrideFunc (MaybeOverride -> Bool -> Bool) -> MaybeOverride -> Bool -> Bool
forall a b. (a -> b) -> a -> b
$ OverrideOptions -> MaybeOverride
overrideEnableClearing OverrideOptions
opts)
(Config -> Config) -> (Config -> Config) -> Config -> Config
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ASetter Config Config Bool Bool
-> (Bool -> Bool) -> Config -> Config
forall s t a b. ASetter s t a b -> (a -> b) -> s -> t
over ASetter Config Config Bool Bool
Lens' Config Bool
enableReset (MaybeOverride -> Bool -> Bool
overrideFunc (MaybeOverride -> Bool -> Bool) -> MaybeOverride -> Bool -> Bool
forall a b. (a -> b) -> a -> b
$ OverrideOptions -> MaybeOverride
overrideEnableReset OverrideOptions
opts)
(Config -> Config) -> (Config -> Config) -> Config -> Config
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ASetter Config Config Bool Bool
-> (Bool -> Bool) -> Config -> Config
forall s t a b. ASetter s t a b -> (a -> b) -> s -> t
over ASetter Config Config Bool Bool
Lens' Config Bool
backupBeforeClear (MaybeOverride -> Bool -> Bool
overrideFunc (MaybeOverride -> Bool -> Bool) -> MaybeOverride -> Bool -> Bool
forall a b. (a -> b) -> a -> b
$ OverrideOptions -> MaybeOverride
overrideBackupBeforeClear OverrideOptions
opts)
overrideEnv :: OverrideOptions -> Env -> Env
overrideEnv :: OverrideOptions -> Env -> Env
overrideEnv = ASetter Env Env Config Config -> (Config -> Config) -> Env -> Env
forall s t a b. ASetter s t a b -> (a -> b) -> s -> t
over ASetter Env Env Config Config
Lens' Env Config
config ((Config -> Config) -> Env -> Env)
-> (OverrideOptions -> Config -> Config)
-> OverrideOptions
-> Env
-> Env
forall b c a. (b -> c) -> (a -> b) -> a -> c
. OverrideOptions -> Config -> Config
overrideConfig
verifyOverrides :: OverrideOptions -> Maybe T.Text
verifyOverrides :: OverrideOptions -> Maybe Text
verifyOverrides (OverrideOptions MaybeOverride
o1 MaybeOverride
o2 MaybeOverride
o3 MaybeOverride
o4 MaybeOverride
o5) = MaybeOverride -> Maybe Text
forall a. IsString a => MaybeOverride -> Maybe a
verify MaybeOverride
o1
Maybe Text -> Maybe Text -> Maybe Text
forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> MaybeOverride -> Maybe Text
forall a. IsString a => MaybeOverride -> Maybe a
verify MaybeOverride
o2
Maybe Text -> Maybe Text -> Maybe Text
forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> MaybeOverride -> Maybe Text
forall a. IsString a => MaybeOverride -> Maybe a
verify MaybeOverride
o3
Maybe Text -> Maybe Text -> Maybe Text
forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> MaybeOverride -> Maybe Text
forall a. IsString a => MaybeOverride -> Maybe a
verify MaybeOverride
o4
Maybe Text -> Maybe Text -> Maybe Text
forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> MaybeOverride -> Maybe Text
forall a. IsString a => MaybeOverride -> Maybe a
verify MaybeOverride
o5
where verify :: MaybeOverride -> Maybe a
verify MaybeOverride
Conflict = a -> Maybe a
forall a. a -> Maybe a
Just a
"conflicting flags"
verify MaybeOverride
_ = Maybe a
forall a. Maybe a
Nothing
defaultOverrideOptions :: OverrideOptions
defaultOverrideOptions :: OverrideOptions
defaultOverrideOptions = MaybeOverride
-> MaybeOverride
-> MaybeOverride
-> MaybeOverride
-> MaybeOverride
-> OverrideOptions
OverrideOptions MaybeOverride
NoOverride
MaybeOverride
NoOverride
MaybeOverride
NoOverride
MaybeOverride
NoOverride
MaybeOverride
NoOverride
defaultGlobalOptions :: GlobalOptions
defaultGlobalOptions :: GlobalOptions
defaultGlobalOptions = Maybe [Char] -> Maybe [Char] -> OverrideOptions -> GlobalOptions
GlobalOptions Maybe [Char]
forall a. Maybe a
Nothing Maybe [Char]
forall a. Maybe a
Nothing OverrideOptions
defaultOverrideOptions
modifyBookmarks :: ([Bookmark] -> [Bookmark]) -> HoyoMonad ()
modifyBookmarks :: ([Bookmark] -> [Bookmark]) -> HoyoMonad ()
modifyBookmarks [Bookmark] -> [Bookmark]
f = ([Bookmark] -> HoyoMonad [Bookmark]) -> HoyoMonad ()
modifyBookmarksM ([Bookmark] -> HoyoMonad [Bookmark]
forall (m :: * -> *) a. Monad m => a -> m a
return ([Bookmark] -> HoyoMonad [Bookmark])
-> ([Bookmark] -> [Bookmark]) -> [Bookmark] -> HoyoMonad [Bookmark]
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [Bookmark] -> [Bookmark]
f)
modifyBookmarksM :: ([Bookmark] -> HoyoMonad [Bookmark]) -> HoyoMonad ()
modifyBookmarksM :: ([Bookmark] -> HoyoMonad [Bookmark]) -> HoyoMonad ()
modifyBookmarksM [Bookmark] -> HoyoMonad [Bookmark]
f = do
Env (Bookmarks [Bookmark]
bms) [Char]
bFp Config
_ [Char]
_ <- HoyoMonad Env
forall r (m :: * -> *). MonadReader r m => m r
ask
Bookmarks
newBookmarks <- [Bookmark] -> Bookmarks
Bookmarks ([Bookmark] -> Bookmarks)
-> HoyoMonad [Bookmark] -> HoyoMonad Bookmarks
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> [Bookmark] -> HoyoMonad [Bookmark]
f [Bookmark]
bms
[Char] -> Bookmarks -> HoyoMonad ()
forall (m :: * -> *). MonadIO m => [Char] -> Bookmarks -> m ()
encodeBookmarksFile [Char]
bFp Bookmarks
newBookmarks
normaliseAndVerifyDirectory :: FilePath -> HoyoMonad FilePath
normaliseAndVerifyDirectory :: [Char] -> HoyoMonad [Char]
normaliseAndVerifyDirectory [Char]
d = do
[Char]
dir <- IO [Char] -> HoyoMonad [Char]
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO [Char] -> HoyoMonad [Char]) -> IO [Char] -> HoyoMonad [Char]
forall a b. (a -> b) -> a -> b
$ [Char] -> IO [Char]
canonicalizePath [Char]
d
HoyoException -> HoyoMonad Bool -> HoyoMonad Bool
assertVerbose (FileSystemException -> HoyoException
FileSystemException (FileSystemException -> HoyoException)
-> FileSystemException -> HoyoException
forall a b. (a -> b) -> a -> b
$ [Char] -> FileSystemException
NoDirException [Char]
dir) (HoyoMonad Bool -> HoyoMonad Bool)
-> HoyoMonad Bool -> HoyoMonad Bool
forall a b. (a -> b) -> a -> b
$ IO Bool -> HoyoMonad Bool
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO Bool -> HoyoMonad Bool) -> IO Bool -> HoyoMonad Bool
forall a b. (a -> b) -> a -> b
$ [Char] -> IO Bool
doesDirectoryExist [Char]
dir
[Char] -> HoyoMonad [Char]
forall (m :: * -> *) a. Monad m => a -> m a
return [Char]
dir
verifyName :: T.Text -> HoyoMonad ()
verifyName :: Text -> HoyoMonad ()
verifyName Text
name = do
let nameStr :: [Char]
nameStr = Text -> [Char]
T.unpack Text
name
HoyoException -> HoyoMonad Bool -> HoyoMonad ()
assert (CommandException -> HoyoException
CommandException (CommandException -> HoyoException)
-> CommandException -> HoyoException
forall a b. (a -> b) -> a -> b
$ [Text] -> CommandException
InvalidArgumentException [Text
"bookmark name can't be empty"])
(HoyoMonad Bool -> HoyoMonad ()) -> HoyoMonad Bool -> HoyoMonad ()
forall a b. (a -> b) -> a -> b
$ Bool -> HoyoMonad Bool
forall (m :: * -> *) a. Monad m => a -> m a
return (Bool -> HoyoMonad Bool) -> Bool -> HoyoMonad Bool
forall a b. (a -> b) -> a -> b
$ Bool -> Bool
not (Bool -> Bool) -> Bool -> Bool
forall a b. (a -> b) -> a -> b
$ Text -> Bool
T.null Text
name
HoyoException -> HoyoMonad Bool -> HoyoMonad ()
assert (CommandException -> HoyoException
CommandException (CommandException -> HoyoException)
-> CommandException -> HoyoException
forall a b. (a -> b) -> a -> b
$ [Text] -> CommandException
InvalidArgumentException [Text
"bookmark name can't be a number"])
(HoyoMonad Bool -> HoyoMonad ()) -> HoyoMonad Bool -> HoyoMonad ()
forall a b. (a -> b) -> a -> b
$ Bool -> HoyoMonad Bool
forall (m :: * -> *) a. Monad m => a -> m a
return (Bool -> HoyoMonad Bool) -> Bool -> HoyoMonad Bool
forall a b. (a -> b) -> a -> b
$ Bool -> Bool
not (Bool -> Bool) -> Bool -> Bool
forall a b. (a -> b) -> a -> b
$ (Char -> Bool) -> [Char] -> Bool
forall (t :: * -> *) a. Foldable t => (a -> Bool) -> t a -> Bool
all Char -> Bool
isDigit [Char]
nameStr
testNameUnique :: [Bookmark] -> T.Text -> HoyoMonad Bool
testNameUnique :: [Bookmark] -> Text -> HoyoMonad Bool
testNameUnique [Bookmark]
bms Text
name =
HoyoException -> HoyoMonad Bool -> HoyoMonad Bool
assertVerbose (CommandException -> HoyoException
CommandException (CommandException -> HoyoException)
-> CommandException -> HoyoException
forall a b. (a -> b) -> a -> b
$ [Text] -> CommandException
InvalidArgumentException [Text
"bookmark name already used"])
(HoyoMonad Bool -> HoyoMonad Bool)
-> HoyoMonad Bool -> HoyoMonad Bool
forall a b. (a -> b) -> a -> b
$ Bool -> HoyoMonad Bool
forall (m :: * -> *) a. Monad m => a -> m a
return (Bool -> HoyoMonad Bool) -> Bool -> HoyoMonad Bool
forall a b. (a -> b) -> a -> b
$ (Bookmark -> Bool) -> [Bookmark] -> Bool
forall (t :: * -> *) a. Foldable t => (a -> Bool) -> t a -> Bool
all ((Maybe Text -> Maybe Text -> Bool
forall a. Eq a => a -> a -> Bool
/= Text -> Maybe Text
forall a. a -> Maybe a
Just Text
name) (Maybe Text -> Bool)
-> (Bookmark -> Maybe Text) -> Bookmark -> Bool
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Getting (Maybe Text) Bookmark (Maybe Text)
-> Bookmark -> Maybe Text
forall a s. Getting a s a -> s -> a
view Getting (Maybe Text) Bookmark (Maybe Text)
Lens' Bookmark (Maybe Text)
bookmarkName) [Bookmark]
bms
runAdd :: AddOptions -> HoyoMonad ()
runAdd :: AddOptions -> HoyoMonad ()
runAdd AddOptions
opts = do
[Char]
dir <- [Char] -> HoyoMonad [Char]
normaliseAndVerifyDirectory ([Char] -> HoyoMonad [Char]) -> [Char] -> HoyoMonad [Char]
forall a b. (a -> b) -> a -> b
$ AddOptions -> [Char]
addDirectory AddOptions
opts
let name :: Maybe Text
name = AddOptions -> Maybe Text
addName AddOptions
opts
([Bookmark] -> HoyoMonad [Bookmark]) -> HoyoMonad ()
modifyBookmarksM (([Bookmark] -> HoyoMonad [Bookmark]) -> HoyoMonad ())
-> ([Bookmark] -> HoyoMonad [Bookmark]) -> HoyoMonad ()
forall a b. (a -> b) -> a -> b
$ \[Bookmark]
bms -> do
Bool
uniqName <- case Maybe Text
name of Maybe Text
Nothing -> Bool -> HoyoMonad Bool
forall (m :: * -> *) a. Monad m => a -> m a
return Bool
True
Just Text
n -> Text -> HoyoMonad ()
verifyName Text
n HoyoMonad () -> HoyoMonad Bool -> HoyoMonad Bool
forall (m :: * -> *) a b. Monad m => m a -> m b -> m b
>> [Bookmark] -> Text -> HoyoMonad Bool
testNameUnique [Bookmark]
bms Text
n
if Bool
uniqName
then do
let maxIndex :: Int
maxIndex = Int -> [Int] -> Int
forall a. Ord a => a -> [a] -> a
maximumDefault Int
0 ([Int] -> Int) -> [Int] -> Int
forall a b. (a -> b) -> a -> b
$ (Bookmark -> Int) -> [Bookmark] -> [Int]
forall a b. (a -> b) -> [a] -> [b]
map (Getting Int Bookmark Int -> Bookmark -> Int
forall a s. Getting a s a -> s -> a
view Getting Int Bookmark Int
Lens' Bookmark Int
bookmarkIndex) [Bookmark]
bms
ZonedTime
zTime <- IO ZonedTime -> HoyoMonad ZonedTime
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO IO ZonedTime
getZonedTime
let newBookMark :: Bookmark
newBookMark = [Char] -> Int -> ZonedTime -> Maybe Text -> Bookmark
Bookmark [Char]
dir (Int
maxIndex Int -> Int -> Int
forall a. Num a => a -> a -> a
+ Int
1) ZonedTime
zTime Maybe Text
name
[Bookmark] -> HoyoMonad [Bookmark]
forall (m :: * -> *) a. Monad m => a -> m a
return (Bookmark
newBookMark Bookmark -> [Bookmark] -> [Bookmark]
forall a. a -> [a] -> [a]
: [Bookmark]
bms)
else [Bookmark] -> HoyoMonad [Bookmark]
forall (m :: * -> *) a. Monad m => a -> m a
return [Bookmark]
bms
runMove :: MoveOptions -> HoyoMonad ()
runMove :: MoveOptions -> HoyoMonad ()
runMove MoveOptions
opts = do
Bookmarks
bms <- SimpleGetter Env Bookmarks -> HoyoMonad Bookmarks
forall a (m :: * -> *) b.
MonadReader a m =>
SimpleGetter a b -> m b
asks' SimpleGetter Env Bookmarks
Lens' Env Bookmarks
bookmarks
let search :: BookmarkSearchTerm
search = MoveOptions -> BookmarkSearchTerm
moveSearch MoveOptions
opts
case ([Bookmark], [Bookmark]) -> [Bookmark]
forall a b. (a, b) -> a
fst (([Bookmark], [Bookmark]) -> [Bookmark])
-> ([Bookmark], [Bookmark]) -> [Bookmark]
forall a b. (a -> b) -> a -> b
$ BookmarkSearchTerm -> Bookmarks -> ([Bookmark], [Bookmark])
searchBookmarks BookmarkSearchTerm
search Bookmarks
bms of
[] -> HoyoException -> HoyoMonad ()
forall e (m :: * -> *) a. MonadError e m => e -> m a
throwError (HoyoException -> HoyoMonad ()) -> HoyoException -> HoyoMonad ()
forall a b. (a -> b) -> a -> b
$ CommandException -> HoyoException
CommandException (CommandException -> HoyoException)
-> CommandException -> HoyoException
forall a b. (a -> b) -> a -> b
$ SearchException -> CommandException
SearchException (SearchException -> CommandException)
-> SearchException -> CommandException
forall a b. (a -> b) -> a -> b
$ BookmarkSearchTerm -> SearchException
NothingFound BookmarkSearchTerm
search
[Bookmark
bm] -> do Text -> HoyoMonad ()
forall (m :: * -> *). MonadIO m => Text -> m ()
printStdout (Text
"cd " Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> [Char] -> Text
T.pack (Getting [Char] Bookmark [Char] -> Bookmark -> [Char]
forall a s. Getting a s a -> s -> a
view Getting [Char] Bookmark [Char]
Lens' Bookmark [Char]
bookmarkDirectory Bookmark
bm))
IO () -> HoyoMonad ()
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO () -> HoyoMonad ()) -> IO () -> HoyoMonad ()
forall a b. (a -> b) -> a -> b
$ ExitCode -> IO ()
forall a. ExitCode -> IO a
exitWith (Int -> ExitCode
ExitFailure Int
3)
[Bookmark]
ms -> do Bool
displayTime <- SimpleGetter Env Bool -> HoyoMonad Bool
forall a (m :: * -> *) b.
MonadReader a m =>
SimpleGetter a b -> m b
asks' ((Config -> Const r Config) -> Env -> Const r Env
Lens' Env Config
config ((Config -> Const r Config) -> Env -> Const r Env)
-> ((Bool -> Const r Bool) -> Config -> Const r Config)
-> (Bool -> Const r Bool)
-> Env
-> Const r Env
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Bool -> Const r Bool) -> Config -> Const r Config
Lens' Config Bool
displayCreationTime)
let strs :: [Text]
strs = Bool -> [Bookmark] -> [Text]
formatBookmarks Bool
displayTime ([Bookmark] -> [Text]) -> [Bookmark] -> [Text]
forall a b. (a -> b) -> a -> b
$ (Bookmark -> Int) -> [Bookmark] -> [Bookmark]
forall b a. Ord b => (a -> b) -> [a] -> [a]
sortOn (Getting Int Bookmark Int -> Bookmark -> Int
forall a s. Getting a s a -> s -> a
view Getting Int Bookmark Int
Lens' Bookmark Int
bookmarkIndex) [Bookmark]
ms
HoyoException -> HoyoMonad ()
forall e (m :: * -> *) a. MonadError e m => e -> m a
throwError (HoyoException -> HoyoMonad ()) -> HoyoException -> HoyoMonad ()
forall a b. (a -> b) -> a -> b
$ CommandException -> HoyoException
CommandException (CommandException -> HoyoException)
-> CommandException -> HoyoException
forall a b. (a -> b) -> a -> b
$ SearchException -> CommandException
SearchException (SearchException -> CommandException)
-> SearchException -> CommandException
forall a b. (a -> b) -> a -> b
$ BookmarkSearchTerm -> [Text] -> SearchException
TooManyResults BookmarkSearchTerm
search [Text]
strs
runList :: ListOptions -> HoyoMonad ()
runList :: ListOptions -> HoyoMonad ()
runList ListOptions
opts = do
let filt :: Bookmark -> Bool
filt = Maybe Text -> Maybe Text -> Bookmark -> Bool
filterBookmarks (ListOptions -> Maybe Text
listFilterName ListOptions
opts) (ListOptions -> Maybe Text
listFilterDirectoryInfix ListOptions
opts)
Bookmarks
bms' <- SimpleGetter Env Bookmarks -> HoyoMonad Bookmarks
forall a (m :: * -> *) b.
MonadReader a m =>
SimpleGetter a b -> m b
asks' SimpleGetter Env Bookmarks
Lens' Env Bookmarks
bookmarks
let bms :: [Bookmark]
bms = (Bookmark -> Bool) -> [Bookmark] -> [Bookmark]
forall a. (a -> Bool) -> [a] -> [a]
filter Bookmark -> Bool
filt ([Bookmark] -> [Bookmark]) -> [Bookmark] -> [Bookmark]
forall a b. (a -> b) -> a -> b
$ (Bookmark -> Int) -> [Bookmark] -> [Bookmark]
forall b a. Ord b => (a -> b) -> [a] -> [a]
sortOn (Getting Int Bookmark Int -> Bookmark -> Int
forall a s. Getting a s a -> s -> a
view Getting Int Bookmark Int
Lens' Bookmark Int
bookmarkIndex) ([Bookmark] -> [Bookmark]) -> [Bookmark] -> [Bookmark]
forall a b. (a -> b) -> a -> b
$ Bookmarks -> [Bookmark]
unBookmarks Bookmarks
bms'
Bool
displayTime <- SimpleGetter Env Bool -> HoyoMonad Bool
forall a (m :: * -> *) b.
MonadReader a m =>
SimpleGetter a b -> m b
asks' ((Config -> Const r Config) -> Env -> Const r Env
Lens' Env Config
config ((Config -> Const r Config) -> Env -> Const r Env)
-> ((Bool -> Const r Bool) -> Config -> Const r Config)
-> (Bool -> Const r Bool)
-> Env
-> Const r Env
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Bool -> Const r Bool) -> Config -> Const r Config
Lens' Config Bool
displayCreationTime)
if ListOptions -> Bool
listJSONOutput ListOptions
opts
then do
let jsonObj :: JSValue
jsonObj = Bool -> [Bookmark] -> JSValue
bookmarksToJSON Bool
displayTime [Bookmark]
bms
Text -> HoyoMonad ()
forall (m :: * -> *). MonadIO m => Text -> m ()
printStdout (Text -> HoyoMonad ()) -> Text -> HoyoMonad ()
forall a b. (a -> b) -> a -> b
$ [Char] -> Text
T.pack ([Char] -> Text) -> [Char] -> Text
forall a b. (a -> b) -> a -> b
$ JSValue -> [Char]
forall a. JSON a => a -> [Char]
encode JSValue
jsonObj
else [Text] -> HoyoMonad ()
forall (m :: * -> *). MonadIO m => [Text] -> m ()
pageLines (Bool -> [Bookmark] -> [Text]
formatBookmarks Bool
displayTime [Bookmark]
bms)
clearDisabledErr :: HoyoException
clearDisabledErr :: HoyoException
clearDisabledErr = [Text] -> HoyoException
ConfigException [
Text
"The 'clear' command is disabled by default."
, Text
"To enable, set enable_clear = true in the config or pass the --enable-clear flag."
]
resetDisabledErr :: HoyoException
resetDisabledErr :: HoyoException
resetDisabledErr = [Text] -> HoyoException
ConfigException [
Text
"The 'config reset' command is disabled by default."
, Text
"To enable, set enable_reset = true in the config or pass the --enable-reset flag."
]
getConfirmation :: String -> IO Bool
getConfirmation :: [Char] -> IO Bool
getConfirmation [Char]
s = IO () -> IO () -> IO Bool -> IO Bool
forall a b c. IO a -> IO b -> IO c -> IO c
bracket_ IO ()
makeRed IO ()
resetColour IO Bool
getConfirmation'
where
makeRed :: IO ()
makeRed = Handle -> [SGR] -> IO ()
hSetSGR Handle
stdout [ConsoleLayer -> ColorIntensity -> Color -> SGR
SetColor ConsoleLayer
Foreground ColorIntensity
Vivid Color
Red]
resetColour :: IO ()
resetColour = Handle -> [SGR] -> IO ()
hSetSGR Handle
stdout [] IO () -> IO () -> IO ()
forall (m :: * -> *) a b. Monad m => m a -> m b -> m b
>> [Char] -> IO ()
putStrLn [Char]
"\n"
getConfirmation' :: IO Bool
getConfirmation' = do
[Char] -> IO ()
putStr ([Char] -> IO ()) -> [Char] -> IO ()
forall a b. (a -> b) -> a -> b
$ [Char]
s [Char] -> [Char] -> [Char]
forall a. Semigroup a => a -> a -> a
<> [Char]
" (y/n): "
Handle -> IO ()
hFlush Handle
stdout
[Char]
inp <- IO [Char]
getLine
case [Char]
inp of
[Char]
"y" -> Bool -> IO Bool
forall (m :: * -> *) a. Monad m => a -> m a
return Bool
True
[Char]
"Y" -> Bool -> IO Bool
forall (m :: * -> *) a. Monad m => a -> m a
return Bool
True
[Char]
"n" -> Bool -> IO Bool
forall (m :: * -> *) a. Monad m => a -> m a
return Bool
False
[Char]
"N" -> Bool -> IO Bool
forall (m :: * -> *) a. Monad m => a -> m a
return Bool
False
[Char]
_ -> IO Bool
getConfirmation'
runClear :: ClearOptions -> HoyoMonad ()
runClear :: ClearOptions -> HoyoMonad ()
runClear ClearOptions
_ = do
HoyoException -> HoyoMonad Bool -> HoyoMonad ()
assert HoyoException
clearDisabledErr (SimpleGetter Env Bool -> HoyoMonad Bool
forall a (m :: * -> *) b.
MonadReader a m =>
SimpleGetter a b -> m b
asks' ((Config -> Const r Config) -> Env -> Const r Env
Lens' Env Config
config ((Config -> Const r Config) -> Env -> Const r Env)
-> ((Bool -> Const r Bool) -> Config -> Const r Config)
-> (Bool -> Const r Bool)
-> Env
-> Const r Env
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Bool -> Const r Bool) -> Config -> Const r Config
Lens' Config Bool
enableClearing))
[Char]
path <- SimpleGetter Env [Char] -> HoyoMonad [Char]
forall a (m :: * -> *) b.
MonadReader a m =>
SimpleGetter a b -> m b
asks' SimpleGetter Env [Char]
Lens' Env [Char]
bookmarksPath
Bool
backup <- SimpleGetter Env Bool -> HoyoMonad Bool
forall a (m :: * -> *) b.
MonadReader a m =>
SimpleGetter a b -> m b
asks' ((Config -> Const r Config) -> Env -> Const r Env
Lens' Env Config
config ((Config -> Const r Config) -> Env -> Const r Env)
-> ((Bool -> Const r Bool) -> Config -> Const r Config)
-> (Bool -> Const r Bool)
-> Env
-> Const r Env
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Bool -> Const r Bool) -> Config -> Const r Config
Lens' Config Bool
backupBeforeClear)
Bool -> HoyoMonad () -> HoyoMonad ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when Bool
backup (HoyoMonad () -> HoyoMonad ()) -> HoyoMonad () -> HoyoMonad ()
forall a b. (a -> b) -> a -> b
$ [Char] -> [Char] -> HoyoMonad ()
forall (m :: * -> *).
(MonadIO m, MonadError HoyoException m) =>
[Char] -> [Char] -> m ()
backupFile [Char]
path [Char]
"bkp"
Bool
isTTY <- IO Bool -> HoyoMonad Bool
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO Bool -> HoyoMonad Bool) -> IO Bool -> HoyoMonad Bool
forall a b. (a -> b) -> a -> b
$ Handle -> IO Bool
hIsTerminalDevice Handle
stdin
if Bool
backup Bool -> Bool -> Bool
|| Bool -> Bool
not Bool
isTTY
then HoyoMonad ()
runClear'
else do
Bool
yes <- IO Bool -> HoyoMonad Bool
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO Bool -> HoyoMonad Bool) -> IO Bool -> HoyoMonad Bool
forall a b. (a -> b) -> a -> b
$ [Char] -> IO Bool
getConfirmation [Char]
"Are you sure you want to delete all your saved backups?"
Bool -> HoyoMonad () -> HoyoMonad ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when Bool
yes HoyoMonad ()
runClear'
where
runClear' :: HoyoMonad ()
runClear' = do
([Bookmark] -> [Bookmark]) -> HoyoMonad ()
modifyBookmarks (([Bookmark] -> [Bookmark]) -> HoyoMonad ())
-> ([Bookmark] -> [Bookmark]) -> HoyoMonad ()
forall a b. (a -> b) -> a -> b
$ [Bookmark] -> [Bookmark] -> [Bookmark]
forall a b. a -> b -> a
const []
Bookmarks
bms <- SimpleGetter Env [DefaultBookmark] -> HoyoMonad [DefaultBookmark]
forall a (m :: * -> *) b.
MonadReader a m =>
SimpleGetter a b -> m b
asks' ((Config -> Const r Config) -> Env -> Const r Env
Lens' Env Config
config ((Config -> Const r Config) -> Env -> Const r Env)
-> (([DefaultBookmark] -> Const r [DefaultBookmark])
-> Config -> Const r Config)
-> ([DefaultBookmark] -> Const r [DefaultBookmark])
-> Env
-> Const r Env
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ([DefaultBookmark] -> Const r [DefaultBookmark])
-> Config -> Const r Config
Lens' Config [DefaultBookmark]
defaultBookmarks) HoyoMonad [DefaultBookmark]
-> ([DefaultBookmark] -> HoyoMonad Bookmarks)
-> HoyoMonad Bookmarks
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= [DefaultBookmark] -> HoyoMonad Bookmarks
forall (m :: * -> *). MonadIO m => [DefaultBookmark] -> m Bookmarks
bookmarksFromDefault
[Char]
fp <- SimpleGetter Env [Char] -> HoyoMonad [Char]
forall a (m :: * -> *) b.
MonadReader a m =>
SimpleGetter a b -> m b
asks' SimpleGetter Env [Char]
Lens' Env [Char]
bookmarksPath
[Char] -> Bookmarks -> HoyoMonad ()
forall (m :: * -> *). MonadIO m => [Char] -> Bookmarks -> m ()
encodeBookmarksFile [Char]
fp Bookmarks
bms
runDelete :: DeleteOptions -> HoyoMonad ()
runDelete :: DeleteOptions -> HoyoMonad ()
runDelete DeleteOptions
opts = do
let search :: BookmarkSearchTerm
search = DeleteOptions -> BookmarkSearchTerm
deleteSearch DeleteOptions
opts
([Bookmark] -> HoyoMonad [Bookmark]) -> HoyoMonad ()
modifyBookmarksM (([Bookmark] -> HoyoMonad [Bookmark]) -> HoyoMonad ())
-> ([Bookmark] -> HoyoMonad [Bookmark]) -> HoyoMonad ()
forall a b. (a -> b) -> a -> b
$ \[Bookmark]
bms -> do
let ([Bookmark]
searchResults, [Bookmark]
afterDelete) = BookmarkSearchTerm -> Bookmarks -> ([Bookmark], [Bookmark])
searchBookmarks BookmarkSearchTerm
search ([Bookmark] -> Bookmarks
Bookmarks [Bookmark]
bms)
HoyoException -> HoyoMonad Bool -> HoyoMonad Bool
assertVerbose (CommandException -> HoyoException
CommandException (CommandException -> HoyoException)
-> CommandException -> HoyoException
forall a b. (a -> b) -> a -> b
$ SearchException -> CommandException
SearchException (SearchException -> CommandException)
-> SearchException -> CommandException
forall a b. (a -> b) -> a -> b
$ BookmarkSearchTerm -> SearchException
NothingFound BookmarkSearchTerm
search)
(HoyoMonad Bool -> HoyoMonad Bool)
-> HoyoMonad Bool -> HoyoMonad Bool
forall a b. (a -> b) -> a -> b
$ Bool -> HoyoMonad Bool
forall (m :: * -> *) a. Monad m => a -> m a
return (Bool -> HoyoMonad Bool) -> Bool -> HoyoMonad Bool
forall a b. (a -> b) -> a -> b
$ Bool -> Bool
not (Bool -> Bool) -> Bool -> Bool
forall a b. (a -> b) -> a -> b
$ [Bookmark] -> Bool
forall (t :: * -> *) a. Foldable t => t a -> Bool
null [Bookmark]
searchResults
Bool
displayTime <- SimpleGetter Env Bool -> HoyoMonad Bool
forall a (m :: * -> *) b.
MonadReader a m =>
SimpleGetter a b -> m b
asks' ((Config -> Const r Config) -> Env -> Const r Env
Lens' Env Config
config ((Config -> Const r Config) -> Env -> Const r Env)
-> ((Bool -> Const r Bool) -> Config -> Const r Config)
-> (Bool -> Const r Bool)
-> Env
-> Const r Env
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Bool -> Const r Bool) -> Config -> Const r Config
Lens' Config Bool
displayCreationTime)
let strs :: [Text]
strs = Bool -> [Bookmark] -> [Text]
formatBookmarks Bool
displayTime ([Bookmark] -> [Text]) -> [Bookmark] -> [Text]
forall a b. (a -> b) -> a -> b
$ (Bookmark -> Int) -> [Bookmark] -> [Bookmark]
forall b a. Ord b => (a -> b) -> [a] -> [a]
sortOn (Getting Int Bookmark Int -> Bookmark -> Int
forall a s. Getting a s a -> s -> a
view Getting Int Bookmark Int
Lens' Bookmark Int
bookmarkIndex) [Bookmark]
searchResults
HoyoException -> HoyoMonad Bool -> HoyoMonad Bool
assertVerbose (CommandException -> HoyoException
CommandException (CommandException -> HoyoException)
-> CommandException -> HoyoException
forall a b. (a -> b) -> a -> b
$ SearchException -> CommandException
SearchException (SearchException -> CommandException)
-> SearchException -> CommandException
forall a b. (a -> b) -> a -> b
$ BookmarkSearchTerm -> [Text] -> SearchException
TooManyResults BookmarkSearchTerm
search [Text]
strs)
(HoyoMonad Bool -> HoyoMonad Bool)
-> HoyoMonad Bool -> HoyoMonad Bool
forall a b. (a -> b) -> a -> b
$ Bool -> HoyoMonad Bool
forall (m :: * -> *) a. Monad m => a -> m a
return (Bool -> HoyoMonad Bool) -> Bool -> HoyoMonad Bool
forall a b. (a -> b) -> a -> b
$ [Bookmark] -> Int
forall (t :: * -> *) a. Foldable t => t a -> Int
length [Bookmark]
searchResults Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
== Int
1
[Bookmark] -> HoyoMonad [Bookmark]
forall (m :: * -> *) a. Monad m => a -> m a
return [Bookmark]
afterDelete
runRefresh :: RefreshOptions -> HoyoMonad ()
runRefresh :: RefreshOptions -> HoyoMonad ()
runRefresh RefreshOptions
_ = ([Bookmark] -> [Bookmark]) -> HoyoMonad ()
modifyBookmarks (([Bookmark] -> [Bookmark]) -> HoyoMonad ())
-> ([Bookmark] -> [Bookmark]) -> HoyoMonad ()
forall a b. (a -> b) -> a -> b
$
(Int -> Bookmark -> Bookmark) -> [Int] -> [Bookmark] -> [Bookmark]
forall a b c. (a -> b -> c) -> [a] -> [b] -> [c]
zipWith (ASetter Bookmark Bookmark Int Int -> Int -> Bookmark -> Bookmark
forall s t a b. ASetter s t a b -> b -> s -> t
set ASetter Bookmark Bookmark Int Int
Lens' Bookmark Int
bookmarkIndex) [Int
1..]
([Bookmark] -> [Bookmark])
-> ([Bookmark] -> [Bookmark]) -> [Bookmark] -> [Bookmark]
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Bookmark -> Bookmark -> Bool) -> [Bookmark] -> [Bookmark]
forall a. (a -> a -> Bool) -> [a] -> [a]
nubBy ([Char] -> [Char] -> Bool
forall a. Eq a => a -> a -> Bool
(==) ([Char] -> [Char] -> Bool)
-> (Bookmark -> [Char]) -> Bookmark -> Bookmark -> Bool
forall b c a. (b -> b -> c) -> (a -> b) -> a -> a -> c
`on` Getting [Char] Bookmark [Char] -> Bookmark -> [Char]
forall a s. Getting a s a -> s -> a
view Getting [Char] Bookmark [Char]
Lens' Bookmark [Char]
bookmarkDirectory)
([Bookmark] -> [Bookmark])
-> ([Bookmark] -> [Bookmark]) -> [Bookmark] -> [Bookmark]
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Bookmark -> UTCTime) -> [Bookmark] -> [Bookmark]
forall b a. Ord b => (a -> b) -> [a] -> [a]
sortOn (ZonedTime -> UTCTime
zonedTimeToUTC (ZonedTime -> UTCTime)
-> (Bookmark -> ZonedTime) -> Bookmark -> UTCTime
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Getting ZonedTime Bookmark ZonedTime -> Bookmark -> ZonedTime
forall a s. Getting a s a -> s -> a
view Getting ZonedTime Bookmark ZonedTime
Lens' Bookmark ZonedTime
bookmarkCreationTime)
runConfigPrint :: ConfigPrintOptions -> HoyoMonad ()
runConfigPrint :: ConfigPrintOptions -> HoyoMonad ()
runConfigPrint ConfigPrintOptions
opts = do
Config
s <- SimpleGetter Env Config -> HoyoMonad Config
forall a (m :: * -> *) b.
MonadReader a m =>
SimpleGetter a b -> m b
asks' SimpleGetter Env Config
Lens' Env Config
config
let keyVals :: [(Text, AnyConfigValue)]
keyVals = Config -> [(Text, AnyConfigValue)]
getKeyVals Config
s
let keyWidth :: Int
keyWidth = [Int] -> Int
forall (t :: * -> *) a. (Foldable t, Ord a) => t a -> a
maximum ([Int] -> Int) -> [Int] -> Int
forall a b. (a -> b) -> a -> b
$ ((Text, AnyConfigValue) -> Int)
-> [(Text, AnyConfigValue)] -> [Int]
forall a b. (a -> b) -> [a] -> [b]
map (Text -> Int
T.length (Text -> Int)
-> ((Text, AnyConfigValue) -> Text)
-> (Text, AnyConfigValue)
-> Int
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Text, AnyConfigValue) -> Text
forall a b. (a, b) -> a
fst) [(Text, AnyConfigValue)]
keyVals
if ConfigPrintOptions -> Bool
configPrintJSONOuput ConfigPrintOptions
opts
then do
let jsonObj :: JSValue
jsonObj = JSObject JSValue -> JSValue
JSObject (JSObject JSValue -> JSValue) -> JSObject JSValue -> JSValue
forall a b. (a -> b) -> a -> b
$ [([Char], JSValue)] -> JSObject JSValue
forall a. [([Char], a)] -> JSObject a
toJSObject ([([Char], JSValue)] -> JSObject JSValue)
-> [([Char], JSValue)] -> JSObject JSValue
forall a b. (a -> b) -> a -> b
$ ((Text, AnyConfigValue) -> ([Char], JSValue))
-> [(Text, AnyConfigValue)] -> [([Char], JSValue)]
forall a b. (a -> b) -> [a] -> [b]
map ((Text -> [Char])
-> (AnyConfigValue -> JSValue)
-> (Text, AnyConfigValue)
-> ([Char], JSValue)
forall (p :: * -> * -> *) a b c d.
Bifunctor p =>
(a -> b) -> (c -> d) -> p a c -> p b d
bimap Text -> [Char]
T.unpack AnyConfigValue -> JSValue
anyCfgValToJson) [(Text, AnyConfigValue)]
keyVals
Text -> HoyoMonad ()
forall (m :: * -> *). MonadIO m => Text -> m ()
printStdout (Text -> HoyoMonad ()) -> Text -> HoyoMonad ()
forall a b. (a -> b) -> a -> b
$ [Char] -> Text
T.pack ([Char] -> Text) -> [Char] -> Text
forall a b. (a -> b) -> a -> b
$ JSValue -> [Char]
forall a. JSON a => a -> [Char]
encode JSValue
jsonObj
else do
let align :: Text -> Text
align = Int -> Char -> Text -> Text
T.justifyLeft Int
keyWidth Char
' '
let ls :: [Text]
ls = ((Text, AnyConfigValue) -> Text)
-> [(Text, AnyConfigValue)] -> [Text]
forall a b. (a -> b) -> [a] -> [b]
map (\(Text
k, AnyConfigValue
v) -> Text -> Text
align Text
k Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
" = " Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> AnyConfigValue -> Text
formatConfigValue AnyConfigValue
v) [(Text, AnyConfigValue)]
keyVals
[Text] -> HoyoMonad ()
forall (m :: * -> *). MonadIO m => [Text] -> m ()
pageLines [Text]
ls
runConfigReset :: ConfigResetOptions -> HoyoMonad ()
runConfigReset :: ConfigResetOptions -> HoyoMonad ()
runConfigReset ConfigResetOptions
_ = do
HoyoException -> HoyoMonad Bool -> HoyoMonad ()
assert HoyoException
resetDisabledErr (SimpleGetter Env Bool -> HoyoMonad Bool
forall a (m :: * -> *) b.
MonadReader a m =>
SimpleGetter a b -> m b
asks' ((Config -> Const r Config) -> Env -> Const r Env
Lens' Env Config
config ((Config -> Const r Config) -> Env -> Const r Env)
-> ((Bool -> Const r Bool) -> Config -> Const r Config)
-> (Bool -> Const r Bool)
-> Env
-> Const r Env
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Bool -> Const r Bool) -> Config -> Const r Config
Lens' Config Bool
enableReset))
[Char]
path <- SimpleGetter Env [Char] -> HoyoMonad [Char]
forall a (m :: * -> *) b.
MonadReader a m =>
SimpleGetter a b -> m b
asks' SimpleGetter Env [Char]
Lens' Env [Char]
configPath
Bool
backup <- SimpleGetter Env Bool -> HoyoMonad Bool
forall a (m :: * -> *) b.
MonadReader a m =>
SimpleGetter a b -> m b
asks' ((Config -> Const r Config) -> Env -> Const r Env
Lens' Env Config
config ((Config -> Const r Config) -> Env -> Const r Env)
-> ((Bool -> Const r Bool) -> Config -> Const r Config)
-> (Bool -> Const r Bool)
-> Env
-> Const r Env
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Bool -> Const r Bool) -> Config -> Const r Config
Lens' Config Bool
backupBeforeClear)
Bool -> HoyoMonad () -> HoyoMonad ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when Bool
backup (HoyoMonad () -> HoyoMonad ()) -> HoyoMonad () -> HoyoMonad ()
forall a b. (a -> b) -> a -> b
$ [Char] -> [Char] -> HoyoMonad ()
forall (m :: * -> *).
(MonadIO m, MonadError HoyoException m) =>
[Char] -> [Char] -> m ()
backupFile [Char]
path [Char]
"bkp"
Bool
isTTY <- IO Bool -> HoyoMonad Bool
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO Bool -> HoyoMonad Bool) -> IO Bool -> HoyoMonad Bool
forall a b. (a -> b) -> a -> b
$ Handle -> IO Bool
hIsTerminalDevice Handle
stdin
if Bool
backup Bool -> Bool -> Bool
|| Bool -> Bool
not Bool
isTTY
then HoyoMonad (Either HoyoException ()) -> HoyoMonad ()
forall (f :: * -> *) a. Functor f => f a -> f ()
void (HoyoMonad (Either HoyoException ()) -> HoyoMonad ())
-> HoyoMonad (Either HoyoException ()) -> HoyoMonad ()
forall a b. (a -> b) -> a -> b
$ [Char] -> Config -> HoyoMonad (Either HoyoException ())
forall (m :: * -> *).
(MonadIO m, MonadCatch m) =>
[Char] -> Config -> m (Either HoyoException ())
encodeConfigFile [Char]
path Config
defaultConfig
else do
Bool
yes <- IO Bool -> HoyoMonad Bool
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO Bool -> HoyoMonad Bool) -> IO Bool -> HoyoMonad Bool
forall a b. (a -> b) -> a -> b
$ [Char] -> IO Bool
getConfirmation [Char]
"Are you sure you want to clear your hoyo configuration?"
Bool -> HoyoMonad () -> HoyoMonad ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when Bool
yes (HoyoMonad () -> HoyoMonad ()) -> HoyoMonad () -> HoyoMonad ()
forall a b. (a -> b) -> a -> b
$ HoyoMonad (Either HoyoException ()) -> HoyoMonad ()
forall (f :: * -> *) a. Functor f => f a -> f ()
void (HoyoMonad (Either HoyoException ()) -> HoyoMonad ())
-> HoyoMonad (Either HoyoException ()) -> HoyoMonad ()
forall a b. (a -> b) -> a -> b
$ [Char] -> Config -> HoyoMonad (Either HoyoException ())
forall (m :: * -> *).
(MonadIO m, MonadCatch m) =>
[Char] -> Config -> m (Either HoyoException ())
encodeConfigFile [Char]
path Config
defaultConfig
runConfigSet :: ConfigSetOptions -> HoyoMonad ()
runConfigSet :: ConfigSetOptions -> HoyoMonad ()
runConfigSet ConfigSetOptions
opts = do
let key :: Text
key = ConfigSetOptions -> Text
setKey ConfigSetOptions
opts
let val :: Text
val = ConfigSetOptions -> Text
setValue ConfigSetOptions
opts
[Char]
cfgPath <- SimpleGetter Env [Char] -> HoyoMonad [Char]
forall a (m :: * -> *) b.
MonadReader a m =>
SimpleGetter a b -> m b
asks' SimpleGetter Env [Char]
Lens' Env [Char]
configPath
SimpleGetter Env Config -> HoyoMonad Config
forall a (m :: * -> *) b.
MonadReader a m =>
SimpleGetter a b -> m b
asks' SimpleGetter Env Config
Lens' Env Config
config
HoyoMonad Config
-> (Config -> HoyoMonad Config) -> HoyoMonad Config
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= Text -> Text -> Config -> HoyoMonad Config
forall (m :: * -> *).
MonadError HoyoException m =>
Text -> Text -> Config -> m Config
setConfig Text
key Text
val
HoyoMonad Config -> (Config -> HoyoMonad ()) -> HoyoMonad ()
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= HoyoMonad (Either HoyoException ()) -> HoyoMonad ()
forall (f :: * -> *) a. Functor f => f a -> f ()
void (HoyoMonad (Either HoyoException ()) -> HoyoMonad ())
-> (Config -> HoyoMonad (Either HoyoException ()))
-> Config
-> HoyoMonad ()
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [Char] -> Config -> HoyoMonad (Either HoyoException ())
forall (m :: * -> *).
(MonadIO m, MonadCatch m) =>
[Char] -> Config -> m (Either HoyoException ())
encodeConfigFile [Char]
cfgPath
runAddDefault :: ConfigAddDefaultOptions -> HoyoMonad ()
runAddDefault :: ConfigAddDefaultOptions -> HoyoMonad ()
runAddDefault ConfigAddDefaultOptions
opts = do
[Char]
dir <- [Char] -> HoyoMonad [Char]
normaliseAndVerifyDirectory ([Char] -> HoyoMonad [Char]) -> [Char] -> HoyoMonad [Char]
forall a b. (a -> b) -> a -> b
$ ConfigAddDefaultOptions -> [Char]
addDefaultDir ConfigAddDefaultOptions
opts
let name :: Maybe Text
name = ConfigAddDefaultOptions -> Maybe Text
addDefaultName ConfigAddDefaultOptions
opts
let defaultBm :: DefaultBookmark
defaultBm = [Char] -> Maybe Text -> DefaultBookmark
DefaultBookmark [Char]
dir Maybe Text
name
[Char]
cfgPath <- SimpleGetter Env [Char] -> HoyoMonad [Char]
forall a (m :: * -> *) b.
MonadReader a m =>
SimpleGetter a b -> m b
asks' SimpleGetter Env [Char]
Lens' Env [Char]
configPath
SimpleGetter Env Config -> HoyoMonad Config
forall a (m :: * -> *) b.
MonadReader a m =>
SimpleGetter a b -> m b
asks' SimpleGetter Env Config
Lens' Env Config
config
HoyoMonad Config -> (Config -> HoyoMonad ()) -> HoyoMonad ()
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= HoyoMonad (Either HoyoException ()) -> HoyoMonad ()
forall (f :: * -> *) a. Functor f => f a -> f ()
void (HoyoMonad (Either HoyoException ()) -> HoyoMonad ())
-> (Config -> HoyoMonad (Either HoyoException ()))
-> Config
-> HoyoMonad ()
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [Char] -> Config -> HoyoMonad (Either HoyoException ())
forall (m :: * -> *).
(MonadIO m, MonadCatch m) =>
[Char] -> Config -> m (Either HoyoException ())
encodeConfigFile [Char]
cfgPath (Config -> HoyoMonad (Either HoyoException ()))
-> (Config -> Config)
-> Config
-> HoyoMonad (Either HoyoException ())
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ASetter Config Config [DefaultBookmark] [DefaultBookmark]
-> ([DefaultBookmark] -> [DefaultBookmark]) -> Config -> Config
forall s t a b. ASetter s t a b -> (a -> b) -> s -> t
over ASetter Config Config [DefaultBookmark] [DefaultBookmark]
Lens' Config [DefaultBookmark]
defaultBookmarks (DefaultBookmark
defaultBm DefaultBookmark -> [DefaultBookmark] -> [DefaultBookmark]
forall a. a -> [a] -> [a]
:)
runConfig :: ConfigCommand -> HoyoMonad ()
runConfig :: ConfigCommand -> HoyoMonad ()
runConfig (Print ConfigPrintOptions
opts) = ConfigPrintOptions -> HoyoMonad ()
runConfigPrint ConfigPrintOptions
opts
runConfig (Reset ConfigResetOptions
opts) = ConfigResetOptions -> HoyoMonad ()
runConfigReset ConfigResetOptions
opts
runConfig (Set ConfigSetOptions
opts) = ConfigSetOptions -> HoyoMonad ()
runConfigSet ConfigSetOptions
opts
runConfig (AddDefaultBookmark ConfigAddDefaultOptions
opts) = ConfigAddDefaultOptions -> HoyoMonad ()
runAddDefault ConfigAddDefaultOptions
opts
runCheckConfig :: FilePath -> IO ()
runCheckConfig :: [Char] -> IO ()
runCheckConfig = [Char] -> IO (Either HoyoException Config)
forall (m :: * -> *).
(MonadIO m, MonadCatch m) =>
[Char] -> m (Either HoyoException Config)
decodeConfigFile ([Char] -> IO (Either HoyoException Config))
-> (Either HoyoException Config -> IO ()) -> [Char] -> IO ()
forall (m :: * -> *) a b c.
Monad m =>
(a -> m b) -> (b -> m c) -> a -> m c
>=> \case
Left HoyoException
err -> Text -> IO ()
forall (m :: * -> *). MonadIO m => Text -> m ()
printStderr (Text -> IO ()) -> Text -> IO ()
forall a b. (a -> b) -> a -> b
$ HoyoException -> Text
formatException HoyoException
err
Right Config
_ -> Text -> IO ()
forall (m :: * -> *). MonadIO m => Text -> m ()
printStdout Text
"Config is good"
runCheckBookmarks :: FilePath -> IO ()
runCheckBookmarks :: [Char] -> IO ()
runCheckBookmarks = [Char] -> IO (Either HoyoException Bookmarks)
forall (m :: * -> *).
(MonadIO m, MonadCatch m) =>
[Char] -> m (Either HoyoException Bookmarks)
decodeBookmarksFile ([Char] -> IO (Either HoyoException Bookmarks))
-> (Either HoyoException Bookmarks -> IO ()) -> [Char] -> IO ()
forall (m :: * -> *) a b c.
Monad m =>
(a -> m b) -> (b -> m c) -> a -> m c
>=> \case
Left HoyoException
err -> Text -> IO ()
forall (m :: * -> *). MonadIO m => Text -> m ()
printStderr (Text -> IO ()) -> Text -> IO ()
forall a b. (a -> b) -> a -> b
$ HoyoException -> Text
formatException HoyoException
err
Right Bookmarks
_ -> Text -> IO ()
forall (m :: * -> *). MonadIO m => Text -> m ()
printStdout Text
"Bookmarks file is good"
runCheck :: CheckOptions -> FilePath -> FilePath -> IO ()
runCheck :: CheckOptions -> [Char] -> [Char] -> IO ()
runCheck CheckOptions
opts [Char]
bFp [Char]
sFp = do
Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when (CheckOptions -> Bool
checkConfig CheckOptions
opts) (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ [Char] -> IO ()
runCheckConfig [Char]
sFp
Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when (CheckOptions -> Bool
checkBookmarks CheckOptions
opts) (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ [Char] -> IO ()
runCheckBookmarks [Char]
bFp
runDefaultCommand :: HoyoMonad ()
runDefaultCommand :: HoyoMonad ()
runDefaultCommand = SimpleGetter Env (Maybe Command) -> HoyoMonad (Maybe Command)
forall a (m :: * -> *) b.
MonadReader a m =>
SimpleGetter a b -> m b
asks' ((Config -> Const r Config) -> Env -> Const r Env
Lens' Env Config
config ((Config -> Const r Config) -> Env -> Const r Env)
-> ((Maybe Command -> Const r (Maybe Command))
-> Config -> Const r Config)
-> (Maybe Command -> Const r (Maybe Command))
-> Env
-> Const r Env
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Maybe Command -> Const r (Maybe Command))
-> Config -> Const r Config
Lens' Config (Maybe Command)
defaultCommand) HoyoMonad (Maybe Command)
-> (Maybe Command -> HoyoMonad ()) -> HoyoMonad ()
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= \case
Maybe Command
Nothing -> IO () -> HoyoMonad ()
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO () -> HoyoMonad ()) -> IO () -> HoyoMonad ()
forall a b. (a -> b) -> a -> b
$ Maybe [Char] -> IO ()
showHelp Maybe [Char]
forall a. Maybe a
Nothing
Just Command
DefaultCommand -> HoyoException -> HoyoMonad ()
forall e (m :: * -> *) a. MonadError e m => e -> m a
throwError (HoyoException -> HoyoMonad ()) -> HoyoException -> HoyoMonad ()
forall a b. (a -> b) -> a -> b
$ CommandException -> HoyoException
CommandException CommandException
LoopException
Just Command
otherCommand -> Command -> HoyoMonad ()
runCommand Command
otherCommand
runHelp :: HelpOptions -> HoyoMonad ()
runHelp :: HelpOptions -> HoyoMonad ()
runHelp (HelpOptions Maybe Text
cmd) = IO () -> HoyoMonad ()
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO () -> HoyoMonad ()) -> IO () -> HoyoMonad ()
forall a b. (a -> b) -> a -> b
$ Maybe [Char] -> IO ()
showHelp (Text -> [Char]
T.unpack (Text -> [Char]) -> Maybe Text -> Maybe [Char]
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Maybe Text
cmd)
runCommand :: Command -> HoyoMonad ()
runCommand :: Command -> HoyoMonad ()
runCommand (Add AddOptions
opts) = AddOptions -> HoyoMonad ()
runAdd AddOptions
opts
runCommand (Move MoveOptions
opts) = MoveOptions -> HoyoMonad ()
runMove MoveOptions
opts
runCommand (List ListOptions
opts) = ListOptions -> HoyoMonad ()
runList ListOptions
opts
runCommand (Clear ClearOptions
opts) = ClearOptions -> HoyoMonad ()
runClear ClearOptions
opts
runCommand (Delete DeleteOptions
opts) = DeleteOptions -> HoyoMonad ()
runDelete DeleteOptions
opts
runCommand (Refresh RefreshOptions
opts) = RefreshOptions -> HoyoMonad ()
runRefresh RefreshOptions
opts
runCommand (ConfigCmd ConfigCommand
opts) = ConfigCommand -> HoyoMonad ()
runConfig ConfigCommand
opts
runCommand Command
DefaultCommand = HoyoMonad ()
runDefaultCommand
runCommand (Help HelpOptions
opts) = HelpOptions -> HoyoMonad ()
runHelp HelpOptions
opts
runCommand (Check CheckOptions
opts) = do
Text -> HoyoMonad ()
forall (m :: * -> *). MonadIO m => Text -> m ()
printStderr Text
"It's discouraged to set default_command = \"check\" in your hoyo config file."
Env Bookmarks
_ [Char]
bFp Config
_ [Char]
sFp <- HoyoMonad Env
forall r (m :: * -> *). MonadReader r m => m r
ask
IO () -> HoyoMonad ()
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO () -> HoyoMonad ()) -> IO () -> HoyoMonad ()
forall a b. (a -> b) -> a -> b
$ CheckOptions -> [Char] -> [Char] -> IO ()
runCheck CheckOptions
opts [Char]
bFp [Char]
sFp