Make sure that generated JS does not use JS's reserved words as variables

This commit is contained in:
Evan Czaplicki 2013-08-24 15:00:23 -07:00
parent 60e90c0f95
commit 40ea6df24b
2 changed files with 25 additions and 18 deletions

View file

@ -3,6 +3,7 @@ module Parse.Declaration where
import Control.Applicative ((<$>), (<*>))
import qualified Data.List as List
import qualified Data.Set as Set
import Text.Parsec hiding (newline,spaces)
import Text.Parsec.Indent
import qualified Text.Pandoc as Pan
@ -94,24 +95,10 @@ importEvent = do
jsVar :: IParser String
jsVar = betwixt '"' '"' $ do
v <- (:) <$> (letter <|> char '_') <*> many (alphaNum <|> char '_')
if v `notElem` jsReserveds then return v else
if Set.notMember v jsReserveds then return v else
error $ "'" ++ v ++
"' is not a good name for a importing or exporting JS values."
jsReserveds :: [String]
jsReserveds =
[ "null", "undefined", "Nan", "Infinity", "true", "false", "eval"
, "arguments", "int", "byte", "char", "goto", "long", "final", "float"
, "short", "double", "native", "throws", "boolean", "abstract", "volatile"
, "transient", "synchronized", "function", "break", "case", "catch"
, "continue", "debugger", "default", "delete", "do", "else", "finally"
, "for", "function", "if", "in", "instanceof", "new", "return", "switch"
, "this", "throw", "try", "typeof", "var", "void", "while", "with", "class"
, "const", "enum", "export", "extends", "import", "super", "implements"
, "interface", "let", "package", "private", "protected", "public"
, "static", "yield"
]
isExportable tipe =
case tipe of
T.Lambda _ _ ->

View file

@ -4,6 +4,7 @@ import Control.Applicative ((<$>),(<*>))
import Control.Monad
import Control.Monad.State
import Data.Char (isUpper)
import qualified Data.Set as Set
import SourceSyntax.Helpers as Help
import SourceSyntax.Location as Location
import SourceSyntax.Expression
@ -18,6 +19,20 @@ reserveds = [ "if", "then", "else"
, "import", "as", "hiding", "open"
, "export", "foreign" ]
jsReserveds :: Set.Set String
jsReserveds = Set.fromList
[ "null", "undefined", "Nan", "Infinity", "true", "false", "eval"
, "arguments", "int", "byte", "char", "goto", "long", "final", "float"
, "short", "double", "native", "throws", "boolean", "abstract", "volatile"
, "transient", "synchronized", "function", "break", "case", "catch"
, "continue", "debugger", "default", "delete", "do", "else", "finally"
, "for", "function", "if", "in", "instanceof", "new", "return", "switch"
, "this", "throw", "try", "typeof", "var", "void", "while", "with", "class"
, "const", "enum", "export", "extends", "import", "super", "implements"
, "interface", "let", "package", "private", "protected", "public"
, "static", "yield"
]
expecting = flip (<?>)
type IParser a = ParsecT String () (State SourcePos) a
@ -49,13 +64,18 @@ rLabel = lowVar
innerVarChar :: IParser Char
innerVarChar = alphaNum <|> char '_' <|> char '\'' <?> ""
deprime :: String -> String
deprime = map (\c -> if c == '\'' then '$' else c)
makeSafe :: String -> String
makeSafe = dereserve . deprime
where
deprime = map (\c -> if c == '\'' then '$' else c)
dereserve x = case Set.member x jsReserveds of
False -> x
True -> "$" ++ x
makeVar :: IParser Char -> IParser String
makeVar p = do v <- (:) <$> p <*> many innerVarChar
guard (v `notElem` reserveds)
return (deprime v)
return (makeSafe v)
reserved :: String -> IParser String
reserved word =