@@ -73,6 +73,8 @@ spec = do
7373 prettyPrintImportSection (addExplicitImport' (IdeDeclValueOperator (IdeValueOperator op (P.Qualified Nothing (Left (P.Ident ""))) 2 P.Infix Nothing)) mn is)
7474 addDtorImport i t mn is =
7575 prettyPrintImportSection (addExplicitImport' (IdeDeclDataConstructor (IdeDataConstructor (P.ProperName i) t wildcard)) mn is)
76+ addTypeImport i mn is =
77+ prettyPrintImportSection (addExplicitImport' (IdeDeclType (IdeType (P.ProperName i) P.Star)) mn is)
7678 it "adds an implicit unqualified import" $
7779 shouldBe
7880 (addImplicitImport' simpleFileImports (P.moduleNameFromString "Data.Map"))
@@ -100,20 +102,26 @@ spec = do
100102 shouldBe
101103 (addOpImport (P.OpName "<~>") (P.moduleNameFromString "Data.Array") explicitImports)
102104 [ "import Prelude"
103− , "import Data.Array ((<~>), tail)"
105+ , "import Data.Array (tail, (<~>))"
104106 ]
107+ it "adds a type with constructors without automatically adding an open import of said constructors " $
108+ shouldBe
109+ (addTypeImport "Maybe" (P.moduleNameFromString "Data.Maybe") simpleFileImports)
110+ [ "import Prelude"
111+ , "import Data.Maybe (Maybe)"
112+ ]
105113 it "adds the type for a given DataConstructor" $
106114 shouldBe
107115 (addDtorImport "Just" (P.ProperName "Maybe") (P.moduleNameFromString "Data.Maybe") simpleFileImports)
108116 [ "import Prelude"
109− , "import Data.Maybe (Maybe(Just))"
117+ , "import Data.Maybe (Maybe(..))"
110118 ]
111119 it "adds a dataconstructor to an existing type import" $ do
112120 let Right (_, _, typeImports, _) = sliceImportSection (withImports ["import Data.Maybe (Maybe)"])
113121 shouldBe
114122 (addDtorImport "Just" (P.ProperName "Maybe") (P.moduleNameFromString "Data.Maybe") typeImports)
115123 [ "import Prelude"
116− , "import Data.Maybe (Maybe(Just))"
124+ , "import Data.Maybe (Maybe(..))"
117125 ]
118126 it "doesn't add a dataconstructor to an existing type import with open dtors" $ do
119127 let Right (_, _, typeImports, _) = sliceImportSection (withImports ["import Data.Maybe (Maybe(..))"])
@@ -128,3 +136,38 @@ spec = do
128136 [ "import Prelude"
129137 , "import Data.Array (tail)"
130138 ]
139+
140+ describe "explicit import sorting" $ do
141+ -- given some basic import skeleton
142+ let Right (_, _, baseImports, _) = sliceImportSection $ withImports ["import Control.Monad (ap)"]
143+ moduleName = (P.moduleNameFromString "Control.Monad")
144+ addImport imports import' = addExplicitImport' import' moduleName imports
145+ valueImport ident = (IdeDeclValue (IdeValue (P.Ident ident) wildcard))
146+ typeImport name = (IdeDeclType (IdeType (P.ProperName name) P.Star))
147+ classImport name = (IdeDeclTypeClass (P.ProperName name))
148+ dtorImport name typeName = (IdeDeclDataConstructor (IdeDataConstructor (P.ProperName name) (P.ProperName typeName) wildcard))
149+ -- expect any list of provided identifiers, when imported, to come out as specified
150+ expectSorted imports expected = shouldBe
151+ (ordNub $ map
152+ (prettyPrintImportSection . foldl addImport baseImports)
153+ (permutations imports))
154+ [expected]
155+ it "sorts class" $
156+ expectSorted (map classImport ["Applicative", "Bind"])
157+ ["import Prelude", "import Control.Monad (class Applicative, class Bind, ap)"]
158+ it "sorts value" $
159+ expectSorted (map valueImport ["unless", "where"])
160+ ["import Prelude", "import Control.Monad (ap, unless, where)"]
161+ it "sorts type, value" $
162+ expectSorted
163+ ((map valueImport ["unless", "where"]) ++ (map typeImport ["Foo", "Bar"]))
164+ ["import Prelude", "import Control.Monad (Bar, Foo, ap, unless, where)"]
165+ it "sorts class, type, value" $
166+ expectSorted
167+ ((map valueImport ["unless", "where"]) ++ (map typeImport ["Foo", "Bar"]) ++ (map classImport ["Applicative", "Bind"]))
168+ ["import Prelude", "import Control.Monad (class Applicative, class Bind, Bar, Foo, ap, unless, where)"]
169+ it "sorts types with constructors, using open imports for the constructors" $
170+ expectSorted
171+ -- the imported names don't actually have to exist!
172+ (map (uncurry dtorImport) [("Just", "Maybe"), ("Nothing", "Maybe"), ("SomeOtherConstructor", "SomeDataType")])
173+ ["import Prelude", "import Control.Monad (Maybe(..), SomeDataType(..), ap)"]