Skip to content

Commit

Permalink
format: run formatter and add comments
Browse files Browse the repository at this point in the history
  • Loading branch information
sloorush committed Aug 12, 2022
1 parent 892a129 commit e6a2b5c
Show file tree
Hide file tree
Showing 5 changed files with 284 additions and 264 deletions.
2 changes: 1 addition & 1 deletion hls-plugin-api/src/Ide/Plugin/Config.hs
Original file line number Diff line number Diff line change
Expand Up @@ -110,7 +110,7 @@ data PluginConfig =
, plcCompletionOn :: !Bool
, plcRenameOn :: !Bool
, plcSelectionRangeOn :: !Bool
, plcFoldingRangeOn :: !Bool
, plcFoldingRangeOn :: !Bool
, plcConfig :: !A.Object
} deriving (Show,Eq)

Expand Down
165 changes: 88 additions & 77 deletions plugins/hls-code-range-plugin/src/Ide/Plugin/CodeRange.hs
Original file line number Diff line number Diff line change
@@ -1,22 +1,23 @@
{-# LANGUAGE OverloadedStrings #-}
{-# LANGUAGE RecordWildCards #-}
{-# LANGUAGE OverloadedStrings #-}
{-# LANGUAGE RecordWildCards #-}
{-# LANGUAGE ScopedTypeVariables #-}

module Ide.Plugin.CodeRange (
descriptor
, Log
module Ide.Plugin.CodeRange
( descriptor,
Log,

-- * Internal
, findPosition
) where
findPosition,
)
where

import Control.Monad.Except (ExceptT (ExceptT),
runExceptT)
import Control.Monad.IO.Class (liftIO)
import Control.Monad.Trans.Maybe (MaybeT (MaybeT),
maybeToExceptT)
import Data.Either.Extra (maybeToEither)
import Data.Maybe ( fromMaybe, catMaybes )
import Data.Maybe (fromMaybe)
import Data.Vector (Vector)
import qualified Data.Vector as V
import Development.IDE (IdeAction,
Expand All @@ -43,62 +44,67 @@ import Ide.Types (PluginDescriptor (pluginH
defaultPluginDescriptor,
mkPluginHandler)
import Language.LSP.Server (LspM)
import Language.LSP.Types (List (List),
import Language.LSP.Types (FoldingRange (..),
FoldingRangeParams (..),
List (List),
NormalizedFilePath,
Position (..),
Range (_start),
ResponseError,
SMethod (STextDocumentSelectionRange, STextDocumentFoldingRange),
SMethod (STextDocumentFoldingRange, STextDocumentSelectionRange),
SelectionRange (..),
SelectionRangeParams (..),
FoldingRange (..),
FoldingRangeParams(..),
TextDocumentIdentifier (TextDocumentIdentifier),
Uri
)
Uri)
import Prelude hiding (log, span)

descriptor :: Recorder (WithPriority Log) -> PluginId -> PluginDescriptor IdeState
descriptor recorder plId = (defaultPluginDescriptor plId)
{ pluginHandlers = mkPluginHandler STextDocumentSelectionRange selectionRangeHandler
<> mkPluginHandler STextDocumentFoldingRange foldingRangeHandler
, pluginRules = codeRangeRule (cmapWithPrio LogRules recorder)
descriptor recorder plId =
(defaultPluginDescriptor plId)
{ pluginHandlers =
mkPluginHandler STextDocumentSelectionRange selectionRangeHandler
<> mkPluginHandler STextDocumentFoldingRange foldingRangeHandler,
pluginRules = codeRangeRule (cmapWithPrio LogRules recorder)
}

data Log = LogRules Rules.Log

instance Pretty Log where
pretty log = case log of
LogRules codeRangeLog -> pretty codeRangeLog
pretty log = case log of
LogRules codeRangeLog -> pretty codeRangeLog

foldingRangeHandler :: IdeState -> PluginId -> FoldingRangeParams -> LspM c (Either ResponseError (List FoldingRange))
foldingRangeHandler ide _ FoldingRangeParams{..} = do
pluginResponse $ do
filePath <- ExceptT . pure . maybeToEither "fail to convert uri to file path" $
toNormalizedFilePath' <$> uriToFilePath' uri
foldingRanges <- ExceptT . liftIO . runIdeAction "FoldingRange" (shakeExtras ide) . runExceptT $
getFoldingRanges filePath
pure . List $ foldingRanges
where
uri :: Uri
TextDocumentIdentifier uri = _textDocument
foldingRangeHandler ide _ FoldingRangeParams {..} = do
pluginResponse $ do
filePath <-
ExceptT . pure . maybeToEither "fail to convert uri to file path" $
toNormalizedFilePath' <$> uriToFilePath' uri
foldingRanges <-
ExceptT . liftIO . runIdeAction "FoldingRange" (shakeExtras ide) . runExceptT $
getFoldingRanges filePath
pure . List $ foldingRanges
where
uri :: Uri
TextDocumentIdentifier uri = _textDocument

getFoldingRanges :: NormalizedFilePath -> ExceptT String IdeAction [FoldingRange]
getFoldingRanges file = do
(codeRange, _) <- maybeToExceptT "fail to get code range" $ useE GetCodeRange file
(codeRange, _) <- maybeToExceptT "fail to get code range" $ useE GetCodeRange file

let foldingRanges = findFoldingRanges codeRange
let foldingRanges = findFoldingRanges codeRange

maybeToExceptT "Fail to generate folding range" (MaybeT . pure $ Just foldingRanges)
maybeToExceptT "Fail to generate folding range" (MaybeT . pure $ Just foldingRanges)

selectionRangeHandler :: IdeState -> PluginId -> SelectionRangeParams -> LspM c (Either ResponseError (List SelectionRange))
selectionRangeHandler ide _ SelectionRangeParams{..} = do
pluginResponse $ do
filePath <- ExceptT . pure . maybeToEither "fail to convert uri to file path" $
toNormalizedFilePath' <$> uriToFilePath' uri
selectionRanges <- ExceptT . liftIO . runIdeAction "SelectionRange" (shakeExtras ide) . runExceptT $
getSelectionRanges filePath positions
pure . List $ selectionRanges
selectionRangeHandler ide _ SelectionRangeParams {..} = do
pluginResponse $ do
filePath <-
ExceptT . pure . maybeToEither "fail to convert uri to file path" $
toNormalizedFilePath' <$> uriToFilePath' uri
selectionRanges <-
ExceptT . liftIO . runIdeAction "SelectionRange" (shakeExtras ide) . runExceptT $
getSelectionRanges filePath positions
pure . List $ selectionRanges
where
uri :: Uri
TextDocumentIdentifier uri = _textDocument
Expand All @@ -108,19 +114,20 @@ selectionRangeHandler ide _ SelectionRangeParams{..} = do

getSelectionRanges :: NormalizedFilePath -> [Position] -> ExceptT String IdeAction [SelectionRange]
getSelectionRanges file positions = do
(codeRange, positionMapping) <- maybeToExceptT "fail to get code range" $ useE GetCodeRange file
-- 'positionMapping' should be appied to the input before using them
positions' <- maybeToExceptT "fail to apply position mapping to input positions" . MaybeT . pure $
traverse (fromCurrentPosition positionMapping) positions
(codeRange, positionMapping) <- maybeToExceptT "fail to get code range" $ useE GetCodeRange file
-- 'positionMapping' should be appied to the input before using them
positions' <-
maybeToExceptT "fail to apply position mapping to input positions" . MaybeT . pure $
traverse (fromCurrentPosition positionMapping) positions

let selectionRanges = flip fmap positions' $ \pos ->
-- We need a default selection range if the lookup fails, so that other positions can still have valid results.
let defaultSelectionRange = SelectionRange (Range pos pos) Nothing
in fromMaybe defaultSelectionRange . findPosition pos $ codeRange
let selectionRanges = flip fmap positions' $ \pos ->
-- We need a default selection range if the lookup fails, so that other positions can still have valid results.
let defaultSelectionRange = SelectionRange (Range pos pos) Nothing
in fromMaybe defaultSelectionRange . findPosition pos $ codeRange

-- 'positionMapping' should be applied to the output ranges before returning them
maybeToExceptT "fail to apply position mapping to output positions" . MaybeT . pure $
traverse (toCurrentSelectionRange positionMapping) selectionRanges
-- 'positionMapping' should be applied to the output ranges before returning them
maybeToExceptT "fail to apply position mapping to output positions" . MaybeT . pure $
traverse (toCurrentSelectionRange positionMapping) selectionRanges

-- | Find 'Position' in 'CodeRange'. This can fail, if the given position is not covered by the 'CodeRange'.
findPosition :: Position -> CodeRange -> Maybe SelectionRange
Expand All @@ -129,54 +136,58 @@ findPosition pos root = go Nothing root
-- Helper function for recursion. The range list is built top-down
go :: Maybe SelectionRange -> CodeRange -> Maybe SelectionRange
go acc node =
if positionInRange pos range
if positionInRange pos range
then maybe acc' (go acc') (binarySearchPos children)
-- If all children doesn't contain pos, acc' will be returned.
else -- If all children doesn't contain pos, acc' will be returned.
-- acc' will be Nothing only if we are in the root level.
else Nothing
Nothing
where
range = _codeRange_range node
children = _codeRange_children node
acc' = Just $ maybe (SelectionRange range Nothing) (SelectionRange range . Just) acc

binarySearchPos :: Vector CodeRange -> Maybe CodeRange
binarySearchPos v
| V.null v = Nothing
| V.length v == 1,
Just r <- V.headM v = if positionInRange pos (_codeRange_range r) then Just r else Nothing
| otherwise = do
let (left, right) = V.splitAt (V.length v `div` 2) v
startOfRight <- _start . _codeRange_range <$> V.headM right
if pos < startOfRight then binarySearchPos left else binarySearchPos right

| V.null v = Nothing
| V.length v == 1,
Just r <- V.headM v =
if positionInRange pos (_codeRange_range r) then Just r else Nothing
| otherwise = do
let (left, right) = V.splitAt (V.length v `div` 2) v
startOfRight <- _start . _codeRange_range <$> V.headM right
if pos < startOfRight then binarySearchPos left else binarySearchPos right

-- | Traverses through the code range and children to a folding ranges
findFoldingRanges :: CodeRange -> [FoldingRange]
findFoldingRanges r@(CodeRange _ children _) =
let frRoot :: [FoldingRange] = case createFoldingRange r of
Just x -> [x]
Just x -> [x]
Nothing -> []

frChildren :: [FoldingRange] = concat $ V.toList $ fmap findFoldingRanges children
in frRoot ++ frChildren

-- | Parses code range to folding range
createFoldingRange :: CodeRange -> Maybe FoldingRange
createFoldingRange node1 = do
let range = _codeRange_range node1
let Range startPos endPos = range
let Position lineStart _= startPos
let Position lineEnd _ = endPos
let codeRangeKind = _codeRange_kind node1
let range = _codeRange_range node1
let Range startPos endPos = range
let Position lineStart _ = startPos
let Position lineEnd _ = endPos
let codeRangeKind = _codeRange_kind node1

let frk = crkToFrk codeRangeKind
let frk = crkToFrk codeRangeKind

case frk of
Just _ -> Just (FoldingRange lineStart Nothing lineEnd Nothing frk)
Nothing -> Nothing
case frk of
Just _ -> Just (FoldingRange lineStart Nothing lineEnd Nothing frk)
Nothing -> Nothing

-- | Likes 'toCurrentPosition', but works on 'SelectionRange'
toCurrentSelectionRange :: PositionMapping -> SelectionRange -> Maybe SelectionRange
toCurrentSelectionRange positionMapping SelectionRange{..} = do
newRange <- toCurrentRange positionMapping _range
pure $ SelectionRange {
_range = newRange,
toCurrentSelectionRange positionMapping SelectionRange {..} = do
newRange <- toCurrentRange positionMapping _range
pure $
SelectionRange
{ _range = newRange,
_parent = _parent >>= toCurrentSelectionRange positionMapping
}
}

0 comments on commit e6a2b5c

Please sign in to comment.