OLD | NEW |
(Empty) | |
| 1 /// <reference path="../typings/mocha/mocha.d.ts"/> |
| 2 import {expectTranslate} from './test_support'; |
| 3 |
| 4 // TODO(jacobr): merge these tests back in with the other tests. These tests are |
| 5 // only separate because we expected at one point to integrate with TS2Dart |
| 6 // instead of refactoring TS2Dart to only output facades. |
| 7 describe('variables', () => { |
| 8 it('should print variable declaration', () => { |
| 9 expectTranslate('var a:number;').to.equal(`@JS() |
| 10 external num get a; |
| 11 @JS() |
| 12 external set a(num v);`); |
| 13 expectTranslate('var a;').to.equal(`@JS() |
| 14 external get a; |
| 15 @JS() |
| 16 external set a(v);`); |
| 17 expectTranslate('var a:any;').to.equal(`@JS() |
| 18 external dynamic get a; |
| 19 @JS() |
| 20 external set a(dynamic v);`); |
| 21 }); |
| 22 it('should transpile variable declaration lists', () => { |
| 23 expectTranslate('var a: A;').to.equal(`@JS() |
| 24 external A get a; |
| 25 @JS() |
| 26 external set a(A v);`); |
| 27 |
| 28 expectTranslate('var a, b;').to.equal(`@JS() |
| 29 external get a; |
| 30 @JS() |
| 31 external set a(v); |
| 32 @JS() |
| 33 external get b; |
| 34 @JS() |
| 35 external set b(v);`); |
| 36 }); |
| 37 it('support vardecls containing more than one type (implicit or explicit)', ()
=> { |
| 38 expectTranslate('var a: A, b: B;').to.equal(`@JS() |
| 39 external A get a; |
| 40 @JS() |
| 41 external set a(A v); |
| 42 @JS() |
| 43 external B get b; |
| 44 @JS() |
| 45 external set b(B v);`); |
| 46 expectTranslate('var a: number, b: string;').to.equal(`@JS() |
| 47 external num get a; |
| 48 @JS() |
| 49 external set a(num v); |
| 50 @JS() |
| 51 external String get b; |
| 52 @JS() |
| 53 external set b(String v);`); |
| 54 }); |
| 55 |
| 56 it('supports const', () => { |
| 57 expectTranslate('const a:number = 1;').to.equal(`@JS() |
| 58 external num get a;`); |
| 59 |
| 60 expectTranslate('const a:number = 1, b:number = 2;').to.equal(`@JS() |
| 61 external num get a; |
| 62 @JS() |
| 63 external num get b;`); |
| 64 |
| 65 expectTranslate('const a:string').to.equal(`@JS() |
| 66 external String get a;`); |
| 67 |
| 68 expectTranslate('const a:number, b:number;').to.equal(`@JS() |
| 69 external num get a; |
| 70 @JS() |
| 71 external num get b;`); |
| 72 }); |
| 73 }); |
| 74 |
| 75 describe('classes', () => { |
| 76 it('should translate classes', () => { |
| 77 expectTranslate('class X {}').to.equal(`@JS() |
| 78 class X { |
| 79 // @Ignore |
| 80 X.fakeConstructor$(); |
| 81 }`); |
| 82 }); |
| 83 it('should support extends', () => { |
| 84 expectTranslate('class X extends Y {}').to.equal(`@JS() |
| 85 class X extends Y { |
| 86 // @Ignore |
| 87 X.fakeConstructor$() : super.fakeConstructor$(); |
| 88 }`); |
| 89 }); |
| 90 it('should support implements', () => { |
| 91 expectTranslate('class X implements Y, Z {}').to.equal(`@JS() |
| 92 class X implements Y, Z { |
| 93 // @Ignore |
| 94 X.fakeConstructor$(); |
| 95 }`); |
| 96 }); |
| 97 it('should support implements', () => { |
| 98 expectTranslate('class X extends Y implements Z {}').to.equal(`@JS() |
| 99 class X extends Y implements Z { |
| 100 // @Ignore |
| 101 X.fakeConstructor$() : super.fakeConstructor$(); |
| 102 }`); |
| 103 }); |
| 104 it('should support abstract', () => { |
| 105 expectTranslate('abstract class X {}').to.equal(`@JS() |
| 106 abstract class X { |
| 107 // @Ignore |
| 108 X.fakeConstructor$(); |
| 109 }`); |
| 110 }); |
| 111 describe('members', () => { |
| 112 it('supports empty declarations', () => { |
| 113 expectTranslate('class X { ; }').to.equal(`@JS() |
| 114 class X { |
| 115 // @Ignore |
| 116 X.fakeConstructor$(); |
| 117 }`); |
| 118 }); |
| 119 it('supports fields', () => { |
| 120 expectTranslate('class X { x: number; y: string; }').to.equal(`@JS() |
| 121 class X { |
| 122 // @Ignore |
| 123 X.fakeConstructor$(); |
| 124 external num get x; |
| 125 external set x(num v); |
| 126 external String get y; |
| 127 external set y(String v); |
| 128 }`); |
| 129 expectTranslate('class X { x; }').to.equal(`@JS() |
| 130 class X { |
| 131 // @Ignore |
| 132 X.fakeConstructor$(); |
| 133 external get x; |
| 134 external set x(v); |
| 135 }`); |
| 136 }); |
| 137 it('ignore field initializers', () => { |
| 138 expectTranslate('class X { x: number = 42; }').to.equal(`@JS() |
| 139 class X { |
| 140 // @Ignore |
| 141 X.fakeConstructor$(); |
| 142 external num get x; |
| 143 external set x(num v); |
| 144 }`); |
| 145 }); |
| 146 it('supports visibility modifiers', () => { |
| 147 expectTranslate('class X { private _x; x; }').to.equal(`@JS() |
| 148 class X { |
| 149 // @Ignore |
| 150 X.fakeConstructor$(); |
| 151 external get JS$_x; |
| 152 external set JS$_x(v); |
| 153 external get x; |
| 154 external set x(v); |
| 155 }`); |
| 156 expectTranslate('class X { private x; }').to.equal(`@JS() |
| 157 class X { |
| 158 // @Ignore |
| 159 X.fakeConstructor$(); |
| 160 external get x; |
| 161 external set x(v); |
| 162 }`); |
| 163 expectTranslate('class X { constructor (private x) {} }').to.equal(`@JS() |
| 164 class X { |
| 165 // @Ignore |
| 166 X.fakeConstructor$(); |
| 167 external get x; |
| 168 external set x(v); |
| 169 external factory X(x); |
| 170 }`); |
| 171 expectTranslate('class X { _x; }').to.equal(`@JS() |
| 172 class X { |
| 173 // @Ignore |
| 174 X.fakeConstructor$(); |
| 175 external get JS$_x; |
| 176 external set JS$_x(v); |
| 177 }`); |
| 178 }); |
| 179 it('does not support protected', () => { |
| 180 expectTranslate('class X { protected x; }').to.equal(`@JS() |
| 181 class X { |
| 182 // @Ignore |
| 183 X.fakeConstructor$(); |
| 184 external get x; |
| 185 external set x(v); |
| 186 }`); |
| 187 }); |
| 188 it('supports static fields', () => { |
| 189 expectTranslate('class X { static x: number = 42; }').to.equal(`@JS() |
| 190 class X { |
| 191 // @Ignore |
| 192 X.fakeConstructor$(); |
| 193 external static num get x; |
| 194 external static set x(num v); |
| 195 }`); |
| 196 }); |
| 197 it('supports methods', () => { |
| 198 expectTranslate('class X { x() { return 42; } }').to.equal(`@JS() |
| 199 class X { |
| 200 // @Ignore |
| 201 X.fakeConstructor$(); |
| 202 external x(); |
| 203 }`); |
| 204 }); |
| 205 it('supports abstract methods', () => { |
| 206 expectTranslate('abstract class X { abstract x(); }').to.equal(`@JS() |
| 207 abstract class X { |
| 208 // @Ignore |
| 209 X.fakeConstructor$(); |
| 210 external x(); |
| 211 }`); |
| 212 }); |
| 213 it('supports method return types', () => { |
| 214 expectTranslate('class X { x(): number { return 42; } }').to.equal(`@JS() |
| 215 class X { |
| 216 // @Ignore |
| 217 X.fakeConstructor$(); |
| 218 external num x(); |
| 219 }`); |
| 220 }); |
| 221 it('supports method params', () => { |
| 222 expectTranslate('class X { x(a, b); }').to.equal(`@JS() |
| 223 class X { |
| 224 // @Ignore |
| 225 X.fakeConstructor$(); |
| 226 external x(a, b); |
| 227 }`); |
| 228 }); |
| 229 it('supports method return types', () => { |
| 230 expectTranslate('class X { x( a : number, b : string ) : num }').to.equal(
`@JS() |
| 231 class X { |
| 232 // @Ignore |
| 233 X.fakeConstructor$(); |
| 234 external num x(num a, String b); |
| 235 }`); |
| 236 }); |
| 237 it('supports get methods', () => { |
| 238 expectTranslate('class X { get y(): number {} }').to.equal(`@JS() |
| 239 class X { |
| 240 // @Ignore |
| 241 X.fakeConstructor$(); |
| 242 external num get y; |
| 243 }`); |
| 244 expectTranslate('class X { static get Y(): number {} }').to.equal(`@JS() |
| 245 class X { |
| 246 // @Ignore |
| 247 X.fakeConstructor$(); |
| 248 external static num get Y; |
| 249 }`); |
| 250 }); |
| 251 it('supports set methods', () => { |
| 252 expectTranslate('class X { set y(n: number) {} }').to.equal(`@JS() |
| 253 class X { |
| 254 // @Ignore |
| 255 X.fakeConstructor$(); |
| 256 external set y(num n); |
| 257 }`); |
| 258 expectTranslate('class X { static get Y(): number {} }').to.equal(`@JS() |
| 259 class X { |
| 260 // @Ignore |
| 261 X.fakeConstructor$(); |
| 262 external static num get Y; |
| 263 }`); |
| 264 }); |
| 265 it('supports generic methods', () => { |
| 266 expectTranslate('class X<T> { static Z<T>(): X<T> {} }').to.equal(`@JS() |
| 267 class X<T> { |
| 268 // @Ignore |
| 269 X.fakeConstructor$(); |
| 270 external static X<dynamic/*=T*/ > Z/*<T>*/(); |
| 271 }`); |
| 272 expectTranslate('class X<T> { Z(): X<T> {} }').to.equal(`@JS() |
| 273 class X<T> { |
| 274 // @Ignore |
| 275 X.fakeConstructor$(); |
| 276 external X<T> Z(); |
| 277 }`); |
| 278 }); |
| 279 it('merge overrides', () => { |
| 280 expectTranslate(` |
| 281 class X { |
| 282 createElement(tagName: "img"): HTMLImageElement; |
| 283 createElement(tagName: "video"): HTMLVideoElement; |
| 284 createElement(tagName: string): HTMLElement; |
| 285 }`).to.equal(`import "dart:html"; |
| 286 |
| 287 @JS() |
| 288 class X { |
| 289 // @Ignore |
| 290 X.fakeConstructor$(); |
| 291 /*external ImageElement createElement("img" tagName);*/ |
| 292 /*external VideoElement createElement("video" tagName);*/ |
| 293 /*external HtmlElement createElement(String tagName);*/ |
| 294 external dynamic /*ImageElement|VideoElement|HtmlElement*/ createElement( |
| 295 String tagName); |
| 296 }`); |
| 297 expectTranslate(` |
| 298 class X { |
| 299 F(a:string):num; |
| 300 F(a:string, b: string|num):string; |
| 301 F(a2:string, b: string, c: num):string; |
| 302 }`).to.equal(`@JS() |
| 303 class X { |
| 304 // @Ignore |
| 305 X.fakeConstructor$(); |
| 306 /*external num F(String a);*/ |
| 307 /*external String F(String a, String|num b);*/ |
| 308 /*external String F(String a2, String b, num c);*/ |
| 309 external dynamic /*num|String*/ F(String a_a2, |
| 310 [dynamic /*String|num*/ b, num c]); |
| 311 }`); |
| 312 |
| 313 expectTranslate(` |
| 314 class X { |
| 315 Y(a:string):num {}; |
| 316 Y(a:string, b: num):string {}; |
| 317 Y(a2:string, b: string, c: num):string {}; |
| 318 }`).to.equal(`@JS() |
| 319 class X { |
| 320 // @Ignore |
| 321 X.fakeConstructor$(); |
| 322 /*external num Y(String a);*/ |
| 323 /*external String Y(String a, num b);*/ |
| 324 /*external String Y(String a2, String b, num c);*/ |
| 325 external dynamic /*num|String*/ Y(String a_a2, |
| 326 [dynamic /*num|String*/ b, num c]); |
| 327 }`); |
| 328 expectTranslate(` |
| 329 class X { |
| 330 firstElement(elements: HTMLImageElement[]): HTMLImageElement; |
| 331 firstElement(elements: HTMLVideoElement[]): HTMLVideoElement; |
| 332 firstElement(elements: HTMLElement[]): HTMLElement; |
| 333 }`).to.equal(`import "dart:html"; |
| 334 |
| 335 @JS() |
| 336 class X { |
| 337 // @Ignore |
| 338 X.fakeConstructor$(); |
| 339 /*external ImageElement firstElement(List<ImageElement> elements);*/ |
| 340 /*external VideoElement firstElement(List<VideoElement> elements);*/ |
| 341 /*external HtmlElement firstElement(List<HtmlElement> elements);*/ |
| 342 external dynamic /*ImageElement|VideoElement|HtmlElement*/ firstElement( |
| 343 List< |
| 344 HtmlElement> /*List<ImageElement>|List<VideoElement>|List<HtmlElement>
*/ elements); |
| 345 }`); |
| 346 |
| 347 // TODO(jacobr): we should consider special casing so EventLister and |
| 348 // EventListenerObject are treated as the same in Dart even though they |
| 349 // are different. |
| 350 expectTranslate(` |
| 351 interface SampleAudioNode { |
| 352 addEventListener(type: "ended", listener: (ev: Event) => any, useCapture?: boo
lean): void; |
| 353 addEventListener(type: string, listener: EventListenerOrEventListenerObject, u
seCapture?: boolean): void; |
| 354 }`).to.equal(`import "dart:html"; |
| 355 import "package:func/func.dart"; |
| 356 |
| 357 @anonymous |
| 358 @JS() |
| 359 abstract class SampleAudioNode { |
| 360 /*external void addEventListener("ended" type, dynamic listener(Event ev), [bo
ol useCapture]);*/ |
| 361 /*external void addEventListener(String type, EventListener|EventListenerObjec
t listener, [bool useCapture]);*/ |
| 362 external void addEventListener(String type, |
| 363 dynamic /*Func1<Event, dynamic>|EventListener|EventListenerObject*/ listen
er, |
| 364 [bool useCapture]); |
| 365 }`); |
| 366 |
| 367 expectTranslate(` |
| 368 interface ListenObject { |
| 369 someDummyMethod(evt: string): void; |
| 370 } |
| 371 |
| 372 interface ExampleListener { |
| 373 (evt: string): void; |
| 374 } |
| 375 |
| 376 interface DummySample { |
| 377 addEventListener(type: "ended", listener: ListenObject): void; |
| 378 addEventListener(type: string, listener: ExampleListener): void; |
| 379 }`).to.equal(`@anonymous |
| 380 @JS() |
| 381 abstract class ListenObject { |
| 382 external void someDummyMethod(String evt); |
| 383 } |
| 384 |
| 385 typedef void ExampleListener(String evt); |
| 386 |
| 387 @anonymous |
| 388 @JS() |
| 389 abstract class DummySample { |
| 390 /*external void addEventListener("ended" type, ListenObject listener);*/ |
| 391 /*external void addEventListener(String type, ExampleListener listener);*/ |
| 392 external void addEventListener( |
| 393 String type, dynamic /*ListenObject|ExampleListener*/ listener); |
| 394 }`); |
| 395 |
| 396 expectTranslate(` |
| 397 interface ListenAny { |
| 398 (evt: any): void; |
| 399 } |
| 400 |
| 401 interface ExampleListener { |
| 402 (evt: string): void; |
| 403 } |
| 404 |
| 405 interface DummySample { |
| 406 addEventListener(type: "ended", listener: ListenAny): void; |
| 407 addEventListener(type: string, listener: ExampleListener): void; |
| 408 }`).to.equal(`typedef void ListenAny(dynamic evt); |
| 409 typedef void ExampleListener(String evt); |
| 410 |
| 411 @anonymous |
| 412 @JS() |
| 413 abstract class DummySample { |
| 414 /*external void addEventListener("ended" type, ListenAny listener);*/ |
| 415 /*external void addEventListener(String type, ExampleListener listener);*/ |
| 416 external void addEventListener( |
| 417 String type, Function /*ListenAny|ExampleListener*/ listener); |
| 418 }`); |
| 419 |
| 420 }); |
| 421 it('dot dot dot', () => { |
| 422 expectTranslate(` |
| 423 function buildName(firstName: string, ...restOfName: string[]): string; |
| 424 `).to.equal(`@JS() |
| 425 external String buildName(String firstName, |
| 426 [String restOfName1, |
| 427 String restOfName2, |
| 428 String restOfName3, |
| 429 String restOfName4, |
| 430 String restOfName5]);`); |
| 431 expectTranslate(` |
| 432 function log(...args);`) |
| 433 .to.equal(`@JS() |
| 434 external log([args1, args2, args3, args4, args5]);`); |
| 435 }); |
| 436 it('interface constructors', () => { |
| 437 expectTranslate(` |
| 438 interface C { |
| 439 oncached: (ev: Event) => any; |
| 440 } |
| 441 declare var C: {new(): C; CHECKING: number; }`) |
| 442 .to.equal(`import "package:func/func.dart"; |
| 443 import "dart:html"; |
| 444 |
| 445 @JS() |
| 446 abstract class C { |
| 447 external Func1<Event, dynamic> get oncached; |
| 448 external set oncached(Func1<Event, dynamic> v); |
| 449 external factory C(); |
| 450 external static num get CHECKING; |
| 451 external static set CHECKING(num v); |
| 452 }`); |
| 453 }); |
| 454 it('property bag interfaces', () => { |
| 455 expectTranslate(` |
| 456 interface X { |
| 457 a: string; |
| 458 b: num; |
| 459 c: X; |
| 460 } |
| 461 interface Y extends X { |
| 462 d: num; |
| 463 /* example comment */ |
| 464 e: any; |
| 465 }`).to.equal(`@anonymous |
| 466 @JS() |
| 467 abstract class X { |
| 468 external String get a; |
| 469 external set a(String v); |
| 470 external num get b; |
| 471 external set b(num v); |
| 472 external X get c; |
| 473 external set c(X v); |
| 474 external factory X({String a, num b, X c}); |
| 475 } |
| 476 |
| 477 @anonymous |
| 478 @JS() |
| 479 abstract class Y implements X { |
| 480 external num get d; |
| 481 external set d(num v); |
| 482 |
| 483 /// example comment |
| 484 external dynamic get e; |
| 485 external set e(dynamic v); |
| 486 external factory Y({num d, dynamic e, String a, num b, X c}); |
| 487 }`); |
| 488 expectTranslate(`interface X<A> { a: A; b: num, c: X } |
| 489 interface Y<A,B> extends X<A> { d: B; e: any; }`) |
| 490 .to.equal(`@anonymous |
| 491 @JS() |
| 492 abstract class X<A> { |
| 493 external A get a; |
| 494 external set a(A v); |
| 495 external num get b; |
| 496 external set b(num v); |
| 497 external X get c; |
| 498 external set c(X v); |
| 499 external factory X({A a, num b, X c}); |
| 500 } |
| 501 |
| 502 @anonymous |
| 503 @JS() |
| 504 abstract class Y<A, B> implements X<A> { |
| 505 external B get d; |
| 506 external set d(B v); |
| 507 external dynamic get e; |
| 508 external set e(dynamic v); |
| 509 external factory Y({B d, dynamic e, A a, num b, X c}); |
| 510 }`); |
| 511 }); |
| 512 it('callable', () => { |
| 513 expectTranslate('interface X<T> { (a:T):T; Y():T; }').to.equal(`@anonymous |
| 514 @JS() |
| 515 abstract class X<T> implements Function { |
| 516 external T call(T a); |
| 517 external T Y(); |
| 518 }`); |
| 519 }); |
| 520 |
| 521 it('supports constructors', () => { |
| 522 expectTranslate('class X { constructor() { } }').to.equal(`@JS() |
| 523 class X { |
| 524 // @Ignore |
| 525 X.fakeConstructor$(); |
| 526 external factory X(); |
| 527 }`); |
| 528 }); |
| 529 it('supports parameter properties', () => { |
| 530 expectTranslate(` |
| 531 class X { |
| 532 c: number; |
| 533 constructor(private _bar: B, public foo: string = "hello", private _goggles: b
oolean = true); |
| 534 }`).to.equal(`@JS() |
| 535 class X { |
| 536 // @Ignore |
| 537 X.fakeConstructor$(); |
| 538 external B get JS$_bar; |
| 539 external set JS$_bar(B v); |
| 540 external String get foo; |
| 541 external set foo(String v); |
| 542 external bool get JS$_goggles; |
| 543 external set JS$_goggles(bool v); |
| 544 external num get c; |
| 545 external set c(num v); |
| 546 external factory X(B JS$_bar, [String foo, bool JS$_goggles]); |
| 547 }`); |
| 548 expectTranslate(` |
| 549 class X { |
| 550 constructor(public foo: string, b: number, private _marbles: boolean = true) {
} |
| 551 }`).to.equal(`@JS() |
| 552 class X { |
| 553 // @Ignore |
| 554 X.fakeConstructor$(); |
| 555 external String get foo; |
| 556 external set foo(String v); |
| 557 external bool get JS$_marbles; |
| 558 external set JS$_marbles(bool v); |
| 559 external factory X(String foo, num b, [bool JS$_marbles]); |
| 560 }`); |
| 561 }); |
| 562 }); |
| 563 }); |
| 564 |
| 565 describe('interfaces', () => { |
| 566 it('translates interfaces to abstract classes', () => { |
| 567 expectTranslate('interface X {}').to.equal(`@anonymous |
| 568 @JS() |
| 569 abstract class X {}`); |
| 570 }); |
| 571 it('translates interface extends to class implements', () => { |
| 572 expectTranslate('interface X extends Y, Z {}').to.equal(`@anonymous |
| 573 @JS() |
| 574 abstract class X implements Y, Z {}`); |
| 575 }); |
| 576 it('supports abstract methods', () => { |
| 577 expectTranslate('interface X { x(); }').to.equal(`@anonymous |
| 578 @JS() |
| 579 abstract class X { |
| 580 external x(); |
| 581 }`); |
| 582 }); |
| 583 |
| 584 it('supports interface properties', () => { |
| 585 expectTranslate('interface X { x: string; y; }').to.equal(`@anonymous |
| 586 @JS() |
| 587 abstract class X { |
| 588 external String get x; |
| 589 external set x(String v); |
| 590 external get y; |
| 591 external set y(v); |
| 592 external factory X({String x, y}); |
| 593 }`); |
| 594 }); |
| 595 }); |
| 596 |
| 597 describe('single call signature interfaces', () => { |
| 598 it('should support declaration', () => { |
| 599 expectTranslate('interface F { (n: number): boolean; }').to.equal('typedef b
ool F(num n);'); |
| 600 }); |
| 601 it('should support generics', () => { |
| 602 expectTranslate('interface F<A, B> { (a: A): B; }').to.equal('typedef B F<A,
B>(A a);'); |
| 603 }); |
| 604 }); |
| 605 |
| 606 describe('enums', () => { |
| 607 it('should support basic enum declaration', () => { |
| 608 expectTranslate('enum Color { Red, Green, Blue }').to.equal(`@JS() |
| 609 class Color { |
| 610 external static num get Red; |
| 611 external static num get Green; |
| 612 external static num get Blue; |
| 613 }`); |
| 614 }); |
| 615 it('empty enum', () => { |
| 616 expectTranslate('enum Color { }').to.equal(`@JS() |
| 617 class Color {}`); |
| 618 }); |
| 619 it('enum with initializer', () => { |
| 620 expectTranslate('enum Color { Red = 1, Green, Blue = 4 }').to.equal(`@JS() |
| 621 class Color { |
| 622 external static num get Red; |
| 623 external static num get Green; |
| 624 external static num get Blue; |
| 625 }`); |
| 626 }); |
| 627 }); |
| 628 |
| 629 describe('renames', () => { |
| 630 it('should support class renames', () => { |
| 631 expectTranslate(` |
| 632 declare module m1 { |
| 633 interface A { x(); } |
| 634 } |
| 635 declare module m2 { |
| 636 interface A { y(); } |
| 637 } |
| 638 `).to.equal(`// Module m1 |
| 639 @anonymous |
| 640 @JS() |
| 641 abstract class A { |
| 642 external x(); |
| 643 } |
| 644 // End module m1 |
| 645 |
| 646 // Module m2 |
| 647 @anonymous |
| 648 @JS() |
| 649 abstract class m2_A { |
| 650 external y(); |
| 651 } |
| 652 // End module m2`); |
| 653 expectTranslate(` |
| 654 declare module m1 { |
| 655 class A { constructor(x); } |
| 656 } |
| 657 declare module m2 { |
| 658 class A { constructor(y); } |
| 659 }`).to.equal(`// Module m1 |
| 660 @JS("m1.A") |
| 661 class A { |
| 662 // @Ignore |
| 663 A.fakeConstructor$(); |
| 664 external factory A(x); |
| 665 } |
| 666 // End module m1 |
| 667 |
| 668 // Module m2 |
| 669 @JS("m2.A") |
| 670 class m2_A { |
| 671 // @Ignore |
| 672 m2_A.fakeConstructor$(); |
| 673 external factory m2_A(y); |
| 674 } |
| 675 // End module m2`); |
| 676 expectTranslate(` |
| 677 declare module m1 { |
| 678 class A { constructor(x:m2.A); } |
| 679 } |
| 680 declare module m2 { |
| 681 class A { constructor(y:m1.A); } |
| 682 } |
| 683 `).to.equal(`// Module m1 |
| 684 @JS("m1.A") |
| 685 class A { |
| 686 // @Ignore |
| 687 A.fakeConstructor$(); |
| 688 external factory A(m2_A x); |
| 689 } |
| 690 // End module m1 |
| 691 |
| 692 // Module m2 |
| 693 @JS("m2.A") |
| 694 class m2_A { |
| 695 // @Ignore |
| 696 m2_A.fakeConstructor$(); |
| 697 external factory m2_A(A y); |
| 698 } |
| 699 // End module m2`); |
| 700 |
| 701 }); |
| 702 it('should support member renames', () => { |
| 703 expectTranslate(` |
| 704 declare module m1 { |
| 705 interface A { x(); } |
| 706 } |
| 707 declare module m2 { |
| 708 export function A(x:m1.A); |
| 709 }`).to.equal(`// Module m1 |
| 710 @anonymous |
| 711 @JS() |
| 712 abstract class A { |
| 713 external x(); |
| 714 } |
| 715 // End module m1 |
| 716 |
| 717 // Module m2 |
| 718 @JS("m2.A") |
| 719 external m2_A(A x); |
| 720 // End module m2`); |
| 721 }); |
| 722 |
| 723 it('handle class renames in type declarations', () => { |
| 724 expectTranslate(` |
| 725 declare module m1 { |
| 726 interface A { x(); } |
| 727 } |
| 728 declare module m2 { |
| 729 interface A { y(); } |
| 730 } |
| 731 export function register(x:m2.A); |
| 732 `).to.equal(`// Module m1 |
| 733 @anonymous |
| 734 @JS() |
| 735 abstract class A { |
| 736 external x(); |
| 737 } |
| 738 // End module m1 |
| 739 |
| 740 // Module m2 |
| 741 @anonymous |
| 742 @JS() |
| 743 abstract class m2_A { |
| 744 external y(); |
| 745 } |
| 746 |
| 747 // End module m2 |
| 748 @JS() |
| 749 external register(m2_A x);`); |
| 750 expectTranslate(` |
| 751 declare module m1 { |
| 752 module foo { |
| 753 interface A { x(); } |
| 754 } |
| 755 } |
| 756 declare module m2 { |
| 757 module foo { |
| 758 interface A { y(); } |
| 759 } |
| 760 } |
| 761 declare module m3 { |
| 762 module foo { |
| 763 interface A { z(); } |
| 764 } |
| 765 } |
| 766 export function register(y:m2.foo.A, z:m3.foo.A); |
| 767 `).to.equal(`// Module m1 |
| 768 |
| 769 // Module foo |
| 770 @anonymous |
| 771 @JS() |
| 772 abstract class A { |
| 773 external x(); |
| 774 } |
| 775 // End module foo |
| 776 |
| 777 // End module m1 |
| 778 |
| 779 // Module m2 |
| 780 |
| 781 // Module foo |
| 782 @anonymous |
| 783 @JS() |
| 784 abstract class foo_A { |
| 785 external y(); |
| 786 } |
| 787 // End module foo |
| 788 |
| 789 // End module m2 |
| 790 |
| 791 // Module m3 |
| 792 |
| 793 // Module foo |
| 794 @anonymous |
| 795 @JS() |
| 796 abstract class m3_foo_A { |
| 797 external z(); |
| 798 } |
| 799 // End module foo |
| 800 |
| 801 // End module m3 |
| 802 @JS() |
| 803 external register(foo_A y, m3_foo_A z);`); |
| 804 |
| 805 expectTranslate(` |
| 806 declare module m1 { |
| 807 interface A { x(); } |
| 808 } |
| 809 declare module m2 { |
| 810 interface A { y(); } |
| 811 } |
| 812 export function register(x:m1.A); |
| 813 `).to.equal(`// Module m1 |
| 814 @anonymous |
| 815 @JS() |
| 816 abstract class A { |
| 817 external x(); |
| 818 } |
| 819 // End module m1 |
| 820 |
| 821 // Module m2 |
| 822 @anonymous |
| 823 @JS() |
| 824 abstract class m2_A { |
| 825 external y(); |
| 826 } |
| 827 |
| 828 // End module m2 |
| 829 @JS() |
| 830 external register(A x);`); |
| 831 }); |
| 832 |
| 833 describe('type alias', () => { |
| 834 it('replace with simple type', () => { |
| 835 expectTranslate(` |
| 836 type MyNumber = number; |
| 837 export function add(x: MyNumber, y: MyNumber): MyNumber; |
| 838 `).to.equal(`@JS() |
| 839 external num add(num x, num y);`); |
| 840 }); |
| 841 }); |
| 842 |
| 843 it('union types', () => { |
| 844 // TODO(jacobr): ideally the draw method should specify that arg el has type |
| 845 // HtmlElement instead of dynamic. |
| 846 expectTranslate(` |
| 847 type listener1 = ()=>boolean; |
| 848 type listener2 = (e:string)=>boolean; |
| 849 function addEventListener(listener: listener1|listener2);`) |
| 850 .to.equal(`import "package:func/func.dart"; |
| 851 |
| 852 @JS() |
| 853 external addEventListener( |
| 854 Function /*Func0<bool>|Func1<String, bool>*/ listener);`); |
| 855 |
| 856 expectTranslate('function draw(el: HTMLCanvasElement|HTMLImageElement):void;
') |
| 857 .to.equal(`import "dart:html"; |
| 858 |
| 859 @JS() |
| 860 external void draw(dynamic /*CanvasElement|ImageElement*/ el);`); |
| 861 }); |
| 862 }); |
OLD | NEW |