From a187c782aa0fa1326154f03be48c780700283eb6 Mon Sep 17 00:00:00 2001 From: Tim Blasi Date: Wed, 10 Jun 2015 12:37:22 -0700 Subject: [PATCH] feat(dart/transform): Allow absolute urls in templates Allow `templateUrl` to be specified as an absolute `package:` import. --- .../src/transform/common/xhr_impl.dart | 3 ++- .../transform/directive_linker/linker.dart | 3 ++- .../extractor.dart | 3 ++- .../view_definition_creator.dart | 5 +++-- .../absolute_export_files/bar.ng_deps.dart | 16 ++++++++++++++ .../absolute_export_files/foo.ng_deps.dart | 20 ++++++++++++++++++ .../all_tests.dart | 21 +++++++++++++++++-- .../expected/hello.ng_deps.dart | 20 ++++++++++++++++++ .../absolute_url_expression_files/hello.dart | 8 +++++++ .../template.html | 1 + .../directive_processor/all_tests.dart | 15 +++++++++++-- 11 files changed, 106 insertions(+), 9 deletions(-) create mode 100644 modules/angular2/test/transform/directive_metadata_extractor/absolute_export_files/bar.ng_deps.dart create mode 100644 modules/angular2/test/transform/directive_metadata_extractor/absolute_export_files/foo.ng_deps.dart create mode 100644 modules/angular2/test/transform/directive_processor/absolute_url_expression_files/expected/hello.ng_deps.dart create mode 100644 modules/angular2/test/transform/directive_processor/absolute_url_expression_files/hello.dart create mode 100644 modules/angular2/test/transform/directive_processor/absolute_url_expression_files/template.html diff --git a/modules/angular2/src/transform/common/xhr_impl.dart b/modules/angular2/src/transform/common/xhr_impl.dart index 5d53d1014c..f487f880c4 100644 --- a/modules/angular2/src/transform/common/xhr_impl.dart +++ b/modules/angular2/src/transform/common/xhr_impl.dart @@ -14,7 +14,8 @@ class XhrImpl implements XHR { XhrImpl(this._reader, this._entryPoint); Future get(String url) async { - var assetId = uriToAssetId(_entryPoint, url, logger, null); + var assetId = uriToAssetId(_entryPoint, url, logger, null /* span */, + errorOnAbsolute: false); var templateExists = await _reader.hasInput(assetId); if (!templateExists) { logger.error('Could not read template at uri $url from $_entryPoint'); diff --git a/modules/angular2/src/transform/directive_linker/linker.dart b/modules/angular2/src/transform/directive_linker/linker.dart index b96c0a8d6c..e5341e1a04 100644 --- a/modules/angular2/src/transform/directive_linker/linker.dart +++ b/modules/angular2/src/transform/directive_linker/linker.dart @@ -113,7 +113,8 @@ Future> _processNgImports(AssetReader reader, .map((UriBasedDirective directive) { var ngDepsUri = _toDepsUri(stringLiteralToString(directive.uri)); var spanArg = null; - var ngDepsAsset = uriToAssetId(entryPoint, ngDepsUri, logger, spanArg); + var ngDepsAsset = uriToAssetId(entryPoint, ngDepsUri, logger, spanArg, + errorOnAbsolute: false); if (ngDepsAsset == entryPoint) return nullFuture; return reader.hasInput(ngDepsAsset).then((hasInput) { if (hasInput) { diff --git a/modules/angular2/src/transform/directive_metadata_extractor/extractor.dart b/modules/angular2/src/transform/directive_metadata_extractor/extractor.dart index 89604e6702..67803e9bdb 100644 --- a/modules/angular2/src/transform/directive_metadata_extractor/extractor.dart +++ b/modules/angular2/src/transform/directive_metadata_extractor/extractor.dart @@ -37,7 +37,8 @@ Future> _extractDirectiveMetadataRecursive( if (uri.startsWith('dart:')) return _nullFuture; uri = toDepsExtension(uri); - var assetId = uriToAssetId(entryPoint, uri, logger, null /* span */); + var assetId = uriToAssetId(entryPoint, uri, logger, null /* span */, + errorOnAbsolute: false); if (assetId == entryPoint) return _nullFuture; return _extractDirectiveMetadataRecursive(reader, assetId) .then((exportMap) { diff --git a/modules/angular2/src/transform/template_compiler/view_definition_creator.dart b/modules/angular2/src/transform/template_compiler/view_definition_creator.dart index 44a01c1290..0e62d61ffd 100644 --- a/modules/angular2/src/transform/template_compiler/view_definition_creator.dart +++ b/modules/angular2/src/transform/template_compiler/view_definition_creator.dart @@ -97,8 +97,9 @@ class _ViewDefinitionCreator { var prefix = node.prefix != null && node.prefix.name != null ? '${node.prefix.name}' : null; - importAssetToPrefix[ - uriToAssetId(entryPoint, uri, logger, null /* span */)] = prefix; + importAssetToPrefix[uriToAssetId( + entryPoint, uri, logger, null /* span */, + errorOnAbsolute: false)] = prefix; } } return importAssetToPrefix; diff --git a/modules/angular2/test/transform/directive_metadata_extractor/absolute_export_files/bar.ng_deps.dart b/modules/angular2/test/transform/directive_metadata_extractor/absolute_export_files/bar.ng_deps.dart new file mode 100644 index 0000000000..381592661d --- /dev/null +++ b/modules/angular2/test/transform/directive_metadata_extractor/absolute_export_files/bar.ng_deps.dart @@ -0,0 +1,16 @@ +library foo.ng_deps.dart; + +import 'bar.dart'; +import 'package:angular2/src/core/annotations/annotations.dart'; + +var _visited = false; +void initReflector(reflector) { + if (_visited) return; + _visited = true; + reflector + ..registerType(BarComponent, { + 'factory': () => new BarComponent(), + 'parameters': const [], + 'annotations': const [const Component(selector: '[bar]')] + }); +} diff --git a/modules/angular2/test/transform/directive_metadata_extractor/absolute_export_files/foo.ng_deps.dart b/modules/angular2/test/transform/directive_metadata_extractor/absolute_export_files/foo.ng_deps.dart new file mode 100644 index 0000000000..17cba130ac --- /dev/null +++ b/modules/angular2/test/transform/directive_metadata_extractor/absolute_export_files/foo.ng_deps.dart @@ -0,0 +1,20 @@ +library foo.ng_deps.dart; + +import 'foo.dart'; +import 'package:angular2/src/core/annotations/annotations.dart'; + +export 'package:bar/bar.dart'; +import 'package:bar/bar.ng_deps.dart' as i0; + +var _visited = false; +void initReflector(reflector) { + if (_visited) return; + _visited = true; + reflector + ..registerType(FooComponent, { + 'factory': () => new FooComponent(), + 'parameters': const [], + 'annotations': const [const Component(selector: '[foo]')] + }); + i0.initReflector(reflector); +} diff --git a/modules/angular2/test/transform/directive_metadata_extractor/all_tests.dart b/modules/angular2/test/transform/directive_metadata_extractor/all_tests.dart index 81b95d172d..e799e1b5e6 100644 --- a/modules/angular2/test/transform/directive_metadata_extractor/all_tests.dart +++ b/modules/angular2/test/transform/directive_metadata_extractor/all_tests.dart @@ -17,9 +17,12 @@ import '../common/read_file.dart'; var formatter = new DartFormatter(); void allTests() { - var reader = new TestAssetReader(); + TestAssetReader reader = null; - beforeEach(() => setLogger(new PrintLogger())); + beforeEach(() { + setLogger(new PrintLogger()); + reader = new TestAssetReader(); + }); Future readMetadata(inputPath) async { var ngDeps = await NgDeps.parse(reader, new AssetId('a', inputPath)); @@ -147,5 +150,19 @@ void allTests() { expect(extracted['BarComponent'].selector).toEqual('[bar]'); expect(extracted['BazComponent'].selector).toEqual('[baz]'); }); + + it('should include `DirectiveMetadata` from exported files ' + 'expressed as absolute uris', () async { + reader.addAsset(new AssetId('bar', 'lib/bar.ng_deps.dart'), readFile( + 'directive_metadata_extractor/absolute_export_files/bar.ng_deps.dart')); + + var extracted = await extractDirectiveMetadata(reader, new AssetId('a', + 'directive_metadata_extractor/absolute_export_files/foo.ng_deps.dart')); + expect(extracted).toContain('FooComponent'); + expect(extracted).toContain('BarComponent'); + + expect(extracted['FooComponent'].selector).toEqual('[foo]'); + expect(extracted['BarComponent'].selector).toEqual('[bar]'); + }); }); } diff --git a/modules/angular2/test/transform/directive_processor/absolute_url_expression_files/expected/hello.ng_deps.dart b/modules/angular2/test/transform/directive_processor/absolute_url_expression_files/expected/hello.ng_deps.dart new file mode 100644 index 0000000000..b877935fb0 --- /dev/null +++ b/modules/angular2/test/transform/directive_processor/absolute_url_expression_files/expected/hello.ng_deps.dart @@ -0,0 +1,20 @@ +library examples.src.hello_world.index_common_dart.ng_deps.dart; + +import 'hello.dart'; +import 'package:angular2/angular2.dart' + show bootstrap, Component, Directive, View, NgElement; + +var _visited = false; +void initReflector(reflector) { + if (_visited) return; + _visited = true; + reflector + ..registerType(HelloCmp, { + 'factory': () => new HelloCmp(), + 'parameters': const [], + 'annotations': const [ + const Component(selector: 'hello-app'), + const View(template: r'''{{greeting}}''') + ] + }); +} diff --git a/modules/angular2/test/transform/directive_processor/absolute_url_expression_files/hello.dart b/modules/angular2/test/transform/directive_processor/absolute_url_expression_files/hello.dart new file mode 100644 index 0000000000..c021513f8c --- /dev/null +++ b/modules/angular2/test/transform/directive_processor/absolute_url_expression_files/hello.dart @@ -0,0 +1,8 @@ +library examples.src.hello_world.index_common_dart; + +import 'package:angular2/angular2.dart' + show bootstrap, Component, Directive, View, NgElement; + +@Component(selector: 'hello-app') +@View(templateUrl: 'package:other_package/template.html') +class HelloCmp {} diff --git a/modules/angular2/test/transform/directive_processor/absolute_url_expression_files/template.html b/modules/angular2/test/transform/directive_processor/absolute_url_expression_files/template.html new file mode 100644 index 0000000000..d75013393f --- /dev/null +++ b/modules/angular2/test/transform/directive_processor/absolute_url_expression_files/template.html @@ -0,0 +1 @@ +{{greeting}} \ No newline at end of file diff --git a/modules/angular2/test/transform/directive_processor/all_tests.dart b/modules/angular2/test/transform/directive_processor/all_tests.dart index 89b987d7bf..65224229db 100644 --- a/modules/angular2/test/transform/directive_processor/all_tests.dart +++ b/modules/angular2/test/transform/directive_processor/all_tests.dart @@ -3,6 +3,7 @@ library angular2.test.transform.directive_processor.all_tests; import 'package:barback/barback.dart'; import 'package:angular2/src/transform/directive_processor/rewriter.dart'; import 'package:angular2/src/transform/common/annotation_matcher.dart'; +import 'package:angular2/src/transform/common/asset_reader.dart'; import 'package:dart_style/dart_style.dart'; import 'package:guinness/guinness.dart'; import 'package:path/path.dart' as path; @@ -40,6 +41,13 @@ void allTests() { _testNgDeps( 'should inline `templateUrl` values.', 'url_expression_files/hello.dart'); + var absoluteReader = new TestAssetReader(); + absoluteReader.addAsset(new AssetId('other_package', 'lib/template.html'), + readFile( + 'directive_processor/absolute_url_expression_files/template.html')); + _testNgDeps('should inline `templateUrl` values expressed as absolute urls.', + 'absolute_url_expression_files/hello.dart', reader: absoluteReader); + _testNgDeps('should inline `templateUrl`s expressed as adjacent strings.', 'split_url_expression_files/hello.dart'); @@ -54,10 +62,13 @@ void allTests() { } void _testNgDeps(String name, String inputPath, - {List customDescriptors: const [], AssetId assetId}) { + {List customDescriptors: const [], AssetId assetId, + AssetReader reader}) { it(name, () async { var inputId = _assetIdForPath(inputPath); - var reader = new TestAssetReader(); + if (reader == null) { + reader = new TestAssetReader(); + } if (assetId != null) { reader.addAsset(assetId, await reader.readAsString(inputId)); inputId = assetId;