Skip to content

Commit

Permalink
Create local alias for super class in --closure mode (issue #312)
Browse files Browse the repository at this point in the history
Closure compiler chokes on super classes that aren't qualified paths.

(example: http://goo.gl/5mHC7S)

BUG=
R=jmesserly@google.com

Review URL: https://codereview.chromium.org/1638533004 .
  • Loading branch information
ochafik committed Feb 3, 2016
1 parent 7632658 commit f7f21ca
Show file tree
Hide file tree
Showing 4 changed files with 32 additions and 7 deletions.
3 changes: 2 additions & 1 deletion pkg/dev_compiler/lib/runtime/dart/_runtime.js
Original file line number Diff line number Diff line change
Expand Up @@ -732,7 +732,8 @@ dart_library.library('dart/_runtime', null, /* Imports */[
const _mixins = Symbol("mixins");
const implements_ = Symbol("implements");
const metadata = Symbol("metadata");
const TypeRep = class TypeRep extends LazyTagged(() => core.Type) {
const _TypeRepBase = LazyTagged(() => core.Type);
const TypeRep = class TypeRep extends _TypeRepBase {
get name() {
return this.toString();
}
Expand Down
30 changes: 26 additions & 4 deletions pkg/dev_compiler/lib/src/codegen/js_codegen.dart
Original file line number Diff line number Diff line change
Expand Up @@ -379,10 +379,11 @@ class JSCodegenVisitor extends GeneralizingAstVisitor with ClosureAnnotator {
}
}

var classDecl = new JS.ClassDeclaration(new JS.ClassExpression(
new JS.Identifier(element.name), _classHeritage(element), body));
var classExpr = new JS.ClassExpression(
new JS.Identifier(element.name), _classHeritage(element), body);

return _finishClassDef(element.type, classDecl);
return _finishClassDef(
element.type, _emitClassHeritageWorkaround(classExpr));
}

JS.Statement _emitJsType(String dartClassName, DartObject jsName) {
Expand Down Expand Up @@ -674,6 +675,27 @@ class JSCodegenVisitor extends GeneralizingAstVisitor with ClosureAnnotator {
}
}

_isQualifiedPath(JS.Expression node) =>
node is JS.Identifier ||
node is JS.PropertyAccess &&
_isQualifiedPath(node.receiver) &&
node.selector is JS.LiteralString;

/// Workaround for Closure: super classes must be qualified paths.
JS.Statement _emitClassHeritageWorkaround(JS.ClassExpression cls) {
if (options.closure &&
cls.heritage != null &&
!_isQualifiedPath(cls.heritage)) {
var superVar = new JS.TemporaryId(cls.name.name + r'$super');
return _statement([
js.statement('const # = #;', [superVar, cls.heritage]),
new JS.ClassDeclaration(
new JS.ClassExpression(cls.name, superVar, cls.methods))
]);
}
return new JS.ClassDeclaration(cls);
}

/// Emit class members that need to come after the class declaration, such
/// as static fields. See [_emitClassMethods] for things that are emitted
/// inside the ES6 `class { ... }` node.
Expand Down Expand Up @@ -702,7 +724,7 @@ class JSCodegenVisitor extends GeneralizingAstVisitor with ClosureAnnotator {
}
}

body.add(new JS.ClassDeclaration(cls));
body.add(_emitClassHeritageWorkaround(cls));

// TODO(jmesserly): we should really just extend native Array.
if (jsPeerName != null && classElem.typeParameters.isNotEmpty) {
Expand Down
3 changes: 2 additions & 1 deletion pkg/dev_compiler/test/codegen/expect/closure.js
Original file line number Diff line number Diff line change
Expand Up @@ -117,7 +117,8 @@ dart_library.library('closure', null, /* Imports */[
});
let Foo = Foo$();
class Bar extends core.Object {}
class Baz extends dart.mixin(Foo$(core.int), Bar) {
const Baz$super = dart.mixin(Foo$(core.int), Bar);
class Baz extends Baz$super {
/** @param {?number} i */
Baz(i) {
super.Foo(i, 123);
Expand Down
3 changes: 2 additions & 1 deletion pkg/dev_compiler/tool/input_sdk/private/types.dart
Original file line number Diff line number Diff line change
Expand Up @@ -38,8 +38,9 @@ final metadata = JS('', 'Symbol("metadata")');
/// String toString();
///
///
final _TypeRepBase = JS('', '$LazyTagged(() => $Type)');
final TypeRep = JS('', '''
class TypeRep extends $LazyTagged(() => $Type) {
class TypeRep extends $_TypeRepBase {
get name() {return this.toString();}
}
''');
Expand Down

0 comments on commit f7f21ca

Please sign in to comment.