598 lines
21 KiB
Java
598 lines
21 KiB
Java
|
/*
|
||
|
* Copyright 2005 The Closure Compiler Authors.
|
||
|
*
|
||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||
|
* you may not use this file except in compliance with the License.
|
||
|
* You may obtain a copy of the License at
|
||
|
*
|
||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||
|
*
|
||
|
* Unless required by applicable law or agreed to in writing, software
|
||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||
|
* See the License for the specific language governing permissions and
|
||
|
* limitations under the License.
|
||
|
*/
|
||
|
|
||
|
package com.google.javascript.jscomp;
|
||
|
|
||
|
import com.google.common.base.Preconditions;
|
||
|
import com.google.common.collect.ImmutableMap;
|
||
|
import com.google.javascript.rhino.Node;
|
||
|
|
||
|
import java.util.*;
|
||
|
|
||
|
|
||
|
/**
|
||
|
* Tests for {@link RenameVars}.
|
||
|
*/
|
||
|
public class RenameVarsTest extends CompilerTestCase {
|
||
|
private static final String DEFAULT_PREFIX = "";
|
||
|
private String prefix = DEFAULT_PREFIX;
|
||
|
|
||
|
private VariableMap previouslyUsedMap =
|
||
|
new VariableMap(ImmutableMap.<String, String>of());
|
||
|
private RenameVars renameVars;
|
||
|
private boolean withClosurePass = false;
|
||
|
private boolean localRenamingOnly = false;
|
||
|
private boolean preserveFunctionExpressionNames = false;
|
||
|
private boolean useGoogleCodingConvention = true;
|
||
|
private boolean generatePseudoNames = false;
|
||
|
private boolean shouldShadow = false;
|
||
|
|
||
|
@Override
|
||
|
protected CodingConvention getCodingConvention() {
|
||
|
if (useGoogleCodingConvention) {
|
||
|
return new GoogleCodingConvention();
|
||
|
} else {
|
||
|
return CodingConventions.getDefault();
|
||
|
}
|
||
|
}
|
||
|
|
||
|
@Override
|
||
|
protected CompilerPass getProcessor(Compiler compiler) {
|
||
|
if (withClosurePass) {
|
||
|
return new ClosurePassAndRenameVars(compiler);
|
||
|
} else {
|
||
|
return renameVars = new RenameVars(compiler, prefix,
|
||
|
localRenamingOnly, preserveFunctionExpressionNames,
|
||
|
generatePseudoNames, shouldShadow,
|
||
|
previouslyUsedMap, null, null);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
@Override
|
||
|
protected int getNumRepetitions() {
|
||
|
return 1;
|
||
|
}
|
||
|
|
||
|
@Override
|
||
|
protected void setUp() throws Exception {
|
||
|
super.setUp();
|
||
|
previouslyUsedMap = new VariableMap(ImmutableMap.<String, String>of());
|
||
|
prefix = DEFAULT_PREFIX;
|
||
|
withClosurePass = false;
|
||
|
localRenamingOnly = false;
|
||
|
preserveFunctionExpressionNames = false;
|
||
|
generatePseudoNames = false;
|
||
|
shouldShadow = false;
|
||
|
|
||
|
// TODO(johnlenz): Enable Normalize during these tests.
|
||
|
}
|
||
|
|
||
|
public void testRenameSimple() {
|
||
|
test("function Foo(v1, v2) {return v1;} Foo();",
|
||
|
"function a(b, c) {return b;} a();");
|
||
|
}
|
||
|
|
||
|
public void testRenameGlobals() {
|
||
|
test("var Foo; var Bar, y; function x() { Bar++; }",
|
||
|
"var a; var b, c; function d() { b++; }");
|
||
|
}
|
||
|
|
||
|
public void testRenameLocals() {
|
||
|
test("(function (v1, v2) {}); (function (v3, v4) {});",
|
||
|
"(function (a, b) {}); (function (a, b) {});");
|
||
|
test("function f1(v1, v2) {}; function f2(v3, v4) {};",
|
||
|
"function c(a, b) {}; function d(a, b) {};");
|
||
|
}
|
||
|
|
||
|
public void testRenameRedeclaredGlobals() {
|
||
|
test("function f1(v1, v2) {f1()};" +
|
||
|
"/** @suppress {duplicate} */" +
|
||
|
"function f1(v3, v4) {f1()};",
|
||
|
"function a(b, c) {a()};" +
|
||
|
"function a(b, c) {a()};");
|
||
|
|
||
|
localRenamingOnly = true;
|
||
|
|
||
|
test("function f1(v1, v2) {f1()};" +
|
||
|
"/** @suppress {duplicate} */" +
|
||
|
"function f1(v3, v4) {f1()};",
|
||
|
"function f1(a, b) {f1()};" +
|
||
|
"function f1(a, b) {f1()};");
|
||
|
}
|
||
|
|
||
|
public void testRecursiveFunctions1() {
|
||
|
test("var walk = function walk(node, aFunction) {" +
|
||
|
" walk(node, aFunction);" +
|
||
|
"};",
|
||
|
"var a = function a(b, c) {" +
|
||
|
" a(b, c);" +
|
||
|
"};");
|
||
|
|
||
|
localRenamingOnly = true;
|
||
|
|
||
|
test("var walk = function walk(node, aFunction) {" +
|
||
|
" walk(node, aFunction);" +
|
||
|
"};",
|
||
|
"var walk = function walk(a, b) {" +
|
||
|
" walk(a, b);" +
|
||
|
"};");
|
||
|
}
|
||
|
|
||
|
public void testRecursiveFunctions2() {
|
||
|
preserveFunctionExpressionNames = true;
|
||
|
|
||
|
test("var walk = function walk(node, aFunction) {" +
|
||
|
" walk(node, aFunction);" +
|
||
|
"};",
|
||
|
"var c = function walk(a, b) {" +
|
||
|
" walk(a, b);" +
|
||
|
"};");
|
||
|
|
||
|
localRenamingOnly = true;
|
||
|
|
||
|
test("var walk = function walk(node, aFunction) {" +
|
||
|
" walk(node, aFunction);" +
|
||
|
"};",
|
||
|
"var walk = function walk(a, b) {" +
|
||
|
" walk(a, b);" +
|
||
|
"};");
|
||
|
}
|
||
|
|
||
|
public void testRenameLocalsClashingWithGlobals() {
|
||
|
test("function a(v1, v2) {return v1;} a();",
|
||
|
"function a(b, c) {return b;} a();");
|
||
|
}
|
||
|
|
||
|
public void testRenameNested() {
|
||
|
test("function f1(v1, v2) { (function(v3, v4) {}) }",
|
||
|
"function a(b, c) { (function(d, e) {}) }");
|
||
|
test("function f1(v1, v2) { function f2(v3, v4) {} }",
|
||
|
"function a(b, c) { function d(e, f) {} }");
|
||
|
}
|
||
|
|
||
|
public void testBleedingRecursiveFunctions1() {
|
||
|
// On IE, bleeding functions will interfere with each other if
|
||
|
// they are in the same scope. In the below example, we want to be
|
||
|
// sure that a and b get separate names.
|
||
|
test("var x = function a(x) { return x ? 1 : a(1); };" +
|
||
|
"var y = function b(x) { return x ? 2 : b(2); };",
|
||
|
"var c = function b(a) { return a ? 1 : b(1); };" +
|
||
|
"var e = function d(a) { return a ? 2 : d(2); };");
|
||
|
}
|
||
|
|
||
|
public void testBleedingRecursiveFunctions2() {
|
||
|
test("function f() {" +
|
||
|
" var x = function a(x) { return x ? 1 : a(1); };" +
|
||
|
" var y = function b(x) { return x ? 2 : b(2); };" +
|
||
|
"}",
|
||
|
"function d() {" +
|
||
|
" var e = function b(a) { return a ? 1 : b(1); };" +
|
||
|
" var f = function a(c) { return c ? 2 : a(2); };" +
|
||
|
"}");
|
||
|
}
|
||
|
|
||
|
public void testBleedingRecursiveFunctions3() {
|
||
|
test("function f() {" +
|
||
|
" var x = function a(x) { return x ? 1 : a(1); };" +
|
||
|
" var y = function b(x) { return x ? 2 : b(2); };" +
|
||
|
" var z = function c(x) { return x ? y : c(2); };" +
|
||
|
"}",
|
||
|
"function f() {" +
|
||
|
" var g = function c(a) { return a ? 1 : c(1); };" +
|
||
|
" var d = function a(b) { return b ? 2 : a(2); };" +
|
||
|
" var h = function b(e) { return e ? d : b(2); };" +
|
||
|
"}");
|
||
|
}
|
||
|
|
||
|
public void testRenameWithExterns1() {
|
||
|
String externs = "var foo;";
|
||
|
test(externs, "var bar; foo(bar);", "var a; foo(a);", null, null);
|
||
|
}
|
||
|
|
||
|
public void testRenameWithExterns2() {
|
||
|
String externs = "var a;";
|
||
|
test(externs, "var b = 5", "var b = 5", null, null);
|
||
|
}
|
||
|
|
||
|
public void testDoNotRenameExportedName() {
|
||
|
test("_foo()", "_foo()");
|
||
|
}
|
||
|
|
||
|
public void testRenameWithNameOverlap() {
|
||
|
test("var a = 1; var b = 2; b + b;",
|
||
|
"var a = 1; var b = 2; b + b;");
|
||
|
}
|
||
|
|
||
|
public void testRenameWithPrefix1() {
|
||
|
prefix = "PRE_";
|
||
|
test("function Foo(v1, v2) {return v1} Foo();",
|
||
|
"function PRE_(a, b) {return a} PRE_();");
|
||
|
prefix = DEFAULT_PREFIX;
|
||
|
|
||
|
}
|
||
|
|
||
|
public void testRenameWithPrefix2() {
|
||
|
prefix = "PRE_";
|
||
|
test("function Foo(v1, v2) {var v3 = v1 + v2; return v3;} Foo();",
|
||
|
"function PRE_(a, b) {var c = a + b; return c;} PRE_();");
|
||
|
prefix = DEFAULT_PREFIX;
|
||
|
}
|
||
|
|
||
|
public void testRenameWithPrefix3() {
|
||
|
prefix = "a";
|
||
|
test("function Foo() {return 1;}" +
|
||
|
"function Bar() {" +
|
||
|
" var a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z," +
|
||
|
" A,B,C,D,E,F,G,H,I,J,K,L,M,N,O,P,Q,R,S,T,U,V,W,X,Y,Z,aa,ab;" +
|
||
|
" Foo();" +
|
||
|
"} Bar();",
|
||
|
|
||
|
"function a() {return 1;}" +
|
||
|
"function aa() {" +
|
||
|
" var b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z,A," +
|
||
|
" B,C,D,E,F,G,H,I,J,K,L,M,N,O,P,Q,R,S,T,U,V,W,X,Y,Z,$,ba,ca;" +
|
||
|
" a();" +
|
||
|
"} aa();");
|
||
|
prefix = DEFAULT_PREFIX;
|
||
|
}
|
||
|
|
||
|
public void testNamingBasedOnOrderOfOccurrence() {
|
||
|
test("var q,p,m,n,l,k; " +
|
||
|
"(function (r) {}); try { } catch(s) {}; var t = q + q;",
|
||
|
"var a,b,c,d,e,f; " +
|
||
|
"(function(g) {}); try { } catch(h) {}; var i = a + a;"
|
||
|
);
|
||
|
test("(function(A,B,C,D,E,F,G,H,I,J,K,L,M,N,O,P,Q,R,S,T,U,V,W,X,Y,Z," +
|
||
|
"a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z,$){});" +
|
||
|
"var a4,a3,a2,a1,b4,b3,b2,b1,ab,ac,ad,fg;function foo(){};",
|
||
|
"(function(a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z," +
|
||
|
"A,B,C,D,E,F,G,H,I,J,K,L,M,N,O,P,Q,R,S,T,U,V,W,X,Y,Z,$){});" +
|
||
|
"var aa,ba,ca,da,ea,fa,ga,ha,ia,ja,ka,la;function ma(){};");
|
||
|
}
|
||
|
|
||
|
public void testStableRenameSimple() {
|
||
|
VariableMap expectedVariableMap = makeVariableMap(
|
||
|
"Foo", "a", "L 0", "b", "L 1", "c");
|
||
|
testRenameMap("function Foo(v1, v2) {return v1;} Foo();",
|
||
|
"function a(b, c) {return b;} a();", expectedVariableMap);
|
||
|
|
||
|
expectedVariableMap = makeVariableMap(
|
||
|
"Foo", "a", "L 0", "b", "L 1", "c", "L 2", "d");
|
||
|
testRenameMapUsingOldMap("function Foo(v1, v2, v3) {return v1;} Foo();",
|
||
|
"function a(b, c, d) {return b;} a();", expectedVariableMap);
|
||
|
}
|
||
|
|
||
|
public void testStableRenameGlobals() {
|
||
|
VariableMap expectedVariableMap = makeVariableMap(
|
||
|
"Foo", "a", "Bar", "b", "y", "c", "x", "d");
|
||
|
testRenameMap("var Foo; var Bar, y; function x() { Bar++; }",
|
||
|
"var a; var b, c; function d() { b++; }",
|
||
|
expectedVariableMap);
|
||
|
|
||
|
expectedVariableMap = makeVariableMap(
|
||
|
"Foo", "a", "Bar", "b", "y", "c", "x", "d", "Baz", "f", "L 0" , "e");
|
||
|
testRenameMapUsingOldMap(
|
||
|
"var Foo, Baz; var Bar, y; function x(R) { return R + Bar++; }",
|
||
|
"var a, f; var b, c; function d(e) { return e + b++; }",
|
||
|
expectedVariableMap);
|
||
|
}
|
||
|
|
||
|
public void testStableRenameWithPointlesslyAnonymousFunctions() {
|
||
|
VariableMap expectedVariableMap = makeVariableMap("L 0", "a", "L 1", "b");
|
||
|
testRenameMap("(function (v1, v2) {}); (function (v3, v4) {});",
|
||
|
"(function (a, b) {}); (function (a, b) {});",
|
||
|
expectedVariableMap);
|
||
|
|
||
|
expectedVariableMap = makeVariableMap("L 0", "a", "L 1", "b", "L 2", "c");
|
||
|
testRenameMapUsingOldMap("(function (v0, v1, v2) {});" +
|
||
|
"(function (v3, v4) {});",
|
||
|
"(function (a, b, c) {});" +
|
||
|
"(function (a, b) {});",
|
||
|
expectedVariableMap);
|
||
|
}
|
||
|
|
||
|
public void testStableRenameLocalsClashingWithGlobals() {
|
||
|
test("function a(v1, v2) {return v1;} a();",
|
||
|
"function a(b, c) {return b;} a();");
|
||
|
previouslyUsedMap = renameVars.getVariableMap();
|
||
|
test("function bar(){return;}function a(v1, v2) {return v1;} a();",
|
||
|
"function d(){return;}function a(b, c) {return b;} a();");
|
||
|
}
|
||
|
|
||
|
public void testStableRenameNested() {
|
||
|
VariableMap expectedVariableMap = makeVariableMap(
|
||
|
"f1", "a", "L 0", "b", "L 1", "c", "L 2", "d", "L 3", "e");
|
||
|
testRenameMap("function f1(v1, v2) { (function(v3, v4) {}) }",
|
||
|
"function a(b, c) { (function(d, e) {}) }",
|
||
|
expectedVariableMap);
|
||
|
|
||
|
expectedVariableMap = makeVariableMap(
|
||
|
"f1", "a", "L 0", "b", "L 1", "c", "L 2", "d", "L 3", "e", "L 4", "f");
|
||
|
testRenameMapUsingOldMap(
|
||
|
"function f1(v1, v2) { (function(v3, v4, v5) {}) }",
|
||
|
"function a(b, c) { (function(d, e, f) {}) }",
|
||
|
expectedVariableMap);
|
||
|
}
|
||
|
|
||
|
public void testStableRenameWithExterns1() {
|
||
|
String externs = "var foo;";
|
||
|
test(externs, "var bar; foo(bar);", "var a; foo(a);", null, null);
|
||
|
previouslyUsedMap = renameVars.getVariableMap();
|
||
|
test(externs, "var bar, baz; foo(bar, baz);",
|
||
|
"var a, b; foo(a, b);", null, null);
|
||
|
}
|
||
|
|
||
|
public void testStableRenameWithExterns2() {
|
||
|
String externs = "var a;";
|
||
|
test(externs, "var b = 5", "var b = 5", null, null);
|
||
|
previouslyUsedMap = renameVars.getVariableMap();
|
||
|
test(externs, "var b = 5, catty = 9;", "var b = 5, c=9;", null, null);
|
||
|
}
|
||
|
|
||
|
public void testStableRenameWithNameOverlap() {
|
||
|
test("var a = 1; var b = 2; b + b;",
|
||
|
"var a = 1; var b = 2; b + b;");
|
||
|
previouslyUsedMap = renameVars.getVariableMap();
|
||
|
test("var a = 1; var c, b = 2; b + b;",
|
||
|
"var a = 1; var c, b = 2; b + b;");
|
||
|
}
|
||
|
|
||
|
public void testStableRenameWithAnonymousFunctions() {
|
||
|
VariableMap expectedVariableMap = makeVariableMap("L 0", "a", "foo", "b");
|
||
|
testRenameMap("function foo(bar){return bar;}foo(function(h){return h;});",
|
||
|
"function b(a){return a}b(function(a){return a;})",
|
||
|
expectedVariableMap);
|
||
|
|
||
|
expectedVariableMap = makeVariableMap("foo", "b", "L 0", "a", "L 1", "c");
|
||
|
testRenameMapUsingOldMap(
|
||
|
"function foo(bar) {return bar;}foo(function(g,h) {return g+h;});",
|
||
|
"function b(a){return a}b(function(a,c){return a+c;})",
|
||
|
expectedVariableMap);
|
||
|
}
|
||
|
|
||
|
public void testStableRenameSimpleExternsChanges() {
|
||
|
VariableMap expectedVariableMap = makeVariableMap(
|
||
|
"Foo", "a", "L 0", "b", "L 1", "c");
|
||
|
testRenameMap("function Foo(v1, v2) {return v1;} Foo();",
|
||
|
"function a(b, c) {return b;} a();", expectedVariableMap);
|
||
|
|
||
|
expectedVariableMap = makeVariableMap("L 0", "b", "L 1", "c", "L 2", "a");
|
||
|
String externs = "var Foo;";
|
||
|
testRenameMapUsingOldMap(externs,
|
||
|
"function Foo(v1, v2, v0) {return v1;} Foo();",
|
||
|
"function Foo(b, c, a) {return b;} Foo();",
|
||
|
expectedVariableMap);
|
||
|
}
|
||
|
|
||
|
public void testStableRenameSimpleLocalNameExterned() {
|
||
|
test("function Foo(v1, v2) {return v1;} Foo();",
|
||
|
"function a(b, c) {return b;} a();");
|
||
|
|
||
|
previouslyUsedMap = renameVars.getVariableMap();
|
||
|
|
||
|
String externs = "var b;";
|
||
|
test(externs, "function Foo(v1, v2) {return v1;} Foo(b);",
|
||
|
"function a(d, c) {return d;} a(b);", null, null);
|
||
|
}
|
||
|
|
||
|
public void testStableRenameSimpleGlobalNameExterned() {
|
||
|
test("function Foo(v1, v2) {return v1;} Foo();",
|
||
|
"function a(b, c) {return b;} a();");
|
||
|
|
||
|
previouslyUsedMap = renameVars.getVariableMap();
|
||
|
|
||
|
String externs = "var Foo;";
|
||
|
test(externs, "function Foo(v1, v2, v0) {return v1;} Foo();",
|
||
|
"function Foo(b, c, a) {return b;} Foo();", null, null);
|
||
|
}
|
||
|
|
||
|
public void testStableRenameWithPrefix1AndUnstableLocalNames() {
|
||
|
prefix = "PRE_";
|
||
|
test("function Foo(v1, v2) {return v1} Foo();",
|
||
|
"function PRE_(a, b) {return a} PRE_();");
|
||
|
|
||
|
previouslyUsedMap = renameVars.getVariableMap();
|
||
|
|
||
|
prefix = "PRE_";
|
||
|
test("function Foo(v0, v1, v2) {return v1} Foo();",
|
||
|
"function PRE_(a, b, c) {return b} PRE_();");
|
||
|
}
|
||
|
|
||
|
public void testStableRenameWithPrefix2() {
|
||
|
prefix = "a";
|
||
|
test("function Foo() {return 1;}" +
|
||
|
"function Bar() {" +
|
||
|
" var a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z," +
|
||
|
" A,B,C,D,E,F,G,H,I,J,K,L,M,N,O,P,Q,R,S,T,U,V,W,X,Y,Z,aa,ab;" +
|
||
|
" Foo();" +
|
||
|
"} Bar();",
|
||
|
|
||
|
"function a() {return 1;}" +
|
||
|
"function aa() {" +
|
||
|
" var b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z,A," +
|
||
|
" B,C,D,E,F,G,H,I,J,K,L,M,N,O,P,Q,R,S,T,U,V,W,X,Y,Z,$,ba,ca;" +
|
||
|
" a();" +
|
||
|
"} aa();");
|
||
|
|
||
|
previouslyUsedMap = renameVars.getVariableMap();
|
||
|
|
||
|
prefix = "a";
|
||
|
test("function Foo() {return 1;}" +
|
||
|
"function Baz() {return 1;}" +
|
||
|
"function Bar() {" +
|
||
|
" var a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z," +
|
||
|
" A,B,C,D,E,F,G,H,I,J,K,L,M,N,O,P,Q,R,S,T,U,V,W,X,Y,Z,aa,ab;" +
|
||
|
" Foo();" +
|
||
|
"} Bar();",
|
||
|
|
||
|
"function a() {return 1;}" +
|
||
|
"function ab() {return 1;}" +
|
||
|
"function aa() {" +
|
||
|
" var b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z,A," +
|
||
|
" B,C,D,E,F,G,H,I,J,K,L,M,N,O,P,Q,R,S,T,U,V,W,X,Y,Z,$,ba,ca;" +
|
||
|
" a();" +
|
||
|
"} aa();");
|
||
|
}
|
||
|
|
||
|
public void testContrivedExampleWhereConsistentRenamingIsWorse() {
|
||
|
previouslyUsedMap = makeVariableMap(
|
||
|
"Foo", "LongString", "L 0", "b", "L 1", "c");
|
||
|
|
||
|
test("function Foo(v1, v2) {return v1;} Foo();",
|
||
|
"function LongString(b, c) {return b;} LongString();");
|
||
|
|
||
|
previouslyUsedMap = renameVars.getVariableMap();
|
||
|
VariableMap expectedVariableMap = makeVariableMap(
|
||
|
"Foo", "LongString", "L 0", "b", "L 1", "c");
|
||
|
assertVariableMapsEqual(expectedVariableMap, previouslyUsedMap);
|
||
|
}
|
||
|
|
||
|
public void testExportSimpleSymbolReservesName() {
|
||
|
test("var goog, x; goog.exportSymbol('a', x);",
|
||
|
"var a, b; a.exportSymbol('a', b);");
|
||
|
withClosurePass = true;
|
||
|
test("var goog, x; goog.exportSymbol('a', x);",
|
||
|
"var b, c; b.exportSymbol('a', c);");
|
||
|
}
|
||
|
|
||
|
public void testExportComplexSymbolReservesName() {
|
||
|
test("var goog, x; goog.exportSymbol('a.b', x);",
|
||
|
"var a, b; a.exportSymbol('a.b', b);");
|
||
|
withClosurePass = true;
|
||
|
test("var goog, x; goog.exportSymbol('a.b', x);",
|
||
|
"var b, c; b.exportSymbol('a.b', c);");
|
||
|
}
|
||
|
|
||
|
public void testExportToNonStringDoesntExplode() {
|
||
|
withClosurePass = true;
|
||
|
test("var goog, a, b; goog.exportSymbol(a, b);",
|
||
|
"var a, b, c; a.exportSymbol(b, c);");
|
||
|
}
|
||
|
|
||
|
public void testDollarSignSuperExport1() {
|
||
|
useGoogleCodingConvention = false;
|
||
|
// See http://code.google.com/p/closure-compiler/issues/detail?id=32
|
||
|
test("var x = function($super,duper,$fantastic){}",
|
||
|
"var c = function($super, a, b){}");
|
||
|
|
||
|
localRenamingOnly = false;
|
||
|
test("var $super = 1", "var a = 1");
|
||
|
|
||
|
useGoogleCodingConvention = true;
|
||
|
test("var x = function($super,duper,$fantastic){}",
|
||
|
"var c = function($super,a,b){}");
|
||
|
}
|
||
|
|
||
|
public void testDollarSignSuperExport2() {
|
||
|
boolean normalizedExpectedJs = false;
|
||
|
super.enableNormalize(false);
|
||
|
|
||
|
useGoogleCodingConvention = false;
|
||
|
// See http://code.google.com/p/closure-compiler/issues/detail?id=32
|
||
|
test("var x = function($super,duper,$fantastic){};" +
|
||
|
"var y = function($super,duper){};",
|
||
|
"var c = function($super, a, b){};" +
|
||
|
"var d = function($super, a){};");
|
||
|
|
||
|
localRenamingOnly = false;
|
||
|
test("var $super = 1", "var a = 1");
|
||
|
|
||
|
useGoogleCodingConvention = true;
|
||
|
test("var x = function($super,duper,$fantastic){};" +
|
||
|
"var y = function($super,duper){};",
|
||
|
"var c = function($super, a, b ){};" +
|
||
|
"var d = function($super,a){};");
|
||
|
|
||
|
super.disableNormalize();
|
||
|
}
|
||
|
|
||
|
public void testPseudoNames() {
|
||
|
generatePseudoNames = false;
|
||
|
// See http://code.google.com/p/closure-compiler/issues/detail?id=32
|
||
|
test("var foo = function(a, b, c){}",
|
||
|
"var d = function(a, b, c){}");
|
||
|
|
||
|
generatePseudoNames = true;
|
||
|
test("var foo = function(a, b, c){}",
|
||
|
"var $foo$$ = function($a$$, $b$$, $c$$){}");
|
||
|
|
||
|
test("var a = function(a, b, c){}",
|
||
|
"var $a$$ = function($a$$, $b$$, $c$$){}");
|
||
|
}
|
||
|
|
||
|
private void testRenameMapUsingOldMap(String input, String expected,
|
||
|
VariableMap expectedMap) {
|
||
|
previouslyUsedMap = renameVars.getVariableMap();
|
||
|
testRenameMap("", input, expected, expectedMap);
|
||
|
}
|
||
|
|
||
|
private void testRenameMapUsingOldMap(String externs, String input,
|
||
|
String expected,
|
||
|
VariableMap expectedMap) {
|
||
|
previouslyUsedMap = renameVars.getVariableMap();
|
||
|
testRenameMap(externs, input, expected, expectedMap);
|
||
|
}
|
||
|
|
||
|
private void testRenameMap(String input, String expected,
|
||
|
VariableMap expectedRenameMap) {
|
||
|
testRenameMap("", input, expected, expectedRenameMap);
|
||
|
}
|
||
|
|
||
|
private void testRenameMap(String externs, String input, String expected,
|
||
|
VariableMap expectedRenameMap) {
|
||
|
test(externs, input, expected, null, null);
|
||
|
VariableMap renameMap = renameVars.getVariableMap();
|
||
|
assertVariableMapsEqual(expectedRenameMap, renameMap);
|
||
|
}
|
||
|
|
||
|
private VariableMap makeVariableMap(String... keyValPairs) {
|
||
|
Preconditions.checkArgument(keyValPairs.length % 2 == 0);
|
||
|
|
||
|
ImmutableMap.Builder<String, String> renameMap = ImmutableMap.builder();
|
||
|
for (int i = 0; i < keyValPairs.length; i += 2) {
|
||
|
renameMap.put(keyValPairs[i], keyValPairs[i + 1]);
|
||
|
}
|
||
|
|
||
|
return new VariableMap(renameMap.build());
|
||
|
}
|
||
|
|
||
|
private static void assertVariableMapsEqual(VariableMap a, VariableMap b) {
|
||
|
Map<String, String> ma = a.getOriginalNameToNewNameMap();
|
||
|
Map<String, String> mb = b.getOriginalNameToNewNameMap();
|
||
|
assertEquals("VariableMaps not equal", ma, mb);
|
||
|
}
|
||
|
|
||
|
private class ClosurePassAndRenameVars implements CompilerPass {
|
||
|
private final Compiler compiler;
|
||
|
|
||
|
private ClosurePassAndRenameVars(Compiler compiler) {
|
||
|
this.compiler = compiler;
|
||
|
}
|
||
|
|
||
|
@Override
|
||
|
public void process(Node externs, Node root) {
|
||
|
ProcessClosurePrimitives closurePass =
|
||
|
new ProcessClosurePrimitives(
|
||
|
compiler, null, CheckLevel.WARNING);
|
||
|
closurePass.process(externs, root);
|
||
|
renameVars = new RenameVars(compiler, prefix,
|
||
|
false, false, false, false, previouslyUsedMap, null,
|
||
|
closurePass.getExportedVariableNames());
|
||
|
renameVars.process(externs, root);
|
||
|
}
|
||
|
}
|
||
|
}
|