1-----------------------------------------------------------------------------
3-- Module : Language.PureScript.Declarations
4-- Copyright : (c) Phil Freeman 2013
7-- Maintainer : Phil Freeman <paf31@cantab.net>
8-- Stability : experimental
11-- | Data types for modules and declarations
13-----------------------------------------------------------------------------
15{-# LANGUAGE DeriveDataTypeable #-}
17module Language.PureScript.Declarations where
19import Language.PureScript.Types
20import Language.PureScript.Names
21import Language.PureScript.Kinds
22import Language.PureScript.TypeClassDictionaries
23import Language.PureScript.CodeGen.JS.AST
24import Language.PureScript.Environment
26import qualified Data.Data as D
27import Data.Generics (mkQ, everything)
30-- A precedence level for an infix operator
32type Precedence = Integer
35-- Associativity for infix operators
37data Associativity = Infixl | Infixr | Infix deriving (D.Data, D.Typeable)
39instance Show Associativity where
40 show Infixl = "infixl"
41 show Infixr = "infixr"
45-- Source position information
47data SourcePos = SourcePos
55 , sourcePosLine :: Int
59 , sourcePosColumn :: Int
60 } deriving (D.Data, D.Typeable)
62instance Show SourcePos where
63 show sp = (sourceName sp) ++ " line " ++ show (sourcePosLine sp) ++ ", column " ++ show (sourcePosColumn sp)
66-- Fixity data for infix operators
68data Fixity = Fixity Associativity Precedence deriving (Show, D.Data, D.Typeable)
71-- A module declaration, consisting of a module name, a list of declarations, and a list of the
72-- declarations that are explicitly imported. If the export list is Nothing, everything is exported.
74data Module = Module ModuleName [Declaration] (Maybe [DeclarationRef]) deriving (Show, D.Data, D.Typeable)
77-- An item in a list of explicit imports or exports
81 -- A type constructor with data constructors
83 = TypeRef ProperName (Maybe [ProperName])
91 | TypeClassRef ProperName
93 -- A type class instance, created during typeclass desugaring (name, class name, instance types)
95 | TypeInstanceRef Ident
96 deriving (Show, Eq, D.Data, D.Typeable)
99-- The data type of declarations
103 -- A data type declaration (name, arguments, data constructors)
105 = DataDeclaration ProperName [String] [(ProperName, [Type])]
107 -- A minimal mutually recursive set of data type declarations
109 | DataBindingGroupDeclaration [Declaration]
111 -- A type synonym declaration (name, arguments, type)
113 | TypeSynonymDeclaration ProperName [String] Type
115 -- A type declaration for a value (name, ty)
117 | TypeDeclaration Ident Type
119 -- A value declaration (name, top-level binders, optional guard, value)
121 | ValueDeclaration Ident NameKind [Binder] (Maybe Guard) Value
123 -- A minimal mutually recursive set of value declarations
125 | BindingGroupDeclaration [(Ident, NameKind, Value)]
127 -- A foreign import declaration (type, name, optional inline Javascript, type)
129 | ExternDeclaration ForeignImportType Ident (Maybe JS) Type
131 -- A data type foreign import (name, kind)
133 | ExternDataDeclaration ProperName Kind
135 -- A type class instance foreign import
137 | ExternInstanceDeclaration Ident [(Qualified ProperName, [Type])] (Qualified ProperName) [Type]
139 -- A fixity declaration (fixity data, operator name)
141 | FixityDeclaration Fixity String
143 -- A module import (module name, optional set of identifiers to import, optional "qualified as"
146 | ImportDeclaration ModuleName (Maybe [DeclarationRef]) (Maybe ModuleName)
148 -- A type class declaration (name, argument, member declarations)
150 | TypeClassDeclaration ProperName [String] [Declaration]
152 -- A type instance declaration (name, dependencies, class name, instance types, member
155 | TypeInstanceDeclaration Ident [(Qualified ProperName, [Type])] (Qualified ProperName) [Type] [Declaration]
157 -- A declaration with source position information
159 | PositionedDeclaration SourcePos Declaration
160 deriving (Show, D.Data, D.Typeable)
163-- Test if a declaration is a value declaration
165isValueDecl :: Declaration -> Bool
166isValueDecl ValueDeclaration{} = True
167isValueDecl (PositionedDeclaration _ d) = isValueDecl d
171-- Test if a declaration is a data type or type synonym declaration
173isDataDecl :: Declaration -> Bool
174isDataDecl DataDeclaration{} = True
175isDataDecl TypeSynonymDeclaration{} = True
176isDataDecl (PositionedDeclaration _ d) = isDataDecl d
180-- Test if a declaration is a module import
182isImportDecl :: Declaration -> Bool
183isImportDecl ImportDeclaration{} = True
184isImportDecl (PositionedDeclaration _ d) = isImportDecl d
185isImportDecl _ = False
188-- Test if a declaration is a data type foreign import
190isExternDataDecl :: Declaration -> Bool
191isExternDataDecl ExternDataDeclaration{} = True
192isExternDataDecl (PositionedDeclaration _ d) = isExternDataDecl d
193isExternDataDecl _ = False
196-- Test if a declaration is a type class instance foreign import
198isExternInstanceDecl :: Declaration -> Bool
199isExternInstanceDecl ExternInstanceDeclaration{} = True
200isExternInstanceDecl (PositionedDeclaration _ d) = isExternInstanceDecl d
201isExternInstanceDecl _ = False
204-- Test if a declaration is a fixity declaration
206isFixityDecl :: Declaration -> Bool
207isFixityDecl FixityDeclaration{} = True
208isFixityDecl (PositionedDeclaration _ d) = isFixityDecl d
209isFixityDecl _ = False
212-- Test if a declaration is a foreign import
214isExternDecl :: Declaration -> Bool
215isExternDecl ExternDeclaration{} = True
216isExternDecl (PositionedDeclaration _ d) = isExternDecl d
217isExternDecl _ = False
220-- Test if a declaration is a type class or instance declaration
222isTypeClassDeclaration :: Declaration -> Bool
223isTypeClassDeclaration TypeClassDeclaration{} = True
224isTypeClassDeclaration TypeInstanceDeclaration{} = True
225isTypeClassDeclaration (PositionedDeclaration _ d) = isTypeClassDeclaration d
226isTypeClassDeclaration _ = False
229-- A guard is just a boolean-valued expression that appears alongside a set of binders
234-- Data type for values
240 = NumericLiteral (Either Integer Double)
244 | StringLiteral String
248 | BooleanLiteral Bool
250 -- A prefix -, will be desugared
254 -- Binary operator application. During the rebracketing phase of desugaring, this data constructor
257 | BinaryNoParens (Qualified Ident) Value Value
259 -- Explicit parentheses. During the rebracketing phase of desugaring, this data constructor
266 | ArrayLiteral [Value]
270 | ObjectLiteral [(String, Value)]
272 -- An record property accessor expression
274 | Accessor String Value
276 -- Partial record update
278 | ObjectUpdate Value [(String, Value)]
280 -- Function introduction
282 | Abs (Either Ident Binder) Value
284 -- Function application
290 | Var (Qualified Ident)
292 -- Conditional (if-then-else expression)
294 | IfThenElse Value Value Value
296 -- A data constructor
298 | Constructor (Qualified ProperName)
300 -- A case expression. During the case expansion phase of desugaring, top-level binders will get
301 -- desugared into case expressions, hence the need for guards and multiple binders per branch here.
303 | Case [Value] [CaseAlternative]
305 -- A value with a type annotation
307 | TypedValue Bool Value Type
311 | Let [Declaration] Value
313 -- A do-notation block
315 | Do [DoNotationElement]
317 -- A placeholder for a type class dictionary to be inserted later. At the end of type checking, these
318 -- placeholders will be replaced with actual expressions representing type classes dictionaries which
319 -- can be evaluated at runtime. The constructor arguments represent (in order): the type class name and
320 -- instance type, and the type class dictionaries in scope.
322 | TypeClassDictionary (Qualified ProperName, [Type]) [TypeClassDictionaryInScope]
324 -- A value with source position information
326 | PositionedValue SourcePos Value deriving (Show, D.Data, D.Typeable)
329-- An alternative in a case statement
331data CaseAlternative = CaseAlternative
333 -- A collection of binders with which to match the inputs
335 caseAlternativeBinders :: [Binder]
339 , caseAlternativeGuard :: Maybe Guard
341 -- The result expression
343 , caseAlternativeResult :: Value
344 } deriving (Show, D.Data, D.Typeable)
347-- Find the original dictionary which a type class dictionary in scope refers to
349canonicalizeDictionary :: TypeClassDictionaryInScope -> Qualified Ident
350canonicalizeDictionary (TypeClassDictionaryInScope { tcdType = TCDRegular, tcdName = nm }) = nm
351canonicalizeDictionary (TypeClassDictionaryInScope { tcdType = TCDAlias nm }) = nm
354-- A statement in a do-notation block
356data DoNotationElement
358 -- A monadic value without a binder
360 = DoNotationValue Value
362 -- A monadic value with a binder
364 | DoNotationBind Binder Value
366 -- A let statement, i.e. a pure value with a binder
368 | DoNotationLet Binder Value
370 -- A do notation element with source position information
372 | PositionedDoNotationElement SourcePos DoNotationElement deriving (Show, D.Data, D.Typeable)
375-- Data type for binders
383 -- A binder which matches a boolean literal
387 -- A binder which matches a string literal
389 | StringBinder String
391 -- A binder which matches a numeric literal
393 | NumberBinder (Either Integer Double)
395 -- A binder which binds an identifier
399 -- A binder which matches a data constructor
401 | ConstructorBinder (Qualified ProperName) [Binder]
403 -- A binder which matches a record and binds its properties
405 | ObjectBinder [(String, Binder)]
407 -- A binder which matches an array and binds its elements
409 | ArrayBinder [Binder]
411 -- A binder which matches an array and binds its head and tail
413 | ConsBinder Binder Binder
415 -- A binder which binds its input to an identifier
417 | NamedBinder Ident Binder
419 -- A binder with source position information
421 | PositionedBinder SourcePos Binder deriving (Show, D.Data, D.Typeable)
424-- Collect all names introduced in binders in an expression
426binderNames :: (D.Data d) => d -> [Ident]
427binderNames = everything (++) (mkQ [] go)
429 go (VarBinder ident) = [ident]
430 go (NamedBinder ident _) = [ident]
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