language-javascript 0.6.0.12 → 0.6.0.13
raw patch · 12 files changed
+140/−66 lines, 12 files
Files
- ChangeLog.md +7/−0
- language-javascript.cabal +2/−2
- src/Language/JavaScript/Parser/AST.hs +33/−17
- src/Language/JavaScript/Parser/Grammar7.y +40/−20
- src/Language/JavaScript/Parser/Lexer.x +2/−2
- src/Language/JavaScript/Parser/Token.hs +1/−1
- src/Language/JavaScript/Pretty/Printer.hs +16/−10
- src/Language/JavaScript/Process/Minify.hs +16/−10
- test/Test/Language/Javascript/ExpressionParser.hs +1/−0
- test/Test/Language/Javascript/Minify.hs +3/−0
- test/Test/Language/Javascript/ModuleParser.hs +15/−4
- test/Test/Language/Javascript/RoundTrip.hs +4/−0
ChangeLog.md view
@@ -1,5 +1,12 @@ # ChangeLog for `language-javascript` +## 0.6.0.13 -- 2019-06-17+++ Add support for (Cyril Sobierajewicz):+ - Unparenthesized arrow functions of one parameter+ - Export from declarations+ - Add back support for identifiers named `as`+ ## 0.6.0.12 -- 2019-05-03 + Add support for for..of and friends (Franco Bulgarelli)
language-javascript.cabal view
@@ -1,5 +1,5 @@ Name: language-javascript-Version: 0.6.0.12+Version: 0.6.0.13 Synopsis: Parser for JavaScript Description: Parses Javascript into an Abstract Syntax Tree (AST). Initially intended as frontend to hjsmin. .@@ -10,7 +10,7 @@ Author: Alan Zimmerman Maintainer: Erik de Castro Lopo <erikd@mega-nerd.com> Copyright: (c) 2010-2015 Alan Zimmerman- (c) 2015-2018 Erik de Castro Lopo+ (c) 2015-2019 Erik de Castro Lopo (c) 2018 Daniel Gasienica Category: Language Build-type: Simple
src/Language/JavaScript/Parser/AST.hs view
@@ -22,6 +22,7 @@ , JSArrayElement (..) , JSCommaList (..) , JSCommaTrailingList (..)+ , JSArrowParameterList (..) -- Modules , JSModuleItem (..)@@ -32,7 +33,8 @@ , JSImportsNamed (..) , JSImportSpecifier (..) , JSExportDeclaration (..)- , JSExportLocalSpecifier (..)+ , JSExportClause (..)+ , JSExportSpecifier (..) , binOpEq , showStripped@@ -87,7 +89,7 @@ -- | Import namespace, e.g. '* as whatever' data JSImportNameSpace- = JSImportNameSpace !JSBinOp !JSBinOp !JSIdent -- ^ *, as, ident+ = JSImportNameSpace !JSBinOp !JSAnnot !JSIdent -- ^ *, as, ident deriving (Data, Eq, Show, Typeable) -- | Named imports, e.g. '{ foo, bar, baz as quux }'@@ -100,22 +102,26 @@ -- grammar is slightly different (e.g. in handling of reserved words). data JSImportSpecifier = JSImportSpecifier !JSIdent -- ^ident- | JSImportSpecifierAs !JSIdent !JSBinOp !JSIdent -- ^ident, as, ident+ | JSImportSpecifierAs !JSIdent !JSAnnot !JSIdent -- ^ident, as, ident deriving (Data, Eq, Show, Typeable) data JSExportDeclaration -- = JSExportAllFrom- -- | JSExportFrom- = JSExportLocals !JSAnnot !(JSCommaList JSExportLocalSpecifier) !JSAnnot !JSSemi -- ^lb, specifiers, rb, autosemi+ = JSExportFrom JSExportClause JSFromClause !JSSemi -- ^exports, module, semi+ | JSExportLocals JSExportClause !JSSemi -- ^exports, autosemi | JSExport !JSStatement !JSSemi -- ^body, autosemi -- | JSExportDefault deriving (Data, Eq, Show, Typeable) -data JSExportLocalSpecifier- = JSExportLocalSpecifier !JSIdent -- ^ident- | JSExportLocalSpecifierAs !JSIdent !JSBinOp !JSIdent -- ^ident1, as, ident2+data JSExportClause+ = JSExportClause !JSAnnot !(JSCommaList JSExportSpecifier) !JSAnnot -- ^lb, specifiers, rb deriving (Data, Eq, Show, Typeable) +data JSExportSpecifier+ = JSExportSpecifier !JSIdent -- ^ident+ | JSExportSpecifierAs !JSIdent !JSAnnot !JSIdent -- ^ident1, as, ident2+ deriving (Data, Eq, Show, Typeable)+ data JSStatement = JSStatementBlock !JSAnnot ![JSStatement] !JSAnnot !JSSemi -- ^lbrace, stmts, rbrace, autosemi | JSBreak !JSAnnot !JSIdent !JSSemi -- ^break,optional identifier, autosemi@@ -170,7 +176,7 @@ | JSExpressionParen !JSAnnot !JSExpression !JSAnnot -- ^lb,expression,rb | JSExpressionPostfix !JSExpression !JSUnaryOp -- ^expression, operator | JSExpressionTernary !JSExpression !JSAnnot !JSExpression !JSAnnot !JSExpression -- ^cond, ?, trueval, :, falseval- | JSArrowExpression !JSAnnot !(JSCommaList JSIdent) !JSAnnot !JSAnnot !JSStatement -- ^parameter list,arrow,block`+ | JSArrowExpression !JSArrowParameterList !JSAnnot !JSStatement -- ^parameter list,arrow,block` | JSFunctionExpression !JSAnnot !JSIdent !JSAnnot !(JSCommaList JSIdent) !JSAnnot !JSBlock -- ^fn,name,lb, parameter list,rb,block` | JSMemberDot !JSExpression !JSAnnot !JSExpression -- ^firstpart, dot, name | JSMemberExpression !JSExpression !JSAnnot !(JSCommaList JSExpression) !JSAnnot -- expr, lb, args, rb@@ -183,9 +189,13 @@ | JSVarInitExpression !JSExpression !JSVarInitializer -- ^identifier, initializer deriving (Data, Eq, Show, Typeable) +data JSArrowParameterList+ = JSUnparenthesizedArrowParameter !JSIdent+ | JSParenthesizedArrowParameterList !JSAnnot !(JSCommaList JSIdent) !JSAnnot+ deriving (Data, Eq, Show, Typeable)+ data JSBinOp = JSBinOpAnd !JSAnnot- | JSBinOpAs !JSAnnot | JSBinOpBitAnd !JSAnnot | JSBinOpBitOr !JSAnnot | JSBinOpBitXor !JSAnnot@@ -369,7 +379,7 @@ ss (JSExpressionParen _lp x _rp) = "JSExpressionParen (" ++ ss x ++ ")" ss (JSExpressionPostfix xs op) = "JSExpressionPostfix (" ++ ss op ++ "," ++ ss xs ++ ")" ss (JSExpressionTernary x1 _q x2 _c x3) = "JSExpressionTernary (" ++ ss x1 ++ "," ++ ss x2 ++ "," ++ ss x3 ++ ")"- ss (JSArrowExpression _ n _ _ e) = "JSArrowExpression (" ++ ss n ++ ") => " ++ ss e+ ss (JSArrowExpression ps _ e) = "JSArrowExpression (" ++ ss ps ++ ") => " ++ ss e ss (JSFunctionExpression _ n _lb pl _rb x3) = "JSFunctionExpression " ++ ssid n ++ " " ++ ss pl ++ " (" ++ ss x3 ++ "))" ss (JSHexInteger _ s) = "JSHexInteger " ++ singleQuote s ss (JSOctal _ s) = "JSOctal " ++ singleQuote s@@ -388,6 +398,10 @@ ss (JSVarInitExpression x1 x2) = "JSVarInitExpression (" ++ ss x1 ++ ") " ++ ss x2 ss (JSSpreadExpression _ x1) = "JSSpreadExpression (" ++ ss x1 ++ ")" +instance ShowStripped JSArrowParameterList where+ ss (JSUnparenthesizedArrowParameter x) = ss x+ ss (JSParenthesizedArrowParameterList _ xs _) = ss xs+ instance ShowStripped JSModuleItem where ss (JSModuleExportDeclaration _ x1) = "JSModuleExportDeclaration (" ++ ss x1 ++ ")" ss (JSModuleImportDeclaration _ x1) = "JSModuleImportDeclaration (" ++ ss x1 ++ ")"@@ -417,13 +431,17 @@ ss (JSImportSpecifierAs x1 _ x2) = "JSImportSpecifierAs (" ++ ss x1 ++ "," ++ ss x2 ++ ")" instance ShowStripped JSExportDeclaration where- ss (JSExportLocals _ xs _ _) = "JSExportLocals (" ++ ss xs ++ ")"+ ss (JSExportFrom xs from _) = "JSExportFrom (" ++ ss xs ++ "," ++ ss from ++ ")"+ ss (JSExportLocals xs _) = "JSExportLocals (" ++ ss xs ++ ")" ss (JSExport x1 _) = "JSExport (" ++ ss x1 ++ ")" -instance ShowStripped JSExportLocalSpecifier where- ss (JSExportLocalSpecifier x1) = "JSExportLocalSpecifier (" ++ ss x1 ++ ")"- ss (JSExportLocalSpecifierAs x1 _ x2) = "JSExportLocalSpecifierAs (" ++ ss x1 ++ "," ++ ss x2 ++ ")"+instance ShowStripped JSExportClause where+ ss (JSExportClause _ xs _) = "JSExportClause (" ++ ss xs ++ ")" +instance ShowStripped JSExportSpecifier where+ ss (JSExportSpecifier x1) = "JSExportSpecifier (" ++ ss x1 ++ ")"+ ss (JSExportSpecifierAs x1 _ x2) = "JSExportSpecifierAs (" ++ ss x1 ++ "," ++ ss x2 ++ ")"+ instance ShowStripped JSTryCatch where ss (JSCatch _ _lb x1 _rb x3) = "JSCatch (" ++ ss x1 ++ "," ++ ss x3 ++ ")" ss (JSCatchIf _ _lb x1 _ ex _rb x3) = "JSCatch (" ++ ss x1 ++ ") if " ++ ss ex ++ " (" ++ ss x3 ++ ")"@@ -458,7 +476,6 @@ instance ShowStripped JSBinOp where ss (JSBinOpAnd _) = "'&&'"- ss (JSBinOpAs _) = "'as'" ss (JSBinOpBitAnd _) = "'&'" ss (JSBinOpBitOr _) = "'|'" ss (JSBinOpBitXor _) = "'^'"@@ -555,7 +572,6 @@ deAnnot :: JSBinOp -> JSBinOp deAnnot (JSBinOpAnd _) = JSBinOpAnd JSNoAnnot-deAnnot (JSBinOpAs _) = JSBinOpAs JSNoAnnot deAnnot (JSBinOpBitAnd _) = JSBinOpBitAnd JSNoAnnot deAnnot (JSBinOpBitOr _) = JSBinOpBitOr JSNoAnnot deAnnot (JSBinOpBitXor _) = JSBinOpBitXor JSNoAnnot
src/Language/JavaScript/Parser/Grammar7.y view
@@ -194,6 +194,9 @@ Dot :: { AST.JSAnnot } Dot : '.' { mkJSAnnot $1 } +As :: { AST.JSAnnot }+As : 'as' { mkJSAnnot $1 }+ Increment :: { AST.JSUnaryOp } Increment : '++' { AST.JSUnaryOpIncr (mkJSAnnot $1) } @@ -251,9 +254,6 @@ Gt :: { AST.JSBinOp } Gt : '>' { AST.JSBinOpGt (mkJSAnnot $1) } -As :: { AST.JSBinOp }-As : 'as' { AST.JSBinOpAs (mkJSAnnot $1) }- In :: { AST.JSBinOp } In : 'in' { AST.JSBinOpIn (mkJSAnnot $1) } @@ -442,6 +442,7 @@ -- IdentifierName IdentifierPart Identifier :: { AST.JSExpression } Identifier : 'ident' { AST.JSIdentifier (mkJSAnnot $1) (tokenLiteral $1) }+ | 'as' { AST.JSIdentifier (mkJSAnnot $1) "as" } | 'get' { AST.JSIdentifier (mkJSAnnot $1) "get" } | 'set' { AST.JSIdentifier (mkJSAnnot $1) "set" } | 'from' { AST.JSIdentifier (mkJSAnnot $1) "from" }@@ -1136,11 +1137,17 @@ | NamedFunctionExpression { $1 {- 'FunctionExpression2' -} } ArrowFunctionExpression :: { AST.JSExpression }-ArrowFunctionExpression : LParen RParen Arrow StatementOrBlock- { AST.JSArrowExpression $1 AST.JSLNil $2 $3 $4 {- 'ArrowFunctionExpression1' -} }- | LParen FormalParameterList RParen Arrow StatementOrBlock- { AST.JSArrowExpression $1 $2 $3 $4 $5 {- 'ArrowFunctionExpression3' -} }+ArrowFunctionExpression : ArrowParameterList Arrow StatementOrBlock+ { AST.JSArrowExpression $1 $2 $3 } +ArrowParameterList :: { AST.JSArrowParameterList }+ArrowParameterList : Identifier+ { AST.JSUnparenthesizedArrowParameter (identName $1) }+ | LParen RParen+ { AST.JSParenthesizedArrowParameterList $1 AST.JSLNil $2 }+ | LParen FormalParameterList RParen+ { AST.JSParenthesizedArrowParameterList $1 $2 $3 }+ StatementOrBlock :: { AST.JSStatement } StatementOrBlock : Block MaybeSemi { blockToStatement $1 $2 } | Expression MaybeSemi { expressionToStatement $1 $2 }@@ -1257,33 +1264,46 @@ -- ExportDeclaration : See 15.2.3 -- [ ] export * FromClause ;--- [ ] export ExportClause FromClause ;+-- [x] export ExportClause FromClause ; -- [x] export ExportClause ; -- [x] export VariableStatement -- [ ] export Declaration+-- [ ] Declaration :+-- [ ] HoistableDeclaration+-- [ ] ClassDeclaration+-- [x] LexicalDeclaration+-- [ ] HoistableDeclaration :+-- [x] FunctionDeclaration+-- [ ] GeneratorDeclaration+-- [ ] AsyncFunctionDeclaration+-- [ ] AsyncGeneratorDeclaration -- [ ] export default HoistableDeclaration[Default] -- [ ] export default ClassDeclaration[Default] -- [ ] export default [lookahead ∉ { function, class }] AssignmentExpression[In] ; ExportDeclaration :: { AST.JSExportDeclaration }-ExportDeclaration : ExportClause AutoSemi- { $1 {- 'ExportDeclaration1' -} }+ExportDeclaration : ExportClause FromClause AutoSemi+ { AST.JSExportFrom $1 $2 $3 {- 'ExportDeclaration1' -} }+ | ExportClause AutoSemi+ { AST.JSExportLocals $1 $2 {- 'ExportDeclaration2' -} } | VariableStatement AutoSemi- { AST.JSExport $1 $2 {- 'ExportDeclaration2' -} }+ { AST.JSExport $1 $2 {- 'ExportDeclaration3' -} }+ | FunctionDeclaration AutoSemi+ { AST.JSExport $1 $2 {- 'ExportDeclaration4' -} } -- ExportClause : -- { } -- { ExportsList } -- { ExportsList , }-ExportClause :: { AST.JSExportDeclaration }-ExportClause : LBrace RBrace AutoSemi- { AST.JSExportLocals $1 AST.JSLNil $2 $3 {- 'ExportClause1' -} }- | LBrace ExportsList RBrace AutoSemi- { AST.JSExportLocals $1 $2 $3 $4 {- 'ExportClause2' -} }+ExportClause :: { AST.JSExportClause }+ExportClause : LBrace RBrace+ { AST.JSExportClause $1 AST.JSLNil $2 {- 'ExportClause1' -} }+ | LBrace ExportsList RBrace+ { AST.JSExportClause $1 $2 $3 {- 'ExportClause2' -} } -- ExportsList : -- ExportSpecifier -- ExportsList , ExportSpecifier-ExportsList :: { AST.JSCommaList AST.JSExportLocalSpecifier }+ExportsList :: { AST.JSCommaList AST.JSExportSpecifier } ExportsList : ExportSpecifier { AST.JSLOne $1 {- 'ExportsList1' -} } | ExportsList Comma ExportSpecifier@@ -1292,11 +1312,11 @@ -- ExportSpecifier : -- IdentifierName -- IdentifierName as IdentifierName-ExportSpecifier :: { AST.JSExportLocalSpecifier }+ExportSpecifier :: { AST.JSExportSpecifier } ExportSpecifier : IdentifierName- { AST.JSExportLocalSpecifier (identName $1) {- 'ExportSpecifier1' -} }+ { AST.JSExportSpecifier (identName $1) {- 'ExportSpecifier1' -} } | IdentifierName As IdentifierName- { AST.JSExportLocalSpecifierAs (identName $1) $2 (identName $3) {- 'ExportSpecifier2' -} }+ { AST.JSExportSpecifierAs (identName $1) $2 (identName $3) {- 'ExportSpecifier2' -} } -- For debugging/other entry points LiteralMain :: { AST.JSAST }
src/Language/JavaScript/Parser/Lexer.x view
@@ -503,8 +503,7 @@ keywordNames :: [(String, TokenPosn -> String -> [CommentAnnotation] -> Token)] keywordNames =- [ ( "as", AsToken )- , ( "break", BreakToken )+ [ ( "break", BreakToken ) , ( "case", CaseToken ) , ( "catch", CatchToken ) @@ -549,6 +548,7 @@ , ( "with", WithToken ) -- TODO: no idea if these are reserved or not, but they are needed -- handled in parser, in the Identifier rule+ , ( "as", AsToken ) -- not reserved , ( "get", GetToken ) , ( "set", SetToken ) {- Come from Table 6 of ECMASCRIPT 5.1, Attributes of a Named Accessor Property
src/Language/JavaScript/Parser/Token.hs view
@@ -56,7 +56,6 @@ -- ^ Literal: Regular Expression -- Keywords- | AsToken { tokenSpan :: !TokenPosn, tokenLiteral :: !String, tokenComment :: ![CommentAnnotation] } | BreakToken { tokenSpan :: !TokenPosn, tokenLiteral :: !String, tokenComment :: ![CommentAnnotation] } | CaseToken { tokenSpan :: !TokenPosn, tokenLiteral :: !String, tokenComment :: ![CommentAnnotation] } | CatchToken { tokenSpan :: !TokenPosn, tokenLiteral :: !String, tokenComment :: ![CommentAnnotation] }@@ -155,6 +154,7 @@ | CondcommentEndToken { tokenSpan :: !TokenPosn, tokenComment :: ![CommentAnnotation] } -- Special cases+ | AsToken { tokenSpan :: !TokenPosn, tokenLiteral :: !String, tokenComment :: ![CommentAnnotation] } | TailToken { tokenSpan :: !TokenPosn, tokenComment :: ![CommentAnnotation] } -- ^ Stuff between last JS and EOF | EOFToken { tokenSpan :: !TokenPosn, tokenComment :: ![CommentAnnotation] } -- ^ End of file deriving (Eq, Show, Typeable)
src/Language/JavaScript/Pretty/Printer.hs view
@@ -72,7 +72,7 @@ -- Non-Terminals (|>) pacc (JSArrayLiteral als xs ars) = pacc |> als |> "[" |> xs |> ars |> "]"- (|>) pacc (JSArrowExpression lp xs rp a x) = pacc |> lp |> "(" |> xs |> rp |> ")" |> a |> "=>" |> x+ (|>) pacc (JSArrowExpression xs a x) = pacc |> xs |> a |> "=>" |> x (|>) pacc (JSAssignExpression lhs op rhs) = pacc |> lhs |> op |> rhs (|>) pacc (JSCallExpression ex lb xs rb) = pacc |> ex |> lb |> "(" |> xs |> rb |> ")" (|>) pacc (JSCallExpressionDot ex os xs) = pacc |> ex |> os |> "." |> xs@@ -93,6 +93,9 @@ (|>) pacc (JSVarInitExpression x1 x2) = pacc |> x1 |> x2 (|>) pacc (JSSpreadExpression a e) = pacc |> a |> "..." |> e +instance RenderJS JSArrowParameterList where+ (|>) pacc (JSUnparenthesizedArrowParameter p) = pacc |> p+ (|>) pacc (JSParenthesizedArrowParameterList lb ps rb) = pacc |> lb |> "(" |> ps |> ")" |> rb -- ----------------------------------------------------------------------------- -- Need an instance of RenderJS for every component of every JSExpression or JSAnnot -- constuctor.@@ -139,7 +142,6 @@ instance RenderJS JSBinOp where (|>) pacc (JSBinOpAnd annot) = pacc |> annot |> "&&"- (|>) pacc (JSBinOpAs annot) = pacc |> annot |> "as" (|>) pacc (JSBinOpBitAnd annot) = pacc |> annot |> "&" (|>) pacc (JSBinOpBitOr annot) = pacc |> annot |> "|" (|>) pacc (JSBinOpBitXor annot) = pacc |> annot |> "^"@@ -295,23 +297,27 @@ (|>) pacc (JSFromClause from annot m) = pacc |> from |> "from" |> annot |> m instance RenderJS JSImportNameSpace where- (|>) pacc (JSImportNameSpace star as x) = pacc |> star |> as |> x+ (|>) pacc (JSImportNameSpace star annot x) = pacc |> star |> annot |> "as" |> x instance RenderJS JSImportsNamed where (|>) pacc (JSImportsNamed lb xs rb) = pacc |> lb |> "{" |> xs |> rb |> "}" instance RenderJS JSImportSpecifier where (|>) pacc (JSImportSpecifier x1) = pacc |> x1- (|>) pacc (JSImportSpecifierAs x1 as x2) = pacc |> x1 |> as |> x2+ (|>) pacc (JSImportSpecifierAs x1 annot x2) = pacc |> x1 |> annot |> "as" |> x2 instance RenderJS JSExportDeclaration where- (|>) pacc (JSExport x1 s) = pacc |> " " |> x1 |> s- (|>) pacc (JSExportLocals alb JSLNil arb semi) = pacc |> alb |> "{" |> arb |> "}" |> semi- (|>) pacc (JSExportLocals alb s arb semi) = pacc |> alb |> "{" |> s |> arb |> "}" |> semi+ (|>) pacc (JSExport x1 s) = pacc |> x1 |> s+ (|>) pacc (JSExportLocals xs semi) = pacc |> xs |> semi+ (|>) pacc (JSExportFrom xs from semi) = pacc |> xs |> from |> semi -instance RenderJS JSExportLocalSpecifier where- (|>) pacc (JSExportLocalSpecifier i) = pacc |> i- (|>) pacc (JSExportLocalSpecifierAs x1 as x2) = pacc |> x1 |> as |> x2+instance RenderJS JSExportClause where+ (|>) pacc (JSExportClause alb JSLNil arb) = pacc |> alb |> "{" |> arb |> "}"+ (|>) pacc (JSExportClause alb s arb) = pacc |> alb |> "{" |> s |> arb |> "}"++instance RenderJS JSExportSpecifier where+ (|>) pacc (JSExportSpecifier i) = pacc |> i+ (|>) pacc (JSExportSpecifierAs x1 annot x2) = pacc |> x1 |> annot |> "as" |> x2 instance RenderJS a => RenderJS (JSCommaList a) where (|>) pacc (JSLCons pl a i) = pacc |> pl |> a |> "," |> i
src/Language/JavaScript/Process/Minify.hs view
@@ -148,7 +148,7 @@ -- Non-Terminals fix _ (JSArrayLiteral _ xs _) = JSArrayLiteral emptyAnnot (map fixEmpty xs) emptyAnnot- fix _ (JSArrowExpression _ ps _ _ ss) = JSArrowExpression emptyAnnot (fixEmpty ps) emptyAnnot emptyAnnot (fixStmt emptyAnnot noSemi ss)+ fix a (JSArrowExpression ps _ ss) = JSArrowExpression (fix a ps) emptyAnnot (fixStmt emptyAnnot noSemi ss) fix a (JSAssignExpression lhs op rhs) = JSAssignExpression (fix a lhs) (fixEmpty op) (fixEmpty rhs) fix a (JSCallExpression ex _ xs _) = JSCallExpression (fix a ex) emptyAnnot (fixEmpty xs) emptyAnnot fix a (JSCallExpressionDot ex _ xs) = JSCallExpressionDot (fix a ex) emptyAnnot (fixEmpty xs)@@ -169,6 +169,9 @@ fix a (JSVarInitExpression x1 x2) = JSVarInitExpression (fix a x1) (fixEmpty x2) fix a (JSSpreadExpression _ e) = JSSpreadExpression a (fixEmpty e) +instance MinifyJS JSArrowParameterList where+ fix _ (JSUnparenthesizedArrowParameter p) = JSUnparenthesizedArrowParameter (fixEmpty p)+ fix _ (JSParenthesizedArrowParameterList _ ps _) = JSParenthesizedArrowParameterList emptyAnnot (fixEmpty ps) emptyAnnot fixVarList :: JSCommaList JSExpression -> JSCommaList JSExpression fixVarList (JSLCons h _ v) = JSLCons (fixVarList h) emptyAnnot (fixEmpty v)@@ -215,7 +218,6 @@ instance MinifyJS JSBinOp where fix _ (JSBinOpAnd _) = JSBinOpAnd emptyAnnot- fix a (JSBinOpAs _) = JSBinOpAs a fix _ (JSBinOpBitAnd _) = JSBinOpBitAnd emptyAnnot fix _ (JSBinOpBitOr _) = JSBinOpBitOr emptyAnnot fix _ (JSBinOpBitXor _) = JSBinOpBitXor emptyAnnot@@ -299,22 +301,26 @@ fix a (JSFromClause _ _ m) = JSFromClause a emptyAnnot m instance MinifyJS JSImportNameSpace where- fix a (JSImportNameSpace _ _ ident) = JSImportNameSpace (JSBinOpTimes a) (JSBinOpAs spaceAnnot) (fixSpace ident)+ fix a (JSImportNameSpace _ _ ident) = JSImportNameSpace (JSBinOpTimes a) spaceAnnot (fixSpace ident) instance MinifyJS JSImportsNamed where- fix _ (JSImportsNamed _ imps _) = JSImportsNamed emptyAnnot (fixEmpty imps) emptyAnnot + fix _ (JSImportsNamed _ imps _) = JSImportsNamed emptyAnnot (fixEmpty imps) emptyAnnot instance MinifyJS JSImportSpecifier where fix _ (JSImportSpecifier x1) = JSImportSpecifier (fixEmpty x1)- fix _ (JSImportSpecifierAs x1 as x2) = JSImportSpecifierAs (fixEmpty x1) (fixSpace as) (fixSpace x2)+ fix _ (JSImportSpecifierAs x1 _ x2) = JSImportSpecifierAs (fixEmpty x1) spaceAnnot (fixSpace x2) instance MinifyJS JSExportDeclaration where- fix _ (JSExportLocals _ x1 _ _) = JSExportLocals emptyAnnot (fixEmpty x1) emptyAnnot noSemi- fix _ (JSExport x1 _) = JSExport (fixStmt emptyAnnot noSemi x1) noSemi+ fix a (JSExportFrom x1 from _) = JSExportFrom (fix a x1) (fix a from) noSemi+ fix _ (JSExportLocals x1 _) = JSExportLocals (fix emptyAnnot x1) noSemi+ fix _ (JSExport x1 _) = JSExport (fixStmt spaceAnnot noSemi x1) noSemi -instance MinifyJS JSExportLocalSpecifier where- fix _ (JSExportLocalSpecifier x1) = JSExportLocalSpecifier (fixEmpty x1)- fix _ (JSExportLocalSpecifierAs x1 as x2) = JSExportLocalSpecifierAs (fixEmpty x1) (fixSpace as) (fixSpace x2)+instance MinifyJS JSExportClause where+ fix a (JSExportClause _ x1 _) = JSExportClause emptyAnnot (fixEmpty x1) a++instance MinifyJS JSExportSpecifier where+ fix _ (JSExportSpecifier x1) = JSExportSpecifier (fixEmpty x1)+ fix _ (JSExportSpecifierAs x1 _ x2) = JSExportSpecifierAs (fixEmpty x1) spaceAnnot (fixSpace x2) instance MinifyJS JSTryCatch where fix a (JSCatch _ _ x1 _ x3) = JSCatch a emptyAnnot (fixEmpty x1) emptyAnnot (fixEmpty x3)
test/Test/Language/Javascript/ExpressionParser.hs view
@@ -123,6 +123,7 @@ testExpr "function(){}" `shouldBe` "Right (JSAstExpression (JSFunctionExpression '' () (JSBlock []))))" testExpr "function(a){}" `shouldBe` "Right (JSAstExpression (JSFunctionExpression '' (JSIdentifier 'a') (JSBlock []))))" testExpr "function(a,b){}" `shouldBe` "Right (JSAstExpression (JSFunctionExpression '' (JSIdentifier 'a',JSIdentifier 'b') (JSBlock []))))"+ testExpr "a => {}" `shouldBe` "Right (JSAstExpression (JSArrowExpression (JSIdentifier 'a') => JSStatementBlock []))" testExpr "(a) => { a + 2 }" `shouldBe` "Right (JSAstExpression (JSArrowExpression ((JSIdentifier 'a')) => JSStatementBlock [JSExpressionBinary ('+',JSIdentifier 'a',JSDecimal '2')]))" testExpr "(a, b) => {}" `shouldBe` "Right (JSAstExpression (JSArrowExpression ((JSIdentifier 'a',JSIdentifier 'b')) => JSStatementBlock []))" testExpr "(a, b) => a + b" `shouldBe` "Right (JSAstExpression (JSArrowExpression ((JSIdentifier 'a',JSIdentifier 'b')) => JSExpressionBinary ('+',JSIdentifier 'a',JSIdentifier 'b')))"
test/Test/Language/Javascript/Minify.hs view
@@ -106,6 +106,7 @@ minifyExpr " function ( a ) { } " `shouldBe` "function(a){}" minifyExpr " function ( a , b ) { return a + b ; } " `shouldBe` "function(a,b){return a+b}" + minifyExpr "a => {}" `shouldBe` "a=>{}" minifyExpr "(a) => {}" `shouldBe` "(a)=>{}" minifyExpr "( a ) => { a + 2 }" `shouldBe` "(a)=>a+2" minifyExpr "(a, b) => a + b" `shouldBe` "(a,b)=>a+b"@@ -272,7 +273,9 @@ minifyModule " export { a } ; " `shouldBe` "export{a}" minifyModule " export { a, b } ; " `shouldBe` "export{a,b}" minifyModule " export { a, b as c , d } ; " `shouldBe` "export{a,b as c,d}"+ minifyModule " export { } from \"mod\" ; " `shouldBe` "export{}from\"mod\"" minifyModule " export const a = 1 ; " `shouldBe` "export const a=1"+ minifyModule " export function f () { } ; " `shouldBe` "export function f(){}" -- ----------------------------------------------------------------------------- -- Minify test helpers.
test/Test/Language/Javascript/ModuleParser.hs view
@@ -9,6 +9,11 @@ testModuleParser :: Spec testModuleParser = describe "Parse modules:" $ do+ it "as" $+ test "as"+ `shouldBe`+ "Right (JSAstModule [JSModuleStatementListItem (JSIdentifier 'as')])"+ it "import" $ do -- Not yet supported -- test "import 'a';" `shouldBe` ""@@ -35,19 +40,25 @@ it "export" $ do test "export {}" `shouldBe`- "Right (JSAstModule [JSModuleExportDeclaration (JSExportLocals (()))])"+ "Right (JSAstModule [JSModuleExportDeclaration (JSExportLocals (JSExportClause (())))])" test "export {};" `shouldBe`- "Right (JSAstModule [JSModuleExportDeclaration (JSExportLocals (()))])"+ "Right (JSAstModule [JSModuleExportDeclaration (JSExportLocals (JSExportClause (())))])" test "export const a = 1;" `shouldBe` "Right (JSAstModule [JSModuleExportDeclaration (JSExport (JSConstant (JSVarInitExpression (JSIdentifier 'a') [JSDecimal '1'])))])"+ test "export function f() {};"+ `shouldBe`+ "Right (JSAstModule [JSModuleExportDeclaration (JSExport (JSFunction 'f' () (JSBlock [])))])" test "export { a };" `shouldBe`- "Right (JSAstModule [JSModuleExportDeclaration (JSExportLocals ((JSExportLocalSpecifier (JSIdentifier 'a'))))])"+ "Right (JSAstModule [JSModuleExportDeclaration (JSExportLocals (JSExportClause ((JSExportSpecifier (JSIdentifier 'a')))))])" test "export { a as b };" `shouldBe`- "Right (JSAstModule [JSModuleExportDeclaration (JSExportLocals ((JSExportLocalSpecifierAs (JSIdentifier 'a',JSIdentifier 'b'))))])"+ "Right (JSAstModule [JSModuleExportDeclaration (JSExportLocals (JSExportClause ((JSExportSpecifierAs (JSIdentifier 'a',JSIdentifier 'b')))))])"+ test "export {} from 'mod'"+ `shouldBe`+ "Right (JSAstModule [JSModuleExportDeclaration (JSExportFrom (JSExportClause (()),JSFromClause ''mod''))])" test :: String -> String
test/Test/Language/Javascript/RoundTrip.hs view
@@ -63,6 +63,7 @@ testRT "/*a*/x/*b*/=/*c*/{/*d*/get/*e*/ foo/*f*/(/*g*/)/*h*/ {/*i*/return/*j*/ 1/*k*/}/*l*/,/*m*/set/*n*/ foo/*o*/(/*p*/a/*q*/) /*r*/{/*s*/x/*t*/=/*u*/a/*v*/}/*w*/}" testRT "... /*a*/ x" + testRT "a => {}" testRT "(a) => { a + 2 }" testRT "(a, b) => {}" testRT "(a, b) => a + b"@@ -117,6 +118,9 @@ testRTModule " export {} ; " testRTModule "export { a , b , c };" testRTModule "export { a, X as B, c }"+ testRTModule "export {} from \"mod\";"+ testRTModule "export const a = 1 ; "+ testRTModule "export function f () { } ; " testRT :: String -> Expectation