Skip to content

Commit bfafe3b

Browse files
authored
Show documentation on hover for symbols defined in the same module (#691)
* Show documentation on hover for symbols defined in the same module When parsing a module, if parsing haddocks succeeds, then use them Previously, even though we were parsing modules twice, with and without haddocks, we were just returning the result of parsing without haddocks. The reason for this was that Opt_KeepRawTokenStream and Opt_Haddock do not interact nicely. We decided that for now it was better to fix an actual issue and then solve the problem when hlint requires a module with Opt_KeepRawTokenStream. * Add option to decide which ParsedModule to return
1 parent 2fece7f commit bfafe3b

File tree

4 files changed

+42
-14
lines changed

4 files changed

+42
-14
lines changed

src/Development/IDE/Core/RuleTypes.hs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,9 @@ type instance RuleResult GetKnownFiles = HS.HashSet NormalizedFilePath
6161
-- that module.
6262
data TcModuleResult = TcModuleResult
6363
{ tmrModule :: TypecheckedModule
64+
-- ^ warning, the ModIface in the tm_checked_module_info of the
65+
-- TypecheckedModule will always be Nothing, use the ModIface in the
66+
-- HomeModInfo instead
6467
, tmrModInfo :: HomeModInfo
6568
, tmrDeferedError :: !Bool -- ^ Did we defer any type errors for this module?
6669
}

src/Development/IDE/Core/Rules.hs

Lines changed: 28 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -233,6 +233,12 @@ priorityGenerateCore = Priority (-1)
233233
priorityFilesOfInterest :: Priority
234234
priorityFilesOfInterest = Priority (-2)
235235

236+
-- | IMPORTANT FOR HLINT INTEGRATION:
237+
-- We currently parse the module both with and without Opt_Haddock, and
238+
-- return the one with Haddocks if it -- succeeds. However, this may not work
239+
-- for hlint, and we might need to save the one without haddocks too.
240+
-- See https://github.com/digital-asset/ghcide/pull/350#discussion_r370878197
241+
-- and https://github.com/mpickering/ghcide/pull/22#issuecomment-625070490
236242
getParsedModuleRule :: Rules ()
237243
getParsedModuleRule = defineEarlyCutoff $ \GetParsedModule file -> do
238244
sess <- use_ GhcSession file
@@ -251,18 +257,28 @@ getParsedModuleRule = defineEarlyCutoff $ \GetParsedModule file -> do
251257
then
252258
liftIO mainParse
253259
else do
254-
let haddockParse = do
255-
(_, (!diagsHaddock, _)) <-
256-
getParsedModuleDefinition (withOptHaddock hsc) opt comp_pkgs file modTime contents
257-
return diagsHaddock
258-
259-
((fingerPrint, (diags, res)), diagsHaddock) <-
260-
-- parse twice, with and without Haddocks, concurrently
261-
-- we want warnings if parsing with Haddock fails
262-
-- but if we parse with Haddock we lose annotations
263-
liftIO $ concurrently mainParse haddockParse
264-
265-
return (fingerPrint, (mergeParseErrorsHaddock diags diagsHaddock, res))
260+
let haddockParse = getParsedModuleDefinition (withOptHaddock hsc) opt comp_pkgs file modTime contents
261+
262+
-- parse twice, with and without Haddocks, concurrently
263+
-- we cannot ignore Haddock parse errors because files of
264+
-- non-interest are always parsed with Haddocks
265+
-- If we can parse Haddocks, might as well use them
266+
--
267+
-- HLINT INTEGRATION: might need to save the other parsed module too
268+
((fp,(diags,res)),(fph,(diagsh,resh))) <- liftIO $ concurrently mainParse haddockParse
269+
270+
-- Merge haddock and regular diagnostics so we can always report haddock
271+
-- parse errors
272+
let diagsM = mergeParseErrorsHaddock diags diagsh
273+
case resh of
274+
Just _
275+
| HaddockParse <- optHaddockParse opt
276+
-> pure (fph, (diagsM, resh))
277+
-- If we fail to parse haddocks, report the haddock diagnostics as well and
278+
-- return the non-haddock parse.
279+
-- This seems to be the correct behaviour because the Haddock flag is added
280+
-- by us and not the user, so our IDE shouldn't stop working because of it.
281+
_ -> pure (fp, (diagsM, res))
266282

267283

268284
withOptHaddock :: HscEnv -> HscEnv
@@ -281,7 +297,6 @@ mergeParseErrorsHaddock normal haddock = normal ++
281297
fixMessage x | "parse error " `T.isPrefixOf` x = "Haddock " <> x
282298
| otherwise = "Haddock: " <> x
283299

284-
285300
getParsedModuleDefinition :: HscEnv -> IdeOptions -> [PackageName] -> NormalizedFilePath -> UTCTime -> Maybe T.Text -> IO (Maybe ByteString, ([FileDiagnostic], Maybe ParsedModule))
286301
getParsedModuleDefinition packageState opt comp_pkgs file modTime contents = do
287302
let fp = fromNormalizedFilePath file

src/Development/IDE/Types/Options.hs

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ module Development.IDE.Types.Options
2424
, defaultLspConfig
2525
, CheckProject(..)
2626
, CheckParents(..)
27+
, OptHaddockParse(..)
2728
) where
2829

2930
import Development.Shake
@@ -88,8 +89,16 @@ data IdeOptions = IdeOptions
8889
-- ^ Whether to typecheck the entire project on load
8990
, optCheckParents :: CheckParents
9091
-- ^ When to typecheck reverse dependencies of a file
92+
, optHaddockParse :: OptHaddockParse
93+
-- ^ Whether to return result of parsing module with Opt_Haddock.
94+
-- Otherwise, return the result of parsing without Opt_Haddock, so
95+
-- that the parsed module contains the result of Opt_KeepRawTokenStream,
96+
-- which might be necessary for hlint.
9197
}
9298

99+
data OptHaddockParse = HaddockParse | NoHaddockParse
100+
deriving (Eq,Ord,Show,Enum)
101+
93102
newtype CheckProject = CheckProject { shouldCheckProject :: Bool }
94103
deriving stock (Eq, Ord, Show)
95104
deriving newtype (FromJSON,ToJSON)
@@ -147,6 +156,7 @@ defaultIdeOptions session = IdeOptions
147156
,optTesting = IdeTesting False
148157
,optCheckProject = checkProject defaultLspConfig
149158
,optCheckParents = checkParents defaultLspConfig
159+
,optHaddockParse = HaddockParse
150160
}
151161

152162

test/exe/Main.hs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2186,7 +2186,7 @@ findDefinitionAndHoverTests = let
21862186
, test yes yes mclL36 mcl "top-level fn 1st clause"
21872187
, test yes yes mclL37 mcl "top-level fn 2nd clause #246"
21882188
, test yes yes spaceL37 space "top-level fn on space #315"
2189-
, test no broken docL41 doc "documentation #7"
2189+
, test no yes docL41 doc "documentation #7"
21902190
, test no yes eitL40 kindE "kind of Either #273"
21912191
, test no yes intL40 kindI "kind of Int #273"
21922192
, test no broken tvrL40 kindV "kind of (* -> *) type variable #273"

0 commit comments

Comments
 (0)