Skip to content

Commit

Permalink
Add the --hyperlink=WHEN option
Browse files Browse the repository at this point in the history
Fix #4.
  • Loading branch information
a5ob7r committed Jul 12, 2022
1 parent 5265d2a commit d93fa6f
Show file tree
Hide file tree
Showing 9 changed files with 108 additions and 11 deletions.
6 changes: 6 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,12 @@

## Unreleased

## 0.5.1.0 -- 2022-07-12

### Added

- Support `--hyperlink=WHEN` option.

## 0.5.0.2 -- 2022-06-19

### Fixed
Expand Down
6 changes: 5 additions & 1 deletion haskellorls.cabal
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
cabal-version: 2.2
name: haskellorls
version: 0.5.0.2
version: 0.5.1.0
synopsis: Haskell implementation of ls
license: BSD-3-Clause
license-file: LICENSE
Expand Down Expand Up @@ -60,6 +60,8 @@ library
Haskellorls.Format.Option
Haskellorls.Format.Type
Haskellorls.Format.Util
Haskellorls.Hyperlink.Option
Haskellorls.Hyperlink.Type
Haskellorls.Icon
Haskellorls.Indicator.Decorator
Haskellorls.Indicator.Option
Expand Down Expand Up @@ -112,6 +114,7 @@ library
LambdaCase
MultiParamTypeClasses
MultiWayIf
NamedFieldPuns
OverloadedStrings
RecordWildCards
StrictData
Expand All @@ -126,6 +129,7 @@ library
, extra ^>=1.7.10
, filepath-bytestring ^>=1.4.2.1.10
, Glob ^>=0.10.2
, hostname ^>=1.0
, mtl ^>=2.2.2
, natural-sort ^>=0.1.2
, optparse-applicative ^>=0.17.0
Expand Down
14 changes: 13 additions & 1 deletion src/Haskellorls.hs
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ where

import Control.Monad
import Data.Either
import qualified Data.Text as T
import Data.Version (showVersion)
import qualified Haskellorls.Decorator as Decorator
import Haskellorls.Exception
Expand All @@ -14,11 +15,13 @@ import qualified Haskellorls.Quote.Utils as Quote
import qualified Haskellorls.Recursive as Recursive
import qualified Haskellorls.Size.Utils as Size
import qualified Haskellorls.Utils as Utils
import Network.HostName
import Options.Applicative
import Paths_haskellorls (version)
import System.Exit
import System.FilePath.Posix.ByteString
import System.IO
import System.Posix.Directory.ByteString

-- | Haskellorls's process flow
-- 1. Gets all arguments passed to itself as string list.
Expand All @@ -38,8 +41,17 @@ haskellorls args = do
isConnectedToTerminal <- hIsTerminalDevice stdout
blockSize <- Size.lookupBlockSize options
quotingStyle <- Quote.lookupQuotingStyle options
cwd <- getWorkingDirectory
hostname <- T.pack <$> getHostName

run options {Option.blockSize = blockSize, Option.quotingStyle = quotingStyle, Option.toStdout = isConnectedToTerminal}
run
options
{ Option.blockSize = blockSize,
Option.quotingStyle = quotingStyle,
Option.toStdout = isConnectedToTerminal,
Option.currentWorkingDirectory = cwd,
Option.hostname = hostname
}

run :: Option.Option -> IO ()
run opt = do
Expand Down
30 changes: 30 additions & 0 deletions src/Haskellorls/Hyperlink/Option.hs
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
module Haskellorls.Hyperlink.Option
( hyperlinkParser,
module Haskellorls.Hyperlink.Type,
)
where

import Haskellorls.Hyperlink.Type
import Options.Applicative

hyperlinkParser :: Parser WHEN
hyperlinkParser =
option reader $
long "hyperlink"
<> metavar "WHEN"
<> value NEVER
<> help "When embed the hyperlink to the file into the filename."
<> completeWith ["never", "always", "auto"]
where
reader =
str @String >>= \case
"never" -> return NEVER
"no" -> return NEVER
"none" -> return NEVER
"always" -> return ALWAYS
"yes" -> return ALWAYS
"force" -> return ALWAYS
"auto" -> return AUTO
"tty" -> return AUTO
"if-tty" -> return AUTO
_ -> readerError "Only never, always or auto"
3 changes: 3 additions & 0 deletions src/Haskellorls/Hyperlink/Type.hs
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
module Haskellorls.Hyperlink.Type (WHEN (..)) where

data WHEN = NEVER | ALWAYS | AUTO
37 changes: 30 additions & 7 deletions src/Haskellorls/Name/Decorator.hs
Original file line number Diff line number Diff line change
Expand Up @@ -9,31 +9,54 @@ where
import Data.Maybe
import qualified Data.Text as T
import qualified Data.Text.Encoding as T
import Haskellorls.Class
import qualified Haskellorls.Hyperlink.Type as Hyperlink
import qualified Haskellorls.LsColor as Color
import qualified Haskellorls.NodeInfo as Node
import qualified Haskellorls.Option as Option
import qualified Haskellorls.Quote.Utils as Quote
import qualified Haskellorls.Utils as Utils
import qualified Haskellorls.WrappedText as WT
import System.FilePath.Posix.ByteString

colorizedNodeNameWrapper :: Option.Option -> Color.LsColors -> Node.NodeInfo -> [WT.WrappedText]
colorizedNodeNameWrapper opt config nd = Quote.quote (Quote.quoteStyle opt) $ colorizedNodeName opt config nd

colorizedNodeName :: Option.Option -> Color.LsColors -> Node.NodeInfo -> WT.WrappedText
colorizedNodeName opt c@(Color.Options {..}) nd = WT.WrappedText (left' <> l <> right') name' (left' <> r <> right')
colorizedNodeName opt c@(Color.Options {..}) nd = WT.WrappedText (left' <> l <> right' <> wtPrefix) wtWord (wtSuffix <> left' <> r <> right')
where
name = nodeName nd
name' = Utils.escapeFormatter opt name
WT.WrappedText {..} = WT.modify (Utils.escapeFormatter opt) $ nodeName opt nd
left' = Color.unSequence $ fromMaybe "" left
right' = Color.unSequence $ fromMaybe "" right
l = maybe "" Color.unSequence $ nd `Color.lookup` c
r = Color.unSequence $ fromMaybe "" reset

nodeNameWrapper :: Option.Option -> Node.NodeInfo -> [WT.WrappedText]
nodeNameWrapper opt node = Quote.quote style . WT.deserialize $ Utils.escapeFormatter opt name
nodeNameWrapper opt node = Quote.quote style $ WT.modify (Utils.escapeFormatter opt) . nodeName opt $ node
where
name = nodeName node
style = Quote.quoteStyle opt

nodeName :: Node.NodeInfo -> T.Text
nodeName = T.decodeUtf8 . Node.getNodePath
nodeName :: Option.Option -> Node.NodeInfo -> WT.WrappedText
nodeName opt@(Option.Option {hyperlink, hostname, toStdout}) node =
case hyperlink of
Hyperlink.NEVER -> deserialize $ rawNodeName node
Hyperlink.ALWAYS -> WT.WrappedText (left <> uri <> right) (rawNodeName node) (left <> right)
where
left = "\^[]8;;"
right = "\^G"
uri = "file://" <> hostname <> T.decodeUtf8 (mkAbsolutePath opt node)
Hyperlink.AUTO
| toStdout -> nodeName opt {Option.hyperlink = Hyperlink.ALWAYS} node
| otherwise -> nodeName opt {Option.hyperlink = Hyperlink.NEVER} node

rawNodeName :: Node.NodeInfo -> T.Text
rawNodeName = T.decodeUtf8 . Node.getNodePath

-- | Make the absolute path from a node.
mkAbsolutePath :: Option.Option -> Node.NodeInfo -> RawFilePath
mkAbsolutePath Option.Option {currentWorkingDirectory} Node.NodeInfo {..} =
normalise $
if
| isAbsolute getNodePath -> getNodePath
| isAbsolute getNodeDirName -> getNodeDirName </> getNodePath
| otherwise -> currentWorkingDirectory </> getNodeDirName </> getNodePath
14 changes: 14 additions & 0 deletions src/Haskellorls/Option.hs
Original file line number Diff line number Diff line change
Expand Up @@ -8,13 +8,15 @@ import qualified Data.Text as T
import qualified Haskellorls.Color.Option as Color
import qualified Haskellorls.Depth as Depth
import qualified Haskellorls.Format.Option as Format
import qualified Haskellorls.Hyperlink.Option as Hyperlink
import qualified Haskellorls.Indicator.Option as Indicator
import qualified Haskellorls.Quote.Option as Quote
import qualified Haskellorls.Size.Option as Size
import qualified Haskellorls.Sort.Option as Sort
import qualified Haskellorls.Time.Option as Time
import qualified Options.Applicative as OA
import qualified Options.Applicative.Help.Pretty as OA
import System.FilePath.Posix.ByteString
import Text.Read

data Option = Option
Expand Down Expand Up @@ -42,6 +44,7 @@ data Option = Option
dereferenceCommandLine :: Bool,
dereferenceCommandLineSymlinkToDir :: Bool,
hide :: String,
hyperlink :: Hyperlink.WHEN,
icon :: Bool,
indicatorStyle :: Indicator.IndicatorStyle,
inode :: Bool,
Expand Down Expand Up @@ -80,6 +83,8 @@ data Option = Option
oneline :: Bool,
toStdout :: Bool,
noQuote :: Bool,
currentWorkingDirectory :: RawFilePath,
hostname :: T.Text,
version :: Bool,
targets :: [FilePath]
}
Expand Down Expand Up @@ -114,6 +119,7 @@ optionParser =
<*> dereferenceCommandLineParser
<*> dereferenceCommandLineSymlinkToDirParser
<*> hideParser
<*> Hyperlink.hyperlinkParser
<*> iconParser
<*> Indicator.indicatorStyleParser
<*> inodeParser
Expand Down Expand Up @@ -152,6 +158,8 @@ optionParser =
<*> onelineParser
<*> toStdoutParser
<*> noQuoteParser
<*> currentWorkingDirectoryParser
<*> hostnameParser
<*> versionParser
<*> argParser

Expand Down Expand Up @@ -481,6 +489,12 @@ escapeParser =
<> OA.short 'b'
<> OA.help "Escape file name and link name by C lang style"

currentWorkingDirectoryParser :: OA.Parser RawFilePath
currentWorkingDirectoryParser = OA.strOption $ OA.value "" <> OA.internal

hostnameParser :: OA.Parser T.Text
hostnameParser = OA.strOption $ OA.value "" <> OA.internal

versionParser :: OA.Parser Bool
versionParser =
OA.switch $
Expand Down
4 changes: 2 additions & 2 deletions src/Haskellorls/SymbolicLink.hs
Original file line number Diff line number Diff line change
Expand Up @@ -16,10 +16,10 @@ import qualified Haskellorls.WrappedText as WT
linkName :: Option.Option -> Node.NodeInfo -> [WT.WrappedText]
linkName opt node = case Node.getNodeLinkInfo node of
Nothing -> []
_ -> prefix' : Quote.quote style (WT.deserialize $ Utils.escapeFormatter opt link)
_ -> prefix' : Quote.quote style (WT.modify (Utils.escapeFormatter opt) link)
where
style = Quote.quoteStyleForLink opt
link = Name.nodeName $ Node.toFileInfo node
link = Name.nodeName opt $ Node.toFileInfo node
prefix' = WT.deserialize prefix

coloredLinkName :: Option.Option -> Color.LsColors -> Node.NodeInfo -> [WT.WrappedText]
Expand Down
5 changes: 5 additions & 0 deletions src/Haskellorls/WrappedText.hs
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
module Haskellorls.WrappedText
( WrappedText (..),
modify,
module Haskellorls.Class,
)
where
Expand All @@ -26,3 +27,7 @@ instance Deserialize WrappedText

instance Length WrappedText where
len = Utils.textLengthForDisplay . wtWord

-- | Modify only 'wtWord' in 'WrappedText'.
modify :: (T.Text -> T.Text) -> WrappedText -> WrappedText
modify f WrappedText {..} = WrappedText wtPrefix (f wtWord) wtSuffix

0 comments on commit d93fa6f

Please sign in to comment.