1{-# OPTIONS_GHC -Wall #-}
2module Canonicalize.Variable where
4import qualified Data.Either as Either
5import qualified Data.Map as Map
6import qualified Data.Set as Set
8import qualified AST.Helpers as Help
9import qualified AST.Module.Name as ModuleName
10import qualified AST.Type as Type
11import qualified AST.Variable as Var
12import qualified Reporting.Annotation as A
13import qualified Reporting.Error.Canonicalize as Error
14import qualified Reporting.Error.Helpers as Error
15import qualified Reporting.Region as R
16import qualified Canonicalize.Environment as Env
17import qualified Canonicalize.Result as Result
18import qualified Elm.Package as Pkg
19import Elm.Utils ((|>))
22variable :: R.Region -> Env.Environment -> String -> Result.ResultErr Var.Canonical
23variable region env var =
25 Right (name, varName) | ModuleName.isNative name ->
28 ModuleName.Canonical Pkg.dummyName name
30 Result.var (Var.Canonical (Var.Module moduleName) varName)
33 case Set.toList `fmap` Map.lookup var (Env._values env) of
38 preferLocals region env "variable" vs var
41 notFound region "variable" (Map.keys (Env._values env)) var
51 (Var.Canonical, [String], Type.Canonical)
54 case adts ++ aliases of
55 [] -> notFound region "type" (Map.keys (Env._adts env) ++ Map.keys (Env._aliases env)) var
56 [v] -> Result.var' extract v
57 vs -> preferLocals' region env extract "type" vs var
60 map Left (maybe [] Set.toList (Map.lookup var (Env._adts env)))
63 map Right (maybe [] Set.toList (Map.lookup var (Env._aliases env)))
76 -> Result.ResultErr Var.Canonical
77pvar region env var actualArgs =
78 case Set.toList `fmap` Map.lookup var (Env._patterns env) of
83 preferLocals' region env fst "pattern" values var
84 `Result.andThen` foundArgCheck
87 notFound region "pattern" (Map.keys (Env._patterns env)) var
89 foundArgCheck (name, expectedArgs) =
90 if actualArgs == expectedArgs
92 else Result.err (A.A region (Error.argMismatch name expectedArgs actualArgs))
103 -> Result.ResultErr Var.Canonical
104preferLocals region env =
105 preferLocals' region env id
111 -> (a -> Var.Canonical)
115 -> Result.ResultErr a
116preferLocals' region env extract kind possibilities var =
117 case filter (isLocal (Env._home env) . extract) possibilities of
119 ambiguous possibilities
122 Result.var' extract v
124 --Local vars shadow top-level vars
126 | isTopLevel (extract v1) ->
127 Result.var' extract v2
129 | isTopLevel (extract v2) ->
130 Result.var' extract v1
135 ambiguous possibleVars =
136 Result.err (A.A region (Error.variable kind var Error.Ambiguous vars))
138 vars = map (Var.toString . extract) possibleVars
141isLocal :: ModuleName.Canonical -> Var.Canonical -> Bool
142isLocal contextName (Var.Canonical home _) =
157isTopLevel :: Var.Canonical -> Bool
158isTopLevel (Var.Canonical home _) =
170 Either String (ModuleName.Raw, String)
173toVarName :: String -> VarName
175 case Help.splitDots var of
177 xs -> Right (init xs, last xs)
180noQualifier :: VarName -> String
187qualifiedToString :: (ModuleName.Raw, String) -> String
188qualifiedToString (modul, name) =
189 ModuleName.toString modul ++ "." ++ name
192isOp :: VarName -> Bool
194 Help.isOp (noQualifier name)
199notFound :: R.Region -> String -> [String] -> String -> Result.ResultErr a
200notFound region kind possibilities var =
205 map toVarName possibilities
207 (problem, suggestions) =
210 exposedProblem name possibleNames
212 Right (modul, varName) ->
213 qualifiedProblem modul varName (Either.rights possibleNames)
215 Result.err (A.A region (Error.variable kind var problem suggestions))
218exposedProblem :: VarName -> [VarName] -> (Error.VarProblem, [String])
219exposedProblem name possibleNames =
220 let (exposed, qualified) =
222 |> filter (\n -> isOp name == isOp n)
223 |> Error.nearbyNames noQualifier name
224 |> Either.partitionEithers
226 ( Error.ExposedUnknown
227 , exposed ++ map qualifiedToString qualified
234 -> [(ModuleName.Raw, String)]
235 -> (Error.VarProblem, [String])
236qualifiedProblem moduleName name allQualified =
237 let availableModules =
238 Set.fromList (map fst allQualified)
241 ModuleName.toString moduleName
243 case Set.member moduleName availableModules of
245 ( Error.QualifiedUnknown moduleNameString name
247 |> filter ((==) moduleName . fst)
249 |> Error.nearbyNames id name
253 ( Error.UnknownQualifier moduleNameString name
254 , Set.toList availableModules
255 |> map ModuleName.toString
256 |> Error.nearbyNames id moduleNameString
keysesc to close
- j k
- move down, up
- enter
- open
- esc
- back, or up a level
- 1 2 3 4
- readme, files, commits, refs
- /
- filter
- y
- copy the clone command
- c
- compare the chosen commit with another (or shift-click both)
- ?
- show or hide this list