Skip to content

Commit 9c090d4

Browse files
akrmnjhmcstanton
andauthored
Add support for post qualified import formatting (more cases) (#372)
* Add support for post qualified import formatting. Adds an option to use post qualified module imports. Related to #284 Resolves #334 * Add failing test cases for post qualified import formatting. Related to #284 and #334 * Fix imports test case 33 - 'qualified' goes before imported names * Consolidate import module name logic Co-authored-by: Jim McStanton <[email protected]>
1 parent d786187 commit 9c090d4

File tree

4 files changed

+146
-52
lines changed

4 files changed

+146
-52
lines changed

data/stylish-haskell.yaml

+14-10
Original file line numberDiff line numberDiff line change
@@ -275,21 +275,25 @@ steps:
275275
# Default: false
276276
space_surround: false
277277

278-
# Enabling this argument will use the new GHC lib parse to format imports.
278+
# Post qualify option moves any qualifies found in import declarations
279+
# to the end of the declaration. This also adjust padding for any
280+
# unqualified import declarations.
279281
#
280-
# This currently assumes a few things, it will assume that you want post
281-
# qualified imports. It is also not as feature complete as the old
282-
# imports formatting.
282+
# - true: Qualified as <module name> is moved to the end of the
283+
# declaration.
283284
#
284-
# It does not remove redundant lines or merge lines. As such, the full
285-
# feature scope is still pending.
285+
# > import Data.Bar
286+
# > import Data.Foo qualified as F
286287
#
287-
# It _is_ however, a fine alternative if you are using features that are
288-
# not parseable by haskell src extensions and you're comfortable with the
289-
# presets.
288+
# - false: Qualified remains in the default location and unqualified
289+
# imports are padded to align with qualified imports.
290+
#
291+
# > import Data.Bar
292+
# > import qualified Data.Foo as F
290293
#
291294
# Default: false
292-
ghc_lib_parser: false
295+
post_qualify: false
296+
293297

294298
# Language pragmas
295299
- language_pragmas:

lib/Language/Haskell/Stylish/Config.hs

+1
Original file line numberDiff line numberDiff line change
@@ -289,6 +289,7 @@ parseImports config o = fmap (Imports.step columns) $ Imports.Options
289289
<*> (o A..:? "list_padding" >>= maybe (pure $ def Imports.listPadding) parseListPadding)
290290
<*> o A..:? "separate_lists" A..!= def Imports.separateLists
291291
<*> o A..:? "space_surround" A..!= def Imports.spaceSurround
292+
<*> o A..:? "post_qualify" A..!= def Imports.postQualified
292293
where
293294
def f = f Imports.defaultOptions
294295

lib/Language/Haskell/Stylish/Step/Imports.hs

+26-18
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,7 @@ data Options = Options
6161
, listPadding :: ListPadding
6262
, separateLists :: Bool
6363
, spaceSurround :: Bool
64+
, postQualified :: Bool
6465
} deriving (Eq, Show)
6566

6667
defaultOptions :: Options
@@ -73,6 +74,7 @@ defaultOptions = Options
7374
, listPadding = LPConstant 4
7475
, separateLists = True
7576
, spaceSurround = False
77+
, postQualified = False
7678
}
7779

7880
data ListPadding
@@ -143,8 +145,8 @@ formatImports
143145
-> NonEmpty (Located Import) -> Lines
144146
formatImports maxCols options m moduleStats rawGroup =
145147
runPrinter_ (PrinterConfig maxCols) [] m do
146-
let
147-
148+
let
149+
148150
group
149151
= NonEmpty.sortWith unLocated rawGroup
150152
& mergeImports
@@ -177,25 +179,31 @@ printQualified Options{..} padNames stats (L _ decl) = do
177179

178180
when (isSafe decl) (putText "safe" >> space)
179181

180-
case (isQualified decl, isAnyQualified stats) of
181-
(True, _) -> putText "qualified" >> space
182-
(_, True) -> putText " " >> space
183-
_ -> pure ()
184-
185-
moduleNamePosition <- length <$> getCurrentLine
186-
forM_ (ideclPkgQual decl') $ \pkg -> putText (stringLiteral pkg) >> space
187-
putText (moduleName decl)
188-
189-
-- Only print spaces if something follows.
190-
when padNames $
191-
when (isJust (ideclAs decl') || isHiding decl ||
192-
not (null $ ideclHiding decl')) $
193-
putText $
194-
replicate (isLongestImport stats - importModuleNameLength decl) ' '
182+
let
183+
module_ = do
184+
moduleNamePosition <- length <$> getCurrentLine
185+
forM_ (ideclPkgQual decl') $ \pkg -> putText (stringLiteral pkg) >> space
186+
putText (moduleName decl)
187+
-- Only print spaces if something follows.
188+
when padNames $
189+
when (isJust (ideclAs decl') || isHiding decl ||
190+
not (null $ ideclHiding decl')) $
191+
putText $
192+
replicate (isLongestImport stats - importModuleNameLength decl) ' '
193+
pure moduleNamePosition
194+
195+
moduleNamePosition <-
196+
case (postQualified, isQualified decl, isAnyQualified stats) of
197+
(False, True , _ ) -> putText "qualified" *> space *> module_
198+
(False, _ , True) -> putText " " *> space *> module_
199+
(True , True , _ ) -> module_ <* space <* putText "qualified"
200+
_ -> module_
195201

196202
beforeAliasPosition <- length <$> getCurrentLine
197-
forM_ (ideclAs decl') \(L _ name) ->
203+
204+
forM_ (ideclAs decl') \(L _ name) -> do
198205
space >> putText "as" >> space >> putText (moduleNameString name)
206+
199207
afterAliasPosition <- length <$> getCurrentLine
200208

201209
when (isHiding decl) (space >> putText "hiding")

0 commit comments

Comments
 (0)