From 7e202b93ab05cdf3cb90a6f769223550c436ecdb Mon Sep 17 00:00:00 2001 From: Janice Collins Date: Tue, 17 Aug 2021 09:55:12 -0700 Subject: [PATCH 01/47] Start the NNBD migration branch with additional github configuration and a basic "non-migration" of all libraries (#2739) * Update analyzer version to 2.0.0 * grind build for analyzer 2 * First steps toward migrating * Basic migration infrastruture for new NNBD branch * use separate workflow file for nnbd branch, for clarity * thinko --- .github/workflows/nnbd-test.yaml | 70 +++++++++++++++++++ .github/workflows/test.yaml | 26 +++---- bin/dartdoc.dart | 2 + lib/dartdoc.dart | 2 + lib/options.dart | 2 + .../model_comment_reference.dart | 3 + lib/src/comment_references/parser.dart | 3 + lib/src/dartdoc_options.dart | 2 + lib/src/element_type.dart | 2 + lib/src/experiment_options.dart | 2 + .../generator/dartdoc_generator_backend.dart | 2 + lib/src/generator/empty_generator.dart | 2 + lib/src/generator/generator.dart | 2 + lib/src/generator/generator_frontend.dart | 2 + lib/src/generator/generator_utils.dart | 2 + lib/src/generator/html_generator.dart | 2 + lib/src/generator/markdown_generator.dart | 2 + lib/src/generator/resource_loader.dart | 2 + lib/src/generator/template_data.dart | 2 + .../templates.aot_renderers_for_html.dart | 1 + .../templates.aot_renderers_for_md.dart | 1 + lib/src/generator/templates.dart | 2 + .../templates.runtime_renderers.dart | 1 + lib/src/io_utils.dart | 2 + lib/src/logging.dart | 2 + lib/src/markdown_processor.dart | 2 + lib/src/matching_link_result.dart | 2 + lib/src/model/accessor.dart | 2 + lib/src/model/annotation.dart | 2 + lib/src/model/canonicalization.dart | 2 + lib/src/model/categorization.dart | 2 + lib/src/model/category.dart | 2 + lib/src/model/class.dart | 2 + lib/src/model/comment_referable.dart | 2 + lib/src/model/constructor.dart | 2 + lib/src/model/container.dart | 2 + lib/src/model/container_member.dart | 2 + lib/src/model/documentable.dart | 2 + lib/src/model/documentation.dart | 2 + lib/src/model/documentation_comment.dart | 2 + lib/src/model/dynamic.dart | 2 + lib/src/model/enclosed_element.dart | 2 + lib/src/model/enum.dart | 2 + lib/src/model/extendable.dart | 2 + lib/src/model/extension.dart | 2 + lib/src/model/extension_target.dart | 2 + lib/src/model/feature.dart | 2 + lib/src/model/feature_set.dart | 2 + lib/src/model/field.dart | 2 + lib/src/model/getter_setter_combo.dart | 2 + lib/src/model/indexable.dart | 2 + lib/src/model/inheritable.dart | 2 + lib/src/model/language_feature.dart | 2 + lib/src/model/library.dart | 2 + lib/src/model/library_container.dart | 2 + lib/src/model/locatable.dart | 2 + lib/src/model/method.dart | 2 + lib/src/model/mixin.dart | 2 + lib/src/model/model.dart | 2 + lib/src/model/model_element.dart | 2 + lib/src/model/model_function.dart | 2 + lib/src/model/model_node.dart | 2 + lib/src/model/nameable.dart | 2 + lib/src/model/never.dart | 2 + lib/src/model/operator.dart | 2 + lib/src/model/package.dart | 2 + lib/src/model/package_builder.dart | 2 + lib/src/model/package_graph.dart | 2 + lib/src/model/parameter.dart | 2 + lib/src/model/prefix.dart | 2 + lib/src/model/privacy.dart | 2 + lib/src/model/source_code_mixin.dart | 2 + lib/src/model/top_level_container.dart | 2 + lib/src/model/top_level_variable.dart | 2 + lib/src/model/type_parameter.dart | 2 + lib/src/model/typedef.dart | 2 + lib/src/model_utils.dart | 2 + lib/src/mustachio/annotations.dart | 2 + lib/src/mustachio/parser.dart | 2 + lib/src/mustachio/renderer_base.dart | 2 + lib/src/package_config_provider.dart | 2 + lib/src/package_meta.dart | 2 + lib/src/quiver.dart | 2 + lib/src/render/category_renderer.dart | 2 + lib/src/render/documentation_renderer.dart | 2 + lib/src/render/element_type_renderer.dart | 2 + lib/src/render/enum_field_renderer.dart | 2 + lib/src/render/feature_renderer.dart | 2 + lib/src/render/language_feature_renderer.dart | 2 + lib/src/render/model_element_renderer.dart | 2 + lib/src/render/parameter_renderer.dart | 2 + lib/src/render/renderer_factory.dart | 2 + lib/src/render/source_code_renderer.dart | 2 + lib/src/render/template_renderer.dart | 2 + lib/src/render/type_parameters_renderer.dart | 2 + lib/src/render/typedef_renderer.dart | 2 + lib/src/source_linker.dart | 2 + lib/src/special_elements.dart | 2 + lib/src/tool_definition.dart | 2 + lib/src/tool_runner.dart | 2 + lib/src/tuple.dart | 2 + lib/src/utils.dart | 3 + lib/src/warnings.dart | 2 + pubspec.yaml | 4 +- .../comment_referable_test.dart | 2 + test/comment_referable/parser_test.dart | 2 + test/dartdoc_options_test.dart | 2 + test/documentation_comment_test.dart | 2 + test/end2end/dartdoc_integration_test.dart | 2 + test/end2end/dartdoc_test.dart | 2 + test/end2end/model_special_cases_test.dart | 2 + test/end2end/model_test.dart | 2 + test/grind_test.dart | 2 + test/html_generator_test.dart | 2 + test/io_utils_test.dart | 2 + test/library_test.dart | 2 + test/markdown_processor_test.dart | 2 + test/model_utils_test.dart | 2 + test/mustachio/aot_compiler_builder_test.dart | 2 + test/mustachio/aot_compiler_render_test.dart | 2 + test/mustachio/builder_test_base.dart | 2 + .../mustachio/foo.aot_renderers_for_html.dart | 1 + test/mustachio/foo.aot_renderers_for_md.dart | 1 + test/mustachio/foo.dart | 2 + test/mustachio/foo.runtime_renderers.dart | 1 + test/mustachio/parser_test.dart | 2 + test/mustachio/render_tests_test.dart | 2 + test/mustachio/renderers_output_test.dart | 2 + .../runtime_renderer_builder_test.dart | 2 + .../runtime_renderer_render_test.dart | 2 + test/package_meta_test.dart | 2 + test/package_test.dart | 2 + test/quiver_test.dart | 2 + test/render/template_renderer_test.dart | 2 + test/resource_loader_test.dart | 2 + test/source_linker_test.dart | 2 + test/src/utils.dart | 2 + test/tool_runner_test.dart | 2 + test/utils_test.dart | 2 + test/warnings_test.dart | 2 + tool/builder.dart | 2 + tool/doc_packages.dart | 2 + tool/grind.dart | 6 ++ tool/mustachio/builder.dart | 2 + tool/mustachio/codegen_aot_compiler.dart | 3 + tool/mustachio/codegen_runtime_renderer.dart | 3 + tool/mustachio/utilities.dart | 2 + tool/subprocess_launcher.dart | 2 + tool/travis.sh | 3 + 149 files changed, 377 insertions(+), 19 deletions(-) create mode 100644 .github/workflows/nnbd-test.yaml diff --git a/.github/workflows/nnbd-test.yaml b/.github/workflows/nnbd-test.yaml new file mode 100644 index 0000000000..fdeaaaf0e0 --- /dev/null +++ b/.github/workflows/nnbd-test.yaml @@ -0,0 +1,70 @@ +name: Test + +on: + # Run CI on pushes to the main branch, and on PRs against main. + push: + branches: [ master ] + pull_request: + branches: [ master ] + schedule: + - cron: 0 15 * * * + +env: + PUB_ENVIRONMENT: bot.github + +jobs: + test: + runs-on: ${{ matrix.os }} + strategy: + fail-fast: false + matrix: + os: [ubuntu-latest] + sdk: [dev, stable] + job: [main, flutter, sdk-analyzer, packages, sdk-docs] + include: + - os: macos-latest + sdk: dev + job: main + - os: windows-latest + sdk: dev + job: main + exclude: + # Do not try to run flutter against the "stable" sdk, + # it is unlikely to work and produces uninteresting + # results. + - sdk: stable + job: flutter + - sdk: stable + job: sdk-analyzer + + steps: + - name: Configure git + if: runner.os == 'Windows' + run: git config --global core.autocrlf input + - uses: actions/checkout@v2 + - uses: dart-lang/setup-dart@v1.0 + with: + sdk: ${{ matrix.sdk }} + - name: Install dependencies + run: dart pub get + - name: ${{ matrix.job }} + if: runner.os != 'Windows' + run: ./tool/travis.sh + env: + DARTDOC_BOT: ${{ matrix.job }} + #COVERAGE_TOKEN: true # this needs to be set to enable coverage + - name: ${{ matrix.job }} + if: runner.os == 'Windows' && matrix.job == 'main' + run: dart run grinder buildbot + env: + DARTDOC_BOT: ${{ matrix.job }} + # - id: coverage + # name: Upload coverage + # if: runner.os == 'Linux' && matrix.job == 'main' && matrix.sdk == 'dev' + # uses: coverallsapp/github-action@v1.1.2 + # with: + # github-token: ${{ secrets.GITHUB_TOKEN }} + # path-to-lcov: lcov.info + # - name: Echo coveralls api result + # if: runner.os == 'Linux' && matrix.job == 'main' && matrix.sdk == 'dev' + # run: echo ${{ steps.coverage.outputs['coveralls-api-result'] }} diff --git a/.github/workflows/test.yaml b/.github/workflows/test.yaml index fdeaaaf0e0..4f3f3c50c9 100644 --- a/.github/workflows/test.yaml +++ b/.github/workflows/test.yaml @@ -1,11 +1,11 @@ -name: Test +name: Test - NNBD branch on: # Run CI on pushes to the main branch, and on PRs against main. push: - branches: [ master ] + branches: [ nnbd ] pull_request: - branches: [ master ] + branches: [ nnbd ] schedule: - cron: 0 15 * * * @@ -19,23 +19,15 @@ jobs: fail-fast: false matrix: os: [ubuntu-latest] - sdk: [dev, stable] - job: [main, flutter, sdk-analyzer, packages, sdk-docs] + sdk: [dev] + job: [nnbd, flutter, sdk-analyzer, packages, sdk-docs] include: - os: macos-latest sdk: dev - job: main + job: nnbd - os: windows-latest sdk: dev - job: main - exclude: - # Do not try to run flutter against the "stable" sdk, - # it is unlikely to work and produces uninteresting - # results. - - sdk: stable - job: flutter - - sdk: stable - job: sdk-analyzer + job: nnbd steps: - name: Configure git @@ -54,8 +46,8 @@ jobs: DARTDOC_BOT: ${{ matrix.job }} #COVERAGE_TOKEN: true # this needs to be set to enable coverage - name: ${{ matrix.job }} - if: runner.os == 'Windows' && matrix.job == 'main' - run: dart run grinder buildbot + if: runner.os == 'Windows' && matrix.job == 'nnbd' + run: dart run grinder buildbot-no-publish env: DARTDOC_BOT: ${{ matrix.job }} # - id: coverage diff --git a/bin/dartdoc.dart b/bin/dartdoc.dart index 83b3f6180f..9b9b87a961 100644 --- a/bin/dartdoc.dart +++ b/bin/dartdoc.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library dartdoc.bin; import 'dart:async'; diff --git a/lib/dartdoc.dart b/lib/dartdoc.dart index 70c31c775d..c4a8649a33 100644 --- a/lib/dartdoc.dart +++ b/lib/dartdoc.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + /// A documentation generator for Dart. /// /// Library interface is currently under heavy construction and may change diff --git a/lib/options.dart b/lib/options.dart index 537c83084f..3a39c4e8fe 100644 --- a/lib/options.dart +++ b/lib/options.dart @@ -1,3 +1,5 @@ +// @dart=2.9 + import 'dart:io' show stderr, exitCode; import 'package:analyzer/file_system/file_system.dart'; diff --git a/lib/src/comment_references/model_comment_reference.dart b/lib/src/comment_references/model_comment_reference.dart index 7d6e0fcbfb..7416994650 100644 --- a/lib/src/comment_references/model_comment_reference.dart +++ b/lib/src/comment_references/model_comment_reference.dart @@ -2,6 +2,9 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. // + +// @dart=2.9 + import 'package:analyzer/dart/ast/ast.dart'; import 'package:analyzer/dart/element/element.dart'; import 'package:analyzer/file_system/file_system.dart'; diff --git a/lib/src/comment_references/parser.dart b/lib/src/comment_references/parser.dart index 6b09ccd308..37d507bd0e 100644 --- a/lib/src/comment_references/parser.dart +++ b/lib/src/comment_references/parser.dart @@ -2,6 +2,9 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. // + +// @dart=2.9 + import 'package:charcode/charcode.dart'; import 'package:meta/meta.dart'; diff --git a/lib/src/dartdoc_options.dart b/lib/src/dartdoc_options.dart index b8eba96f65..00ae7448c7 100644 --- a/lib/src/dartdoc_options.dart +++ b/lib/src/dartdoc_options.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + /// /// dartdoc's dartdoc_options.yaml configuration file follows similar loading /// semantics to that of analysis_options.yaml, diff --git a/lib/src/element_type.dart b/lib/src/element_type.dart index b56dca3336..95f0429db2 100644 --- a/lib/src/element_type.dart +++ b/lib/src/element_type.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + /// The models used to represent Dart code. library dartdoc.element_type; diff --git a/lib/src/experiment_options.dart b/lib/src/experiment_options.dart index 017dc942f3..5bf0edd84a 100644 --- a/lib/src/experiment_options.dart +++ b/lib/src/experiment_options.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + /// /// Implementation of Dart language experiment option handling for dartdoc. /// See https://github.com/dart-lang/sdk/blob/master/docs/process/experimental-flags.md. diff --git a/lib/src/generator/dartdoc_generator_backend.dart b/lib/src/generator/dartdoc_generator_backend.dart index 8b2d6aae8c..44967238da 100644 --- a/lib/src/generator/dartdoc_generator_backend.dart +++ b/lib/src/generator/dartdoc_generator_backend.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/file_system/file_system.dart'; import 'package:dartdoc/dartdoc.dart'; import 'package:dartdoc/options.dart'; diff --git a/lib/src/generator/empty_generator.dart b/lib/src/generator/empty_generator.dart index bd2dbb2cfb..4962848af5 100644 --- a/lib/src/generator/empty_generator.dart +++ b/lib/src/generator/empty_generator.dart @@ -1,3 +1,5 @@ +// @dart=2.9 + library dartdoc.empty_generator; import 'package:dartdoc/src/dartdoc_options.dart'; diff --git a/lib/src/generator/generator.dart b/lib/src/generator/generator.dart index 3253d60071..2a5c2f319e 100644 --- a/lib/src/generator/generator.dart +++ b/lib/src/generator/generator.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + /// A library containing an abstract documentation generator. library dartdoc.generator; diff --git a/lib/src/generator/generator_frontend.dart b/lib/src/generator/generator_frontend.dart index 08d9f3caff..30e31ab184 100644 --- a/lib/src/generator/generator_frontend.dart +++ b/lib/src/generator/generator_frontend.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/generator/generator.dart'; import 'package:dartdoc/src/logging.dart'; import 'package:dartdoc/src/model/model.dart'; diff --git a/lib/src/generator/generator_utils.dart b/lib/src/generator/generator_utils.dart index 122e927605..83b7860b7b 100644 --- a/lib/src/generator/generator_utils.dart +++ b/lib/src/generator/generator_utils.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'dart:convert'; import 'package:collection/collection.dart'; diff --git a/lib/src/generator/html_generator.dart b/lib/src/generator/html_generator.dart index bf73bcc889..81f00dd9b9 100644 --- a/lib/src/generator/html_generator.dart +++ b/lib/src/generator/html_generator.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library dartdoc.html_generator; import 'package:analyzer/file_system/file_system.dart'; diff --git a/lib/src/generator/markdown_generator.dart b/lib/src/generator/markdown_generator.dart index e51e7b477b..d60d4c9735 100644 --- a/lib/src/generator/markdown_generator.dart +++ b/lib/src/generator/markdown_generator.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/file_system/file_system.dart'; import 'package:dartdoc/options.dart'; import 'package:dartdoc/src/generator/dartdoc_generator_backend.dart'; diff --git a/lib/src/generator/resource_loader.dart b/lib/src/generator/resource_loader.dart index b4f77842d3..aa5a53b4e3 100644 --- a/lib/src/generator/resource_loader.dart +++ b/lib/src/generator/resource_loader.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + /// Make it possible to load resources from the dartdoc code repository. library dartdoc.resource_loader; diff --git a/lib/src/generator/template_data.dart b/lib/src/generator/template_data.dart index 594816fd50..e505359425 100644 --- a/lib/src/generator/template_data.dart +++ b/lib/src/generator/template_data.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/model/model.dart'; typedef ContainerSidebar = String Function( diff --git a/lib/src/generator/templates.aot_renderers_for_html.dart b/lib/src/generator/templates.aot_renderers_for_html.dart index 0ece2698bb..8eb4ee4fcd 100644 --- a/lib/src/generator/templates.aot_renderers_for_html.dart +++ b/lib/src/generator/templates.aot_renderers_for_html.dart @@ -7,6 +7,7 @@ // the variable is not used; generally when the section is checking if a // non-bool, non-Iterable field is non-null. // ignore_for_file: unused_local_variable +// @dart=2.9 import 'dart:convert' as _i18; diff --git a/lib/src/generator/templates.aot_renderers_for_md.dart b/lib/src/generator/templates.aot_renderers_for_md.dart index 32f53245a2..81f508f7c0 100644 --- a/lib/src/generator/templates.aot_renderers_for_md.dart +++ b/lib/src/generator/templates.aot_renderers_for_md.dart @@ -7,6 +7,7 @@ // the variable is not used; generally when the section is checking if a // non-bool, non-Iterable field is non-null. // ignore_for_file: unused_local_variable +// @dart=2.9 import 'dart:convert' as _i18; diff --git a/lib/src/generator/templates.dart b/lib/src/generator/templates.dart index 7d99dbf768..ae57a18a50 100644 --- a/lib/src/generator/templates.dart +++ b/lib/src/generator/templates.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + @Renderer(#renderCategory, Context(), 'category', visibleTypes: _visibleTypes) @Renderer(#renderClass, Context(), 'class') diff --git a/lib/src/generator/templates.runtime_renderers.dart b/lib/src/generator/templates.runtime_renderers.dart index 1c0afd7366..476d4695a1 100644 --- a/lib/src/generator/templates.runtime_renderers.dart +++ b/lib/src/generator/templates.runtime_renderers.dart @@ -5,6 +5,7 @@ // ignore_for_file: camel_case_types, deprecated_member_use_from_same_package // ignore_for_file: unused_import +// @dart=2.9 import 'package:dartdoc/dartdoc.dart'; import 'package:dartdoc/src/generator/template_data.dart'; import 'package:dartdoc/src/model/annotation.dart'; diff --git a/lib/src/io_utils.dart b/lib/src/io_utils.dart index 2be1ffa625..97a95c18a6 100644 --- a/lib/src/io_utils.dart +++ b/lib/src/io_utils.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + /// This is a helper library to make working with io easier. library dartdoc.io_utils; diff --git a/lib/src/logging.dart b/lib/src/logging.dart index b56a8d39c1..8c87b968c7 100644 --- a/lib/src/logging.dart +++ b/lib/src/logging.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'dart:convert'; import 'dart:io' show stderr, stdout; diff --git a/lib/src/markdown_processor.dart b/lib/src/markdown_processor.dart index 74d7f9c2ea..08a02797c9 100644 --- a/lib/src/markdown_processor.dart +++ b/lib/src/markdown_processor.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + /// Utility code to convert markdown comments to html. library dartdoc.markdown_processor; diff --git a/lib/src/matching_link_result.dart b/lib/src/matching_link_result.dart index 5cd1130916..f19d9b10f8 100644 --- a/lib/src/matching_link_result.dart +++ b/lib/src/matching_link_result.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/element_type.dart'; import 'package:dartdoc/src/model/comment_referable.dart'; import 'package:dartdoc/src/model/model.dart'; diff --git a/lib/src/model/accessor.dart b/lib/src/model/accessor.dart index 48daf92fdf..2d598809f9 100644 --- a/lib/src/model/accessor.dart +++ b/lib/src/model/accessor.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:analyzer/source/line_info.dart'; import 'package:analyzer/src/dart/element/member.dart' show ExecutableMember; diff --git a/lib/src/model/annotation.dart b/lib/src/model/annotation.dart index 0e6bc696a6..d03a8a2835 100644 --- a/lib/src/model/annotation.dart +++ b/lib/src/model/annotation.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:dartdoc/src/element_type.dart'; import 'package:dartdoc/src/model/feature.dart'; diff --git a/lib/src/model/canonicalization.dart b/lib/src/model/canonicalization.dart index b22a9e6e9c..ba6ccba6f8 100644 --- a/lib/src/model/canonicalization.dart +++ b/lib/src/model/canonicalization.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/comment_references/model_comment_reference.dart'; import 'package:dartdoc/src/model/model.dart'; diff --git a/lib/src/model/categorization.dart b/lib/src/model/categorization.dart index 5652e1209f..f477773af1 100644 --- a/lib/src/model/categorization.dart +++ b/lib/src/model/categorization.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/model/model.dart'; final RegExp _categoryRegExp = RegExp( diff --git a/lib/src/model/category.dart b/lib/src/model/category.dart index 02e3d96a7a..a6c5c9916a 100644 --- a/lib/src/model/category.dart +++ b/lib/src/model/category.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:analyzer/file_system/file_system.dart'; import 'package:dartdoc/src/comment_references/model_comment_reference.dart'; diff --git a/lib/src/model/class.dart b/lib/src/model/class.dart index db3f826765..63e4c9c278 100644 --- a/lib/src/model/class.dart +++ b/lib/src/model/class.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:analyzer/dart/element/type.dart'; import 'package:dartdoc/src/element_type.dart'; diff --git a/lib/src/model/comment_referable.dart b/lib/src/model/comment_referable.dart index d7696cfa0e..224b2409bd 100644 --- a/lib/src/model/comment_referable.dart +++ b/lib/src/model/comment_referable.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + /// /// Code for managing comment reference lookups in dartdoc. /// diff --git a/lib/src/model/constructor.dart b/lib/src/model/constructor.dart index 9a01ea5871..66b22317bf 100644 --- a/lib/src/model/constructor.dart +++ b/lib/src/model/constructor.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:analyzer/source/line_info.dart'; import 'package:dartdoc/src/element_type.dart'; diff --git a/lib/src/model/container.dart b/lib/src/model/container.dart index 75becea76b..13adf614a5 100644 --- a/lib/src/model/container.dart +++ b/lib/src/model/container.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:analyzer/dart/element/scope.dart'; import 'package:dartdoc/src/model/comment_referable.dart'; diff --git a/lib/src/model/container_member.dart b/lib/src/model/container_member.dart index 1898bc0ba0..f3ec632515 100644 --- a/lib/src/model/container_member.dart +++ b/lib/src/model/container_member.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/model/feature.dart'; import 'package:dartdoc/src/model/model.dart'; import 'package:meta/meta.dart'; diff --git a/lib/src/model/documentable.dart b/lib/src/model/documentable.dart index 4779b0bda6..dc773426b8 100644 --- a/lib/src/model/documentable.dart +++ b/lib/src/model/documentable.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/file_system/file_system.dart'; import 'package:dartdoc/src/dartdoc_options.dart'; import 'package:dartdoc/src/io_utils.dart'; diff --git a/lib/src/model/documentation.dart b/lib/src/model/documentation.dart index 44dc46d891..8830e78d2c 100644 --- a/lib/src/model/documentation.dart +++ b/lib/src/model/documentation.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/comment_references/model_comment_reference.dart'; import 'package:dartdoc/src/markdown_processor.dart'; import 'package:dartdoc/src/model/model.dart'; diff --git a/lib/src/model/documentation_comment.dart b/lib/src/model/documentation_comment.dart index 1422cc8f5b..ae8a5335ff 100644 --- a/lib/src/model/documentation_comment.dart +++ b/lib/src/model/documentation_comment.dart @@ -1,3 +1,5 @@ +// @dart=2.9 + import 'package:args/args.dart'; import 'package:crypto/crypto.dart' as crypto; import 'package:dartdoc/src/model/model.dart'; diff --git a/lib/src/model/dynamic.dart b/lib/src/model/dynamic.dart index a345f4c8c6..4d130dd65e 100644 --- a/lib/src/model/dynamic.dart +++ b/lib/src/model/dynamic.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:dartdoc/src/element_type.dart'; import 'package:dartdoc/src/model/comment_referable.dart'; diff --git a/lib/src/model/enclosed_element.dart b/lib/src/model/enclosed_element.dart index 228be4b30a..bc285f4505 100644 --- a/lib/src/model/enclosed_element.dart +++ b/lib/src/model/enclosed_element.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/model/model.dart'; /// An element that is enclosed by some other element. diff --git a/lib/src/model/enum.dart b/lib/src/model/enum.dart index c6c6da6f85..93762618cb 100644 --- a/lib/src/model/enum.dart +++ b/lib/src/model/enum.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + // TODO(jcollins-g): Consider Enum as subclass of Container? import 'package:analyzer/dart/element/element.dart'; import 'package:dartdoc/src/model/model.dart'; diff --git a/lib/src/model/extendable.dart b/lib/src/model/extendable.dart index bb496c6b4f..909bd30a13 100644 --- a/lib/src/model/extendable.dart +++ b/lib/src/model/extendable.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/model/model.dart'; /// Mixin for subclasses of [ModelElement] representing Elements that can be diff --git a/lib/src/model/extension.dart b/lib/src/model/extension.dart index ff0704c5af..b189b42fc9 100644 --- a/lib/src/model/extension.dart +++ b/lib/src/model/extension.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:dartdoc/src/element_type.dart'; import 'package:dartdoc/src/model/comment_referable.dart'; diff --git a/lib/src/model/extension_target.dart b/lib/src/model/extension_target.dart index bea6e7c65f..3291c2de05 100644 --- a/lib/src/model/extension_target.dart +++ b/lib/src/model/extension_target.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/element_type.dart'; import 'package:dartdoc/src/model/model.dart'; diff --git a/lib/src/model/feature.dart b/lib/src/model/feature.dart index c899c09be1..eaa2638c8b 100644 --- a/lib/src/model/feature.dart +++ b/lib/src/model/feature.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:collection/collection.dart'; import 'package:dartdoc/src/model/privacy.dart'; diff --git a/lib/src/model/feature_set.dart b/lib/src/model/feature_set.dart index f3bbb58daf..31b67d84cf 100644 --- a/lib/src/model/feature_set.dart +++ b/lib/src/model/feature_set.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/model/language_feature.dart'; import 'package:dartdoc/src/model/model.dart'; diff --git a/lib/src/model/field.dart b/lib/src/model/field.dart index d259ff916d..0542828abe 100644 --- a/lib/src/model/field.dart +++ b/lib/src/model/field.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:analyzer/src/dart/element/element.dart'; import 'package:dartdoc/src/model/feature.dart'; diff --git a/lib/src/model/getter_setter_combo.dart b/lib/src/model/getter_setter_combo.dart index 134cd6c045..53d353e53a 100644 --- a/lib/src/model/getter_setter_combo.dart +++ b/lib/src/model/getter_setter_combo.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'dart:convert'; import 'package:analyzer/dart/ast/ast.dart' diff --git a/lib/src/model/indexable.dart b/lib/src/model/indexable.dart index 0e46d0d1fd..24d47da254 100644 --- a/lib/src/model/indexable.dart +++ b/lib/src/model/indexable.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/model/model.dart'; /// Something able to be indexed. diff --git a/lib/src/model/inheritable.dart b/lib/src/model/inheritable.dart index 5b6a9dd4cb..d3d01c25a1 100644 --- a/lib/src/model/inheritable.dart +++ b/lib/src/model/inheritable.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/model/feature.dart'; import 'package:dartdoc/src/model/model.dart'; import 'package:dartdoc/src/special_elements.dart'; diff --git a/lib/src/model/language_feature.dart b/lib/src/model/language_feature.dart index 9045675402..79f65ed7f2 100644 --- a/lib/src/model/language_feature.dart +++ b/lib/src/model/language_feature.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/render/language_feature_renderer.dart'; const Map _featureDescriptions = { diff --git a/lib/src/model/library.dart b/lib/src/model/library.dart index 0d473879b0..42a11c933d 100644 --- a/lib/src/model/library.dart +++ b/lib/src/model/library.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'dart:collection'; import 'package:analyzer/dart/ast/ast.dart' hide CommentReference; diff --git a/lib/src/model/library_container.dart b/lib/src/model/library_container.dart index 2a10757c4c..46c94593d5 100644 --- a/lib/src/model/library_container.dart +++ b/lib/src/model/library_container.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:collection/collection.dart'; import 'package:dartdoc/src/model/model.dart'; import 'package:dartdoc/src/model_utils.dart' as model_utils; diff --git a/lib/src/model/locatable.dart b/lib/src/model/locatable.dart index f140fb90ca..94d03d1ae0 100644 --- a/lib/src/model/locatable.dart +++ b/lib/src/model/locatable.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart' show Element; /// Something that can be located for warning purposes. diff --git a/lib/src/model/method.dart b/lib/src/model/method.dart index 05c6f12c3e..9873457d29 100644 --- a/lib/src/model/method.dart +++ b/lib/src/model/method.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:analyzer/source/line_info.dart'; import 'package:analyzer/src/dart/element/member.dart' show ExecutableMember; diff --git a/lib/src/model/mixin.dart b/lib/src/model/mixin.dart index 6daaa12270..424c8b9fa2 100644 --- a/lib/src/model/mixin.dart +++ b/lib/src/model/mixin.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:analyzer/dart/element/type.dart'; import 'package:dartdoc/src/element_type.dart'; diff --git a/lib/src/model/model.dart b/lib/src/model/model.dart index 34557bf9ef..9591fe6394 100644 --- a/lib/src/model/model.dart +++ b/lib/src/model/model.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + export 'accessor.dart'; export 'canonicalization.dart'; export 'categorization.dart'; diff --git a/lib/src/model/model_element.dart b/lib/src/model/model_element.dart index f01ce12963..f922194ceb 100644 --- a/lib/src/model/model_element.dart +++ b/lib/src/model/model_element.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + /// The models used to represent Dart code. library dartdoc.models; diff --git a/lib/src/model/model_function.dart b/lib/src/model/model_function.dart index 236f1e6ea6..419f2fd9e1 100644 --- a/lib/src/model/model_function.dart +++ b/lib/src/model/model_function.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:dartdoc/src/element_type.dart'; import 'package:dartdoc/src/model/comment_referable.dart'; diff --git a/lib/src/model/model_node.dart b/lib/src/model/model_node.dart index af9e9882eb..dbd48274b1 100644 --- a/lib/src/model/model_node.dart +++ b/lib/src/model/model_node.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/ast/ast.dart'; import 'package:analyzer/dart/element/element.dart'; import 'package:analyzer/file_system/file_system.dart'; diff --git a/lib/src/model/nameable.dart b/lib/src/model/nameable.dart index 761ea0150c..8843244534 100644 --- a/lib/src/model/nameable.dart +++ b/lib/src/model/nameable.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:collection/collection.dart'; import 'locatable.dart'; diff --git a/lib/src/model/never.dart b/lib/src/model/never.dart index f3099925e2..ad67fa774e 100644 --- a/lib/src/model/never.dart +++ b/lib/src/model/never.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:dartdoc/src/model/comment_referable.dart'; import 'package:dartdoc/src/model/model.dart'; diff --git a/lib/src/model/operator.dart b/lib/src/model/operator.dart index 68551e541c..77b58e384f 100644 --- a/lib/src/model/operator.dart +++ b/lib/src/model/operator.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:analyzer/src/dart/element/member.dart' show Member; import 'package:dartdoc/src/comment_references/parser.dart'; diff --git a/lib/src/model/package.dart b/lib/src/model/package.dart index 327207a6b8..e0bb6e4a8d 100644 --- a/lib/src/model/package.dart +++ b/lib/src/model/package.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:analyzer/file_system/file_system.dart'; import 'package:dartdoc/src/comment_references/model_comment_reference.dart'; diff --git a/lib/src/model/package_builder.dart b/lib/src/model/package_builder.dart index d2e90ff489..ffeb4dfdf1 100644 --- a/lib/src/model/package_builder.dart +++ b/lib/src/model/package_builder.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'dart:async'; import 'package:analyzer/dart/analysis/analysis_context_collection.dart'; diff --git a/lib/src/model/package_graph.dart b/lib/src/model/package_graph.dart index 7ac8c07122..d0ea3e7b29 100644 --- a/lib/src/model/package_graph.dart +++ b/lib/src/model/package_graph.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'dart:collection'; import 'package:analyzer/dart/ast/ast.dart' hide CommentReference; diff --git a/lib/src/model/parameter.dart b/lib/src/model/parameter.dart index 0d39fa89a4..ce53e205fa 100644 --- a/lib/src/model/parameter.dart +++ b/lib/src/model/parameter.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:analyzer/src/dart/element/member.dart' show ParameterMember; import 'package:dartdoc/src/element_type.dart'; diff --git a/lib/src/model/prefix.dart b/lib/src/model/prefix.dart index 627ab555d6..0e97aeaf4a 100644 --- a/lib/src/model/prefix.dart +++ b/lib/src/model/prefix.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:analyzer/dart/element/scope.dart'; import 'package:analyzer/src/dart/element/element.dart'; diff --git a/lib/src/model/privacy.dart b/lib/src/model/privacy.dart index 9961eb0dda..0b00685aa7 100644 --- a/lib/src/model/privacy.dart +++ b/lib/src/model/privacy.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + /// Classes implementing this have a public/private distinction. abstract class Privacy { bool get isPublic; diff --git a/lib/src/model/source_code_mixin.dart b/lib/src/model/source_code_mixin.dart index 1c09f98d13..c36b5cb244 100644 --- a/lib/src/model/source_code_mixin.dart +++ b/lib/src/model/source_code_mixin.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:analyzer/source/line_info.dart'; import 'package:dartdoc/src/model/model.dart'; diff --git a/lib/src/model/top_level_container.dart b/lib/src/model/top_level_container.dart index 0f29d608cb..183e6f1620 100644 --- a/lib/src/model/top_level_container.dart +++ b/lib/src/model/top_level_container.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/model/model.dart'; import 'package:dartdoc/src/model_utils.dart' as model_utils; diff --git a/lib/src/model/top_level_variable.dart b/lib/src/model/top_level_variable.dart index 3046a60b77..ea61044977 100644 --- a/lib/src/model/top_level_variable.dart +++ b/lib/src/model/top_level_variable.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:dartdoc/src/model/comment_referable.dart'; import 'package:dartdoc/src/model/feature.dart'; diff --git a/lib/src/model/type_parameter.dart b/lib/src/model/type_parameter.dart index 54056ed6e0..100d4d895f 100644 --- a/lib/src/model/type_parameter.dart +++ b/lib/src/model/type_parameter.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:dartdoc/src/element_type.dart'; import 'package:dartdoc/src/model/comment_referable.dart'; diff --git a/lib/src/model/typedef.dart b/lib/src/model/typedef.dart index 7c47548a50..3398db83e4 100644 --- a/lib/src/model/typedef.dart +++ b/lib/src/model/typedef.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:analyzer/dart/element/type.dart'; import 'package:dartdoc/src/element_type.dart'; diff --git a/lib/src/model_utils.dart b/lib/src/model_utils.dart index 7a94cb7848..2f8b408a7d 100644 --- a/lib/src/model_utils.dart +++ b/lib/src/model_utils.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library dartdoc.model_utils; import 'dart:convert'; diff --git a/lib/src/mustachio/annotations.dart b/lib/src/mustachio/annotations.dart index 17e837983e..e7854432ec 100644 --- a/lib/src/mustachio/annotations.dart +++ b/lib/src/mustachio/annotations.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + // See the Mustachio README at tool/mustachio/README.md for high-level // documentation. diff --git a/lib/src/mustachio/parser.dart b/lib/src/mustachio/parser.dart index 296f9861e1..a33e3c10f7 100644 --- a/lib/src/mustachio/parser.dart +++ b/lib/src/mustachio/parser.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + // See the Mustachio README at tool/mustachio/README.md for high-level // documentation. diff --git a/lib/src/mustachio/renderer_base.dart b/lib/src/mustachio/renderer_base.dart index 85fcfa8f9d..072594a264 100644 --- a/lib/src/mustachio/renderer_base.dart +++ b/lib/src/mustachio/renderer_base.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + // See the Mustachio README at tool/mustachio/README.md for high-level // documentation. diff --git a/lib/src/package_config_provider.dart b/lib/src/package_config_provider.dart index f82922ce0c..61a0a50116 100644 --- a/lib/src/package_config_provider.dart +++ b/lib/src/package_config_provider.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'dart:io' as io; import 'package:analyzer/file_system/file_system.dart'; diff --git a/lib/src/package_meta.dart b/lib/src/package_meta.dart index 439e9c6d8c..d481f6019f 100644 --- a/lib/src/package_meta.dart +++ b/lib/src/package_meta.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library dartdoc.package_meta; import 'dart:convert'; diff --git a/lib/src/quiver.dart b/lib/src/quiver.dart index dd36843303..4e79c2883d 100644 --- a/lib/src/quiver.dart +++ b/lib/src/quiver.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + /// Methods in-lined from package:quiver. // From lib/iterables.dart: diff --git a/lib/src/render/category_renderer.dart b/lib/src/render/category_renderer.dart index 0b6e838bc4..45d6db7eec 100644 --- a/lib/src/render/category_renderer.dart +++ b/lib/src/render/category_renderer.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/model/category.dart'; /// A renderer for a [Category]. diff --git a/lib/src/render/documentation_renderer.dart b/lib/src/render/documentation_renderer.dart index 47b2351238..aab5206137 100644 --- a/lib/src/render/documentation_renderer.dart +++ b/lib/src/render/documentation_renderer.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:html/parser.dart' show parse; import 'package:markdown/markdown.dart' as md; import 'package:meta/meta.dart'; diff --git a/lib/src/render/element_type_renderer.dart b/lib/src/render/element_type_renderer.dart index 5ef50c24af..8e0aed669e 100644 --- a/lib/src/render/element_type_renderer.dart +++ b/lib/src/render/element_type_renderer.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/dartdoc.dart'; import 'package:dartdoc/src/render/parameter_renderer.dart'; diff --git a/lib/src/render/enum_field_renderer.dart b/lib/src/render/enum_field_renderer.dart index 99f370fbd5..b8f847a9c4 100644 --- a/lib/src/render/enum_field_renderer.dart +++ b/lib/src/render/enum_field_renderer.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/model/enum.dart'; abstract class EnumFieldRenderer { diff --git a/lib/src/render/feature_renderer.dart b/lib/src/render/feature_renderer.dart index 7cce8145ac..3eb18c1b60 100644 --- a/lib/src/render/feature_renderer.dart +++ b/lib/src/render/feature_renderer.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'dart:convert'; import 'package:dartdoc/src/model/annotation.dart'; diff --git a/lib/src/render/language_feature_renderer.dart b/lib/src/render/language_feature_renderer.dart index 5117d71623..24972ab9d9 100644 --- a/lib/src/render/language_feature_renderer.dart +++ b/lib/src/render/language_feature_renderer.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/model/language_feature.dart'; /// A renderer for a [LanguageFeature]. diff --git a/lib/src/render/model_element_renderer.dart b/lib/src/render/model_element_renderer.dart index 63885667ef..b37bc20de9 100644 --- a/lib/src/render/model_element_renderer.dart +++ b/lib/src/render/model_element_renderer.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/model/feature.dart'; import 'package:dartdoc/src/model/model_element.dart'; diff --git a/lib/src/render/parameter_renderer.dart b/lib/src/render/parameter_renderer.dart index b1e551e758..df0f17a970 100644 --- a/lib/src/render/parameter_renderer.dart +++ b/lib/src/render/parameter_renderer.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'dart:convert'; import 'package:analyzer/dart/element/type.dart'; diff --git a/lib/src/render/renderer_factory.dart b/lib/src/render/renderer_factory.dart index 9bc6d3ba11..a03f1bbfa4 100644 --- a/lib/src/render/renderer_factory.dart +++ b/lib/src/render/renderer_factory.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/dartdoc.dart'; import 'package:dartdoc/src/render/category_renderer.dart'; import 'package:dartdoc/src/render/documentation_renderer.dart'; diff --git a/lib/src/render/source_code_renderer.dart b/lib/src/render/source_code_renderer.dart index 0a15830d78..91ffec2d73 100644 --- a/lib/src/render/source_code_renderer.dart +++ b/lib/src/render/source_code_renderer.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'dart:convert'; /// Renderer for source code snippets extracted from source files. diff --git a/lib/src/render/template_renderer.dart b/lib/src/render/template_renderer.dart index 24da3e01ca..73475e2a70 100644 --- a/lib/src/render/template_renderer.dart +++ b/lib/src/render/template_renderer.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + abstract class LayoutRenderer { String composeLayoutTitle(String name, String kind, bool isDeprecated); } diff --git a/lib/src/render/type_parameters_renderer.dart b/lib/src/render/type_parameters_renderer.dart index 26d947a103..c205f79f2b 100644 --- a/lib/src/render/type_parameters_renderer.dart +++ b/lib/src/render/type_parameters_renderer.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/model/type_parameter.dart'; abstract class TypeParametersRenderer { diff --git a/lib/src/render/typedef_renderer.dart b/lib/src/render/typedef_renderer.dart index 0a0e224716..a491744c7b 100644 --- a/lib/src/render/typedef_renderer.dart +++ b/lib/src/render/typedef_renderer.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/model/type_parameter.dart'; import 'package:dartdoc/src/model/typedef.dart'; diff --git a/lib/src/source_linker.dart b/lib/src/source_linker.dart index 26d07329c5..5fc2313ce1 100644 --- a/lib/src/source_linker.dart +++ b/lib/src/source_linker.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + /// A library for getting external source code links for Dartdoc. library dartdoc.source_linker; diff --git a/lib/src/special_elements.dart b/lib/src/special_elements.dart index 67b45197b4..a58297ca4b 100644 --- a/lib/src/special_elements.dart +++ b/lib/src/special_elements.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + /// Handling for special elements within Dart. When identified these /// may alter the interpretation and documentation generated for other /// [ModelElement]s. diff --git a/lib/src/tool_definition.dart b/lib/src/tool_definition.dart index 039d501e5d..95046d815e 100644 --- a/lib/src/tool_definition.dart +++ b/lib/src/tool_definition.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'dart:async'; import 'package:analyzer/file_system/file_system.dart'; diff --git a/lib/src/tool_runner.dart b/lib/src/tool_runner.dart index 1cfa337f41..bc24e3fad8 100644 --- a/lib/src/tool_runner.dart +++ b/lib/src/tool_runner.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library dartdoc.tool_runner; import 'dart:io' show Process, ProcessException; diff --git a/lib/src/tuple.dart b/lib/src/tuple.dart index e4e1dfe926..a0655e03b8 100644 --- a/lib/src/tuple.dart +++ b/lib/src/tuple.dart @@ -1,5 +1,7 @@ // Copied from source at github.com/kseo/tuple/blob/470ed3aeb/lib/src/tuple.dart +// @dart=2.9 + // Original copyright: // Copyright (c) 2014, the tuple project authors. Please see the AUTHORS // file for details. All rights reserved. Use of this source code is governed diff --git a/lib/src/utils.dart b/lib/src/utils.dart index 0975566d07..5819b6d3c3 100644 --- a/lib/src/utils.dart +++ b/lib/src/utils.dart @@ -1,6 +1,9 @@ // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. + +// @dart=2.9 + library dartdoc.utils; final RegExp leadingWhiteSpace = RegExp(r'^([ \t]*)[^ ]'); diff --git a/lib/src/warnings.dart b/lib/src/warnings.dart index 505b8d5bea..f34b790e72 100644 --- a/lib/src/warnings.dart +++ b/lib/src/warnings.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'dart:collection'; import 'package:analyzer/dart/element/element.dart'; diff --git a/pubspec.yaml b/pubspec.yaml index d9d6e1e6b6..f421247c86 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -4,13 +4,13 @@ version: 1.0.2 description: A non-interactive HTML documentation generator for Dart source code. homepage: https://github.com/dart-lang/dartdoc environment: - sdk: '>=2.11.99 <3.0.0' + sdk: '>=2.12.0 <3.0.0' dependencies: analyzer: ^2.0.0 args: ^2.0.0 charcode: ^1.2.0 - collection: ^1.2.0 + collection: ^1.15.0-nullsafety.4 cli_util: ^0.3.0 crypto: ^3.0.0 glob: ^2.0.0 diff --git a/test/comment_referable/comment_referable_test.dart b/test/comment_referable/comment_referable_test.dart index 127d6262ef..84843b542c 100644 --- a/test/comment_referable/comment_referable_test.dart +++ b/test/comment_referable/comment_referable_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library dartdoc.comment_reference_test; import 'package:analyzer/dart/element/element.dart'; diff --git a/test/comment_referable/parser_test.dart b/test/comment_referable/parser_test.dart index b716408be7..7f35c82ea3 100644 --- a/test/comment_referable/parser_test.dart +++ b/test/comment_referable/parser_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/comment_references/parser.dart'; import 'package:test/test.dart'; diff --git a/test/dartdoc_options_test.dart b/test/dartdoc_options_test.dart index f10f85810a..95f7d38bab 100644 --- a/test/dartdoc_options_test.dart +++ b/test/dartdoc_options_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library dartdoc.options_test; import 'package:analyzer/file_system/file_system.dart'; diff --git a/test/documentation_comment_test.dart b/test/documentation_comment_test.dart index d6b5deb679..1650f759d9 100644 --- a/test/documentation_comment_test.dart +++ b/test/documentation_comment_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/file_system/file_system.dart'; import 'package:analyzer/file_system/memory_file_system.dart'; import 'package:analyzer/src/test_utilities/mock_sdk.dart'; diff --git a/test/end2end/dartdoc_integration_test.dart b/test/end2end/dartdoc_integration_test.dart index c8bddf94ab..c26398e314 100644 --- a/test/end2end/dartdoc_integration_test.dart +++ b/test/end2end/dartdoc_integration_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library dartdoc.dartdoc_integration_test; import 'dart:async'; diff --git a/test/end2end/dartdoc_test.dart b/test/end2end/dartdoc_test.dart index 91ccfc83f1..58640eee44 100644 --- a/test/end2end/dartdoc_test.dart +++ b/test/end2end/dartdoc_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library dartdoc.dartdoc_test; import 'dart:async'; diff --git a/test/end2end/model_special_cases_test.dart b/test/end2end/model_special_cases_test.dart index 159decd1a9..2ced723a72 100644 --- a/test/end2end/model_special_cases_test.dart +++ b/test/end2end/model_special_cases_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + /// This test library handles checks against the model for configurations /// that require different PackageGraph configurations. Since those /// take a long time to initialize, isolate them here to keep model_test diff --git a/test/end2end/model_test.dart b/test/end2end/model_test.dart index 9959891cc5..769ecd2935 100644 --- a/test/end2end/model_test.dart +++ b/test/end2end/model_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library dartdoc.model_test; import 'dart:io'; diff --git a/test/grind_test.dart b/test/grind_test.dart index 23087548cb..154cc7f3f5 100644 --- a/test/grind_test.dart +++ b/test/grind_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library dartdoc.io_utils_test; import 'package:test/test.dart'; diff --git a/test/html_generator_test.dart b/test/html_generator_test.dart index 899fb1b49d..291b1785a1 100644 --- a/test/html_generator_test.dart +++ b/test/html_generator_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/file_system/file_system.dart'; import 'package:analyzer/file_system/memory_file_system.dart'; import 'package:dartdoc/dartdoc.dart'; diff --git a/test/io_utils_test.dart b/test/io_utils_test.dart index ee24db4243..119d0421b8 100644 --- a/test/io_utils_test.dart +++ b/test/io_utils_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library dartdoc.io_utils_test; import 'package:dartdoc/src/io_utils.dart'; diff --git a/test/library_test.dart b/test/library_test.dart index fc25c8e7a3..4dff2f197a 100644 --- a/test/library_test.dart +++ b/test/library_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/file_system/file_system.dart'; import 'package:dartdoc/src/model/model.dart'; import 'package:dartdoc/src/package_config_provider.dart'; diff --git a/test/markdown_processor_test.dart b/test/markdown_processor_test.dart index 61a900bad2..9a5dce0a83 100644 --- a/test/markdown_processor_test.dart +++ b/test/markdown_processor_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library dartdoc.markdown_processor_test; import 'package:dartdoc/src/markdown_processor.dart'; diff --git a/test/model_utils_test.dart b/test/model_utils_test.dart index 850c2d4901..1705a51362 100644 --- a/test/model_utils_test.dart +++ b/test/model_utils_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library dartdoc.model_utils_test; import 'package:dartdoc/src/model_utils.dart'; diff --git a/test/mustachio/aot_compiler_builder_test.dart b/test/mustachio/aot_compiler_builder_test.dart index aa80b5cc66..33968513ac 100644 --- a/test/mustachio/aot_compiler_builder_test.dart +++ b/test/mustachio/aot_compiler_builder_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + @Timeout.factor(4) import 'dart:convert'; import 'package:analyzer/dart/element/element.dart'; diff --git a/test/mustachio/aot_compiler_render_test.dart b/test/mustachio/aot_compiler_render_test.dart index 1fafe717eb..37469af23b 100644 --- a/test/mustachio/aot_compiler_render_test.dart +++ b/test/mustachio/aot_compiler_render_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'dart:async'; import 'dart:convert' show json, utf8; import 'dart:io'; diff --git a/test/mustachio/builder_test_base.dart b/test/mustachio/builder_test_base.dart index 59a7ea9206..5a0fce3d9e 100644 --- a/test/mustachio/builder_test_base.dart +++ b/test/mustachio/builder_test_base.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:build/build.dart'; import 'package:build_test/build_test.dart'; diff --git a/test/mustachio/foo.aot_renderers_for_html.dart b/test/mustachio/foo.aot_renderers_for_html.dart index d75402395d..c56403bfdb 100644 --- a/test/mustachio/foo.aot_renderers_for_html.dart +++ b/test/mustachio/foo.aot_renderers_for_html.dart @@ -7,6 +7,7 @@ // the variable is not used; generally when the section is checking if a // non-bool, non-Iterable field is non-null. // ignore_for_file: unused_local_variable +// @dart=2.9 import 'dart:convert' as _i2; diff --git a/test/mustachio/foo.aot_renderers_for_md.dart b/test/mustachio/foo.aot_renderers_for_md.dart index e2e7c00b0a..ff78fe8ba1 100644 --- a/test/mustachio/foo.aot_renderers_for_md.dart +++ b/test/mustachio/foo.aot_renderers_for_md.dart @@ -7,6 +7,7 @@ // the variable is not used; generally when the section is checking if a // non-bool, non-Iterable field is non-null. // ignore_for_file: unused_local_variable +// @dart=2.9 import 'dart:convert' as _i2; diff --git a/test/mustachio/foo.dart b/test/mustachio/foo.dart index 08d046155d..3ef2a46f2f 100644 --- a/test/mustachio/foo.dart +++ b/test/mustachio/foo.dart @@ -1,3 +1,5 @@ +// @dart=2.9 + @Renderer.forTest(#renderFoo, Context(), 'foo', visibleTypes: {Property1, Property2, Property3}) @Renderer.forTest(#renderBar, Context(), 'bar') diff --git a/test/mustachio/foo.runtime_renderers.dart b/test/mustachio/foo.runtime_renderers.dart index 118a2c88b0..6a4960555b 100644 --- a/test/mustachio/foo.runtime_renderers.dart +++ b/test/mustachio/foo.runtime_renderers.dart @@ -5,6 +5,7 @@ // ignore_for_file: camel_case_types, deprecated_member_use_from_same_package // ignore_for_file: unused_import +// @dart=2.9 import 'package:dartdoc/dartdoc.dart'; import 'package:dartdoc/src/generator/template_data.dart'; import 'package:dartdoc/src/model/annotation.dart'; diff --git a/test/mustachio/parser_test.dart b/test/mustachio/parser_test.dart index a601a1d8f4..b612db6b25 100644 --- a/test/mustachio/parser_test.dart +++ b/test/mustachio/parser_test.dart @@ -1,3 +1,5 @@ +// @dart=2.9 + import 'package:dartdoc/src/mustachio/parser.dart'; import 'package:test/test.dart'; diff --git a/test/mustachio/render_tests_test.dart b/test/mustachio/render_tests_test.dart index 1282dd43fc..2b409addfa 100644 --- a/test/mustachio/render_tests_test.dart +++ b/test/mustachio/render_tests_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'dart:io'; import 'dart:isolate' show Isolate; diff --git a/test/mustachio/renderers_output_test.dart b/test/mustachio/renderers_output_test.dart index b1c3ec4446..b26c462750 100644 --- a/test/mustachio/renderers_output_test.dart +++ b/test/mustachio/renderers_output_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library dartdoc.dartdoc_test; import 'dart:async'; diff --git a/test/mustachio/runtime_renderer_builder_test.dart b/test/mustachio/runtime_renderer_builder_test.dart index 65dcf65c96..d84cb543fb 100644 --- a/test/mustachio/runtime_renderer_builder_test.dart +++ b/test/mustachio/runtime_renderer_builder_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + @Timeout.factor(2) import 'dart:convert'; import 'package:analyzer/dart/element/element.dart'; diff --git a/test/mustachio/runtime_renderer_render_test.dart b/test/mustachio/runtime_renderer_render_test.dart index a0dd698376..456423b9a3 100644 --- a/test/mustachio/runtime_renderer_render_test.dart +++ b/test/mustachio/runtime_renderer_render_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/file_system/file_system.dart'; import 'package:analyzer/file_system/memory_file_system.dart'; import 'package:dartdoc/src/mustachio/renderer_base.dart'; diff --git a/test/package_meta_test.dart b/test/package_meta_test.dart index 7339818a90..3c1c262097 100644 --- a/test/package_meta_test.dart +++ b/test/package_meta_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library dartdoc.package_utils_test; import 'package:dartdoc/src/io_utils.dart'; diff --git a/test/package_test.dart b/test/package_test.dart index ca93d97fae..4c44da5178 100644 --- a/test/package_test.dart +++ b/test/package_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/file_system/file_system.dart'; import 'package:analyzer/file_system/memory_file_system.dart'; import 'package:dartdoc/src/dartdoc_options.dart'; diff --git a/test/quiver_test.dart b/test/quiver_test.dart index eb8c2a98e7..341cce4568 100644 --- a/test/quiver_test.dart +++ b/test/quiver_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/quiver.dart'; import 'package:test/test.dart'; diff --git a/test/render/template_renderer_test.dart b/test/render/template_renderer_test.dart index 379da3e0aa..4d43a1daf5 100644 --- a/test/render/template_renderer_test.dart +++ b/test/render/template_renderer_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:dartdoc/src/render/template_renderer.dart'; import 'package:test/test.dart'; diff --git a/test/resource_loader_test.dart b/test/resource_loader_test.dart index aa915ba123..2962f71ba9 100644 --- a/test/resource_loader_test.dart +++ b/test/resource_loader_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library dartdoc.resource_loader_test; import 'package:analyzer/file_system/file_system.dart'; diff --git a/test/source_linker_test.dart b/test/source_linker_test.dart index 7c68a8d96b..adc591e34a 100644 --- a/test/source_linker_test.dart +++ b/test/source_linker_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library dartdoc.source_linker_test; import 'package:dartdoc/src/dartdoc_options.dart'; diff --git a/test/src/utils.dart b/test/src/utils.dart index 779fc77839..aa89a5b491 100644 --- a/test/src/utils.dart +++ b/test/src/utils.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library test_utils; import 'dart:io'; diff --git a/test/tool_runner_test.dart b/test/tool_runner_test.dart index 71515b1c70..015b50f0d1 100644 --- a/test/tool_runner_test.dart +++ b/test/tool_runner_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library dartdoc.model_test; import 'dart:io'; diff --git a/test/utils_test.dart b/test/utils_test.dart index 9556f3cc28..4dcf171d2b 100644 --- a/test/utils_test.dart +++ b/test/utils_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + library dartdoc.utils_test; import 'package:dartdoc/src/utils.dart'; diff --git a/test/warnings_test.dart b/test/warnings_test.dart index b4db31ee41..6f63e6b497 100644 --- a/test/warnings_test.dart +++ b/test/warnings_test.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + /// Unit tests for lib/src/warnings.dart. library dartdoc.warnings_test; diff --git a/tool/builder.dart b/tool/builder.dart index d77d109653..6a53d9d019 100644 --- a/tool/builder.dart +++ b/tool/builder.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'dart:async'; import 'package:build/build.dart'; diff --git a/tool/doc_packages.dart b/tool/doc_packages.dart index 0988498faa..b8ea616150 100644 --- a/tool/doc_packages.dart +++ b/tool/doc_packages.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + /// A CLI tool to generate documentation for packages from pub.dartlang.org. library dartdoc.doc_packages; diff --git a/tool/grind.dart b/tool/grind.dart index db4701cbcc..5485e95383 100644 --- a/tool/grind.dart +++ b/tool/grind.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'dart:async'; import 'dart:io' hide ProcessException; @@ -316,6 +318,10 @@ void presubmit() => null; @Depends(presubmit, longTest, testDartdoc) void buildbot() => null; +@Task('Run buildbot tests, but without publish test') +@Depends(analyze, dartfmt, checkBuild, smokeTest, longTest, testDartdoc) +void buildbotNoPublish() => null; + @Task('Generate docs for the Dart SDK') Future buildSdkDocs() async { log('building SDK docs'); diff --git a/tool/mustachio/builder.dart b/tool/mustachio/builder.dart index 85ed810b8e..17a39abae1 100644 --- a/tool/mustachio/builder.dart +++ b/tool/mustachio/builder.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:analyzer/dart/element/type.dart'; import 'package:analyzer/src/dart/element/member.dart'; diff --git a/tool/mustachio/codegen_aot_compiler.dart b/tool/mustachio/codegen_aot_compiler.dart index 2bd4b84a09..1e12843d15 100644 --- a/tool/mustachio/codegen_aot_compiler.dart +++ b/tool/mustachio/codegen_aot_compiler.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:analyzer/dart/element/type.dart'; import 'package:analyzer/dart/element/type_provider.dart'; @@ -67,6 +69,7 @@ Future compileTemplatesToRenderers( // the variable is not used; generally when the section is checking if a // non-bool, non-Iterable field is non-null. // ignore_for_file: unused_local_variable +// @dart=2.9 ${library.accept(DartEmitter.scoped(orderDirectives: true))} '''); diff --git a/tool/mustachio/codegen_runtime_renderer.dart b/tool/mustachio/codegen_runtime_renderer.dart index 4636e2478c..162c6a99b6 100644 --- a/tool/mustachio/codegen_runtime_renderer.dart +++ b/tool/mustachio/codegen_runtime_renderer.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'dart:collection'; import 'package:analyzer/dart/element/element.dart'; @@ -81,6 +83,7 @@ class RuntimeRenderersBuilder { // ignore_for_file: camel_case_types, deprecated_member_use_from_same_package // ignore_for_file: unused_import +// @dart=2.9 import 'package:dartdoc/dartdoc.dart'; import 'package:dartdoc/src/generator/template_data.dart'; import 'package:dartdoc/src/model/annotation.dart'; diff --git a/tool/mustachio/utilities.dart b/tool/mustachio/utilities.dart index 983c421a5e..920a6592b3 100644 --- a/tool/mustachio/utilities.dart +++ b/tool/mustachio/utilities.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; extension ClassExtensions on ClassElement { diff --git a/tool/subprocess_launcher.dart b/tool/subprocess_launcher.dart index e25646e753..4fc793fab4 100644 --- a/tool/subprocess_launcher.dart +++ b/tool/subprocess_launcher.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'dart:async'; import 'dart:convert'; import 'dart:io'; diff --git a/tool/travis.sh b/tool/travis.sh index 17f5607930..f9c33eb78e 100755 --- a/tool/travis.sh +++ b/tool/travis.sh @@ -42,6 +42,9 @@ elif [ "$DARTDOC_BOT" = "sdk-analyzer" ]; then echo "Running all tests against the SDK analyzer" unset COVERAGE_TOKEN pub run grinder test-with-analyzer-sdk +elif [ "$DARTDOC_BOT" = "nnbd" ]; then + echo "Running main dartdoc bot excluding publish test" + pub run grinder buildbot-no-publish else echo "Running main dartdoc bot" pub run grinder buildbot From 50f38ec2496de93ceadeef55270b99d515a23f4e Mon Sep 17 00:00:00 2001 From: Janice Collins Date: Wed, 18 Aug 2021 09:24:40 -0700 Subject: [PATCH 02/47] Merge master into nnbd branch (#2747) * Switch to using CompilationUnitElement.classes (#2743) * Prepare dartdoc_options for migration (#2745) * more specific imports in options * do not allow autoinitialization * dartfmt * parameterize the valueWithContext type * Use alternative constructors instead of externalizing, didn't realize the autodetect was so widely used * more subclasses * Empty commit to straighten out GitHub Actions --- lib/options.dart | 16 +++- lib/src/dartdoc_options.dart | 110 +++++++++++----------- lib/src/model/library.dart | 2 +- test/end2end/dartdoc_test.dart | 4 +- test/mustachio/renderers_output_test.dart | 4 +- test/src/utils.dart | 7 +- 6 files changed, 76 insertions(+), 67 deletions(-) diff --git a/lib/options.dart b/lib/options.dart index 3a39c4e8fe..92fe2224d3 100644 --- a/lib/options.dart +++ b/lib/options.dart @@ -4,8 +4,11 @@ import 'dart:io' show stderr, exitCode; import 'package:analyzer/file_system/file_system.dart'; import 'package:args/args.dart'; -import 'package:dartdoc/dartdoc.dart'; +import 'package:dartdoc/dartdoc.dart' show dartdocVersion, programName; +import 'package:dartdoc/src/dartdoc_options.dart'; +import 'package:dartdoc/src/generator/generator.dart'; import 'package:dartdoc/src/logging.dart'; +import 'package:dartdoc/src/package_meta.dart'; /// Helper class that consolidates option contexts for instantiating generators. class DartdocGeneratorOptionContext extends DartdocOptionContext { @@ -13,6 +16,10 @@ class DartdocGeneratorOptionContext extends DartdocOptionContext { DartdocOptionSet optionSet, Folder dir, ResourceProvider resourceProvider) : super(optionSet, dir, resourceProvider); + DartdocGeneratorOptionContext.fromDefaultContextLocation( + DartdocOptionSet optionSet, ResourceProvider resourceProvider) + : super.fromDefaultContextLocation(optionSet, resourceProvider); + // TODO(migration): Make late final with initializer when Null Safe. String _header; @@ -59,6 +66,9 @@ class DartdocProgramOptionContext extends DartdocGeneratorOptionContext DartdocProgramOptionContext( DartdocOptionSet optionSet, Folder dir, ResourceProvider resourceProvider) : super(optionSet, dir, resourceProvider); + DartdocProgramOptionContext.fromDefaultContextLocation( + DartdocOptionSet optionSet, ResourceProvider resourceProvider) + : super.fromDefaultContextLocation(optionSet, resourceProvider); bool get generateDocs => optionSet['generateDocs'].valueAt(context); bool get help => optionSet['help'].valueAt(context); @@ -120,8 +130,8 @@ Future parseOptions( DartdocProgramOptionContext config; try { - config = DartdocProgramOptionContext( - optionSet, null, packageMetaProvider.resourceProvider); + config = DartdocProgramOptionContext.fromDefaultContextLocation( + optionSet, packageMetaProvider.resourceProvider); } on DartdocOptionError catch (e) { stderr.writeln(' fatal error: ${e.message}'); stderr.writeln(''); diff --git a/lib/src/dartdoc_options.dart b/lib/src/dartdoc_options.dart index 00ae7448c7..a5ecfca71c 100644 --- a/lib/src/dartdoc_options.dart +++ b/lib/src/dartdoc_options.dart @@ -398,10 +398,10 @@ abstract class DartdocOption { bool get _isDouble => _kDoubleVal is T; - DartdocOption _parent; + DartdocOption _parent; /// The parent of this DartdocOption, or null if this is the root. - DartdocOption get parent => _parent; + DartdocOption get parent => _parent; final Map __yamlAtCanonicalPathCache = {}; @@ -426,18 +426,18 @@ abstract class DartdocOption { /// Throw [DartdocFileMissing] with a detailed error message indicating where /// the error came from when a file or directory option is missing. void _onMissing( - _OptionValueWithContext valueWithContext, String missingFilename); + _OptionValueWithContext valueWithContext, String missingFilename); /// Call [_onMissing] for every path that does not exist. - void _validatePaths(_OptionValueWithContext valueWithContext) { + void _validatePaths(_OptionValueWithContext valueWithContext) { if (!mustExist) return; assert(isDir || isFile); List resolvedPaths; var value = valueWithContext.value; if (value is String) { - resolvedPaths = [valueWithContext.resolvedValue]; + resolvedPaths = [valueWithContext.resolvedValue as String]; } else if (value is List) { - resolvedPaths = valueWithContext.resolvedValue as List; + resolvedPaths = valueWithContext.resolvedValue as List; } else if (value is Map) { resolvedPaths = (valueWithContext.resolvedValue as Map).values.toList(); } else { @@ -458,7 +458,7 @@ abstract class DartdocOption { /// For a [List] or [String] value, if [isDir] or [isFile] is set, /// resolve paths in value relative to canonicalPath. - T _handlePathsInContext(_OptionValueWithContext valueWithContext) { + T _handlePathsInContext(_OptionValueWithContext valueWithContext) { if (valueWithContext?.value == null || !(isDir || isFile || isGlob)) { return valueWithContext?.value; } @@ -474,15 +474,15 @@ abstract class DartdocOption { ArgResults get _argResults => root.__argResults; /// Set the parent of this [DartdocOption]. Do not call more than once. - set parent(DartdocOption newParent) { + set parent(DartdocOption newParent) { assert(_parent == null); _parent = newParent; } /// The root [DartdocOption] containing this object, or [this] if the object /// has no parent. - DartdocOption get root { - DartdocOption p = this; + DartdocOption get root { + DartdocOption p = this; while (p.parent != null) { p = p.parent; } @@ -492,7 +492,7 @@ abstract class DartdocOption { /// All object names starting at the root. Iterable get keys { var keyList = []; - DartdocOption option = this; + DartdocOption option = this; while (option?.name != null) { keyList.add(option.name); option = option.parent; @@ -501,7 +501,7 @@ abstract class DartdocOption { } /// Direct children of this node, mapped by name. - final Map> _children = {}; + final Map _children = {}; /// Return the calculated value of this option, given the directory as /// context. @@ -533,7 +533,7 @@ abstract class DartdocOption { resourceProvider.pathContext.basename(element.source.fullName)))); /// Adds a DartdocOption to the children of this DartdocOption. - void add(DartdocOption option) { + void add(DartdocOption option) { if (_children.containsKey(option.name)) { throw DartdocOptionError( 'Tried to add two children with the same name: ${option.name}'); @@ -547,7 +547,7 @@ abstract class DartdocOption { void _onAdd() {} /// Adds a list of dartdoc options to the children of this DartdocOption. - void addAll(Iterable> options) => options.forEach(add); + void addAll(Iterable options) => options.forEach(add); /// Get the immediate child of this node named [name]. DartdocOption operator [](String name) { @@ -555,7 +555,7 @@ abstract class DartdocOption { } /// Apply the function [visit] to [this] and all children. - void traverse(void Function(DartdocOption option) visit) { + void traverse(void Function(DartdocOption option) visit) { visit(this); _children.values.forEach((d) => d.traverse(visit)); } @@ -592,7 +592,7 @@ class DartdocOptionFileSynth extends DartdocOption @override void _onMissing( - _OptionValueWithContext valueWithContext, String missingPath) { + _OptionValueWithContext valueWithContext, String missingPath) { if (valueWithContext.definingFile != null) { _onMissingFromFiles(valueWithContext, missingPath); } else { @@ -634,7 +634,7 @@ class DartdocOptionArgSynth extends DartdocOption @override void _onMissing( - _OptionValueWithContext valueWithContext, String missingPath) { + _OptionValueWithContext valueWithContext, String missingPath) { _onMissingFromArgs(valueWithContext, missingPath); } @@ -689,12 +689,12 @@ abstract class DartdocSyntheticOption implements DartdocOption { } @override - void _onMissing(_OptionValueWithContext valueWithContext, - String missingPath) => + void _onMissing( + _OptionValueWithContext valueWithContext, String missingPath) => _onMissingFromSynthetic(valueWithContext, missingPath); void _onMissingFromSynthetic( - _OptionValueWithContext valueWithContext, String missingPath) { + _OptionValueWithContext valueWithContext, String missingPath) { var description = 'Synthetic configuration option $name from '; throw DartdocFileMissing( '$description, computed as ${valueWithContext.value}, resolves to ' @@ -702,7 +702,7 @@ abstract class DartdocSyntheticOption implements DartdocOption { } } -typedef OptionGenerator = Future>> Function( +typedef OptionGenerator = Future> Function( PackageMetaProvider); /// A [DartdocOption] that only contains other [DartdocOption]s and is not an @@ -736,13 +736,13 @@ class DartdocOptionSet extends DartdocOption { /// Since we have no value, [_onMissing] does nothing. @override - void _onMissing(_OptionValueWithContext valueWithContext, - String missingFilename) {} + void _onMissing( + _OptionValueWithContext valueWithContext, String missingFilename) {} /// Traverse skips this node, because it doesn't represent a real /// configuration object. @override - void traverse(void Function(DartdocOption option) visitor) { + void traverse(void Function(DartdocOption option) visitor) { _children.values.forEach((d) => d.traverse(visitor)); } } @@ -817,7 +817,7 @@ class DartdocOptionArgFile extends DartdocOption @override void _onMissing( - _OptionValueWithContext valueWithContext, String missingPath) { + _OptionValueWithContext valueWithContext, String missingPath) { if (valueWithContext.definingFile != null) { _onMissingFromFiles(valueWithContext, missingPath); } else { @@ -889,12 +889,12 @@ abstract class _DartdocFileOption implements DartdocOption { String get fieldName => keys.join('.'); @override - void _onMissing(_OptionValueWithContext valueWithContext, - String missingPath) => + void _onMissing( + _OptionValueWithContext valueWithContext, String missingPath) => _onMissingFromFiles(valueWithContext, missingPath); void _onMissingFromFiles( - _OptionValueWithContext valueWithContext, String missingPath) { + _OptionValueWithContext valueWithContext, String missingPath) { var dartdocYaml = resourceProvider.pathContext.join( valueWithContext.canonicalDirectoryPath, valueWithContext.definingFile); throw DartdocFileMissing('Field $fieldName from $dartdocYaml, set to ' @@ -916,7 +916,7 @@ abstract class _DartdocFileOption implements DartdocOption { T _valueAtFromFiles(Folder dir) { var key = resourceProvider.pathContext.canonicalize(dir.path); if (!__valueAtFromFiles.containsKey(key)) { - _OptionValueWithContext valueWithContext; + _OptionValueWithContext valueWithContext; if (parentDirOverridesChild) { valueWithContext = _valueAtFromFilesLastFound(dir); } else { @@ -929,8 +929,8 @@ abstract class _DartdocFileOption implements DartdocOption { /// Searches all dartdoc_options files through parent directories, starting at /// [dir], for the option and returns one once found. - _OptionValueWithContext _valueAtFromFilesFirstFound(Folder folder) { - _OptionValueWithContext value; + _OptionValueWithContext _valueAtFromFilesFirstFound(Folder folder) { + _OptionValueWithContext value; for (var dir in folder.withAncestors) { value = _valueAtFromFile(dir); if (value != null) break; @@ -941,8 +941,8 @@ abstract class _DartdocFileOption implements DartdocOption { /// Searches all dartdoc_options files for the option, and returns the value /// in the top-most parent directory `dartdoc_options.yaml` file it is /// mentioned in. - _OptionValueWithContext _valueAtFromFilesLastFound(Folder folder) { - _OptionValueWithContext value; + _OptionValueWithContext _valueAtFromFilesLastFound(Folder folder) { + _OptionValueWithContext value; for (var dir in folder.withAncestors) { var tmpValue = _valueAtFromFile(dir); if (tmpValue != null) value = tmpValue; @@ -952,7 +952,7 @@ abstract class _DartdocFileOption implements DartdocOption { /// Returns null if not set in the YAML file in this directory (or its /// parents). - _OptionValueWithContext _valueAtFromFile(Folder dir) { + _OptionValueWithContext _valueAtFromFile(Folder dir) { var yamlFileData = _yamlAtDirectory(dir); var contextPath = yamlFileData.canonicalDirectoryPath; Object yamlData = yamlFileData.data ?? {}; @@ -1083,12 +1083,12 @@ abstract class _DartdocArgOption implements DartdocOption { } @override - void _onMissing(_OptionValueWithContext valueWithContext, - String missingPath) => + void _onMissing( + _OptionValueWithContext valueWithContext, String missingPath) => _onMissingFromArgs(valueWithContext, missingPath); void _onMissingFromArgs( - _OptionValueWithContext valueWithContext, String missingPath) { + _OptionValueWithContext valueWithContext, String missingPath) { throw DartdocFileMissing( 'Argument --$argName, set to ${valueWithContext.value}, resolves to ' 'missing path: "$missingPath"'); @@ -1098,7 +1098,7 @@ abstract class _DartdocArgOption implements DartdocOption { /// the [argParser] and the working directory from [_directoryCurrent]. /// /// Throws [UnsupportedError] if [T] is not a supported type. - _OptionValueWithContext _valueAtFromArgsWithContext() { + _OptionValueWithContext _valueAtFromArgsWithContext() { if (!_argResults.wasParsed(argName)) return null; T retval; @@ -1217,21 +1217,23 @@ class DartdocOptionContext extends DartdocOptionContextBase // TODO(jcollins-g): Allow passing in structured data to initialize a // [DartdocOptionContext]'s arguments instead of having to parse strings // via optionSet. - /// If [entity] is null, assume this is the initialization case and use - /// the inputDir flag to determine the context. - DartdocOptionContext( - this.optionSet, Resource resource, ResourceProvider resourceProvider) { - if (resource == null) { - var current = resourceProvider.pathContext.current; - String inputDir = - optionSet['inputDir'].valueAt(resourceProvider.getFolder(current)) ?? - current; - context = resourceProvider.getFolder(inputDir); - } else { - context = resourceProvider.getFolder(resourceProvider.pathContext - .canonicalize( - resource is File ? resource.parent2.path : resource.path)); - } + DartdocOptionContext(this.optionSet, Resource contextLocation, + ResourceProvider resourceProvider) { + assert(contextLocation != null); + context = resourceProvider.getFolder(resourceProvider.pathContext + .canonicalize(contextLocation is File + ? contextLocation.parent2.path + : contextLocation.path)); + } + + /// Build a DartdocOptionContext via the 'inputDir' command line option. + DartdocOptionContext.fromDefaultContextLocation( + this.optionSet, ResourceProvider resourceProvider) { + var current = resourceProvider.pathContext.current; + String inputDir = + optionSet['inputDir'].valueAt(resourceProvider.getFolder(current)) ?? + current; + context = resourceProvider.getFolder(inputDir); } /// Build a DartdocOptionContext from an analyzer element (using its source @@ -1368,7 +1370,7 @@ class DartdocOptionContext extends DartdocOptionContextBase /// Instantiate dartdoc's configuration file and options parser with the /// given command line arguments. -Future>> createDartdocOptions( +Future> createDartdocOptions( PackageMetaProvider packageMetaProvider, ) async { var resourceProvider = packageMetaProvider.resourceProvider; diff --git a/lib/src/model/library.dart b/lib/src/model/library.dart index 42a11c933d..d6e61c0b82 100644 --- a/lib/src/model/library.dart +++ b/lib/src/model/library.dart @@ -104,13 +104,13 @@ class Library extends ModelElement with Categorization, TopLevelContainer { CompilationUnitElement compilationUnit) { return quiver.concat([ compilationUnit.accessors, + compilationUnit.classes, compilationUnit.enums, compilationUnit.extensions, compilationUnit.functions, compilationUnit.mixins, compilationUnit.topLevelVariables, compilationUnit.typeAliases, - compilationUnit.types, ]); } diff --git a/test/end2end/dartdoc_test.dart b/test/end2end/dartdoc_test.dart index 58640eee44..62f961e1cc 100644 --- a/test/end2end/dartdoc_test.dart +++ b/test/end2end/dartdoc_test.dart @@ -57,8 +57,8 @@ Future _generatorContextFromArgv( ], pubPackageMetaProvider); optionSet.parseArguments(argv); - return DartdocGeneratorOptionContext( - optionSet, null, pubPackageMetaProvider.resourceProvider); + return DartdocGeneratorOptionContext.fromDefaultContextLocation( + optionSet, pubPackageMetaProvider.resourceProvider); } class DartdocLoggingOptionContext extends DartdocGeneratorOptionContext diff --git a/test/mustachio/renderers_output_test.dart b/test/mustachio/renderers_output_test.dart index b26c462750..39c7dbf604 100644 --- a/test/mustachio/renderers_output_test.dart +++ b/test/mustachio/renderers_output_test.dart @@ -29,8 +29,8 @@ Future _generatorContextFromArgv( ], pubPackageMetaProvider); optionSet.parseArguments(argv); - return DartdocGeneratorOptionContext( - optionSet, null, pubPackageMetaProvider.resourceProvider); + return DartdocGeneratorOptionContext.fromDefaultContextLocation( + optionSet, pubPackageMetaProvider.resourceProvider); } void main() { diff --git a/test/src/utils.dart b/test/src/utils.dart index aa89a5b491..3636ddf3f3 100644 --- a/test/src/utils.dart +++ b/test/src/utils.dart @@ -36,14 +36,11 @@ final Folder testPackageToolError = _resourceProvider.getFolder(_pathContext /// [DartdocOptionSet] based on the current working directory. Future contextFromArgv( List argv, PackageMetaProvider packageMetaProvider) async { - var resourceProvider = packageMetaProvider.resourceProvider; var optionSet = await DartdocOptionSet.fromOptionGenerators( 'dartdoc', [createDartdocOptions], packageMetaProvider); optionSet.parseArguments(argv); - return DartdocOptionContext( - optionSet, - resourceProvider.getFolder(resourceProvider.pathContext.current), - pubPackageMetaProvider.resourceProvider); + return DartdocOptionContext.fromDefaultContextLocation( + optionSet, pubPackageMetaProvider.resourceProvider); } Future bootBasicPackage( From dbbc79e14812b139e31ce85f5c39002db6282f06 Mon Sep 17 00:00:00 2001 From: Janice Collins Date: Wed, 18 Aug 2021 13:22:08 -0700 Subject: [PATCH 03/47] Convert options/logging libraries to null safety (#2748) * Update analyzer version to 2.0.0 * grind build for analyzer 2 * First steps toward migrating * Start migrating some things around the edges and see what happens * Basic migration infrastruture for new NNBD branch * use separate workflow file for nnbd branch, for clarity * thinko * Switch to using CompilationUnitElement.classes (#2743) * Ignore null safe import warnings for presubmits * Prepare dartdoc_options for migration (#2745) * more specific imports in options * do not allow autoinitialization * dartfmt * parameterize the valueWithContext type * Use alternative constructors instead of externalizing, didn't realize the autodetect was so widely used * more subclasses * Empty commit to straighten out GitHub Actions * dartfmt --- analysis_options_presubmit.yaml | 2 ++ lib/options.dart | 34 +++++++++++---------------------- lib/src/logging.dart | 2 -- pubspec.yaml | 2 +- 4 files changed, 14 insertions(+), 26 deletions(-) diff --git a/analysis_options_presubmit.yaml b/analysis_options_presubmit.yaml index 26dffd27ac..f9b11470d9 100644 --- a/analysis_options_presubmit.yaml +++ b/analysis_options_presubmit.yaml @@ -10,6 +10,8 @@ analyzer: ### Extra ignores for presubmit deprecated_member_use: ignore deprecated_member_use_from_same_package: ignore + ### Temporary presubmit ignore for NNBD migration + import_of_legacy_library_into_null_safe: ignore exclude: - 'doc/**' - 'lib/src/third_party/pkg/**' diff --git a/lib/options.dart b/lib/options.dart index 92fe2224d3..85fdfa67e0 100644 --- a/lib/options.dart +++ b/lib/options.dart @@ -1,5 +1,3 @@ -// @dart=2.9 - import 'dart:io' show stderr, exitCode; import 'package:analyzer/file_system/file_system.dart'; @@ -12,34 +10,24 @@ import 'package:dartdoc/src/package_meta.dart'; /// Helper class that consolidates option contexts for instantiating generators. class DartdocGeneratorOptionContext extends DartdocOptionContext { - DartdocGeneratorOptionContext( - DartdocOptionSet optionSet, Folder dir, ResourceProvider resourceProvider) + DartdocGeneratorOptionContext(DartdocOptionSet optionSet, Folder? dir, + ResourceProvider resourceProvider) : super(optionSet, dir, resourceProvider); - DartdocGeneratorOptionContext.fromDefaultContextLocation( DartdocOptionSet optionSet, ResourceProvider resourceProvider) : super.fromDefaultContextLocation(optionSet, resourceProvider); - // TODO(migration): Make late final with initializer when Null Safe. - String _header; - /// Returns the joined contents of any 'header' files specified in options. - String get header => - _header ??= _joinCustomTextFiles(optionSet['header'].valueAt(context)); - - // TODO(migration): Make late final with initializer when Null Safe. - String _footer; + late final String header = + _joinCustomTextFiles(optionSet['header'].valueAt(context)); /// Returns the joined contents of any 'footer' files specified in options. - String get footer => - _footer ??= _joinCustomTextFiles(optionSet['footer'].valueAt(context)); - - // TODO(migration): Make late final with initializer when Null Safe. - String _footerText; + late final String footer = + _joinCustomTextFiles(optionSet['footer'].valueAt(context)); /// Returns the joined contents of any 'footer-text' files specified in /// options. - String get footerText => _footerText ??= + late final String footerText = _joinCustomTextFiles(optionSet['footerText'].valueAt(context)); String _joinCustomTextFiles(Iterable paths) => paths @@ -63,8 +51,8 @@ class DartdocGeneratorOptionContext extends DartdocOptionContext { class DartdocProgramOptionContext extends DartdocGeneratorOptionContext with LoggingContext { - DartdocProgramOptionContext( - DartdocOptionSet optionSet, Folder dir, ResourceProvider resourceProvider) + DartdocProgramOptionContext(DartdocOptionSet optionSet, Folder? dir, + ResourceProvider resourceProvider) : super(optionSet, dir, resourceProvider); DartdocProgramOptionContext.fromDefaultContextLocation( DartdocOptionSet optionSet, ResourceProvider resourceProvider) @@ -91,10 +79,10 @@ Future>> createDartdocProgramOptions( ]; } -Future parseOptions( +Future parseOptions( PackageMetaProvider packageMetaProvider, List arguments, { - OptionGenerator additionalOptions, + OptionGenerator? additionalOptions, }) async { var optionSet = await DartdocOptionSet.fromOptionGenerators( 'dartdoc', diff --git a/lib/src/logging.dart b/lib/src/logging.dart index 8c87b968c7..b56a8d39c1 100644 --- a/lib/src/logging.dart +++ b/lib/src/logging.dart @@ -2,8 +2,6 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. -// @dart=2.9 - import 'dart:convert'; import 'dart:io' show stderr, stdout; diff --git a/pubspec.yaml b/pubspec.yaml index f421247c86..fd5b5e365a 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -10,7 +10,7 @@ dependencies: analyzer: ^2.0.0 args: ^2.0.0 charcode: ^1.2.0 - collection: ^1.15.0-nullsafety.4 + collection: ^1.15.0 cli_util: ^0.3.0 crypto: ^3.0.0 glob: ^2.0.0 From 952d8374b37f8f232ad2f34fd3809d3f6aba80ea Mon Sep 17 00:00:00 2001 From: Janice Collins Date: Mon, 23 Aug 2021 13:54:19 -0700 Subject: [PATCH 04/47] update NNBD branch from head (#2758) * Switch to using CompilationUnitElement.classes (#2743) * Prepare dartdoc_options for migration (#2745) * more specific imports in options * do not allow autoinitialization * dartfmt * parameterize the valueWithContext type * Use alternative constructors instead of externalizing, didn't realize the autodetect was so widely used * more subclasses * Disable the unstable template checks and prepare for 2.14 stable. (#2752) * Disable one of the template checks? and add beta branch for testing * beta is the new stable * empty commit - force check reset * Add a blurb to the README about requiring analysis (#2753) * Allow comment references on generic typedefs (#2756) Co-authored-by: Janice Collins * Prepare for dartdoc 2.0.0 (#2754) * Prepare for dartdoc 2.0.0 * Update changelog for additional bugfix Co-authored-by: Simon Binder --- .github/workflows/test.yaml | 8 ++++++++ CHANGELOG.md | 9 +++++++++ README.md | 4 +++- dartdoc_options.yaml | 2 +- lib/src/model/typedef.dart | 8 ++++++-- lib/src/version.dart | 2 +- pubspec.yaml | 2 +- .../test_package/lib/features/generalized_typedefs.dart | 2 ++ tool/grind.dart | 3 ++- 9 files changed, 33 insertions(+), 7 deletions(-) diff --git a/.github/workflows/test.yaml b/.github/workflows/test.yaml index 4f3f3c50c9..a53d16c2f3 100644 --- a/.github/workflows/test.yaml +++ b/.github/workflows/test.yaml @@ -28,6 +28,14 @@ jobs: - os: windows-latest sdk: dev job: nnbd + exclude: + # Do not try to run flutter against the "stable" sdk, + # it is unlikely to work and produces uninteresting + # results. + - sdk: stable + job: flutter + - sdk: stable + job: sdk-analyzer steps: - name: Configure git diff --git a/CHANGELOG.md b/CHANGELOG.md index a9a32e1a3c..e47033a8da 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,12 @@ +## 2.0.0 +* BREAKING CHANGE: changes to dartdoc options API + to prepare for NNBD migration (#2745, #2744). +* Fix unbound type reference in extension method comment + reference creating a null dereference (#2741, #2740) +* Update to analyzer 2.0. (#2734) +* Fix comment references on generic typedefs in new + lookup code. (#2755, #2756) + ## 1.0.2 * Fix where extensions header in library sidebar linked to the diff --git a/README.md b/README.md index 01fb7d69d5..6c41da2dd2 100644 --- a/README.md +++ b/README.md @@ -18,7 +18,9 @@ Run `pub global activate dartdoc` to install the latest version of dartdoc compa ## Generating docs -Run `dartdoc` from the root directory of a package. Here is an example of dartdoc documenting itself: +Run `dartdoc` from the root directory of a package. Your package must analyze without errors +with `dart analyze` or `flutter analyze` as appropriate. Here is an example of dartdoc documenting +itself: ``` $ dartdoc diff --git a/dartdoc_options.yaml b/dartdoc_options.yaml index 1f6e65ac2c..242689dbfc 100644 --- a/dartdoc_options.yaml +++ b/dartdoc_options.yaml @@ -1,4 +1,4 @@ dartdoc: linkToSource: root: '.' - uriTemplate: 'https://github.com/dart-lang/dartdoc/blob/v1.0.2/%f%#L%l%' + uriTemplate: 'https://github.com/dart-lang/dartdoc/blob/v2.0.0/%f%#L%l%' diff --git a/lib/src/model/typedef.dart b/lib/src/model/typedef.dart index 3398db83e4..75bc26c921 100644 --- a/lib/src/model/typedef.dart +++ b/lib/src/model/typedef.dart @@ -73,8 +73,12 @@ class Typedef extends ModelElement Map get referenceChildren { if (_referenceChildren == null) { _referenceChildren = {}; - _referenceChildren - .addEntriesIfAbsent(parameters.explicitOnCollisionWith(this)); + + // Only consider parameters if this is a function typedef. + if (isCallable) { + _referenceChildren + .addEntriesIfAbsent(parameters.explicitOnCollisionWith(this)); + } _referenceChildren .addEntriesIfAbsent(typeParameters.explicitOnCollisionWith(this)); } diff --git a/lib/src/version.dart b/lib/src/version.dart index b0e99a53ed..0e58df3934 100644 --- a/lib/src/version.dart +++ b/lib/src/version.dart @@ -1,2 +1,2 @@ // Generated code. Do not modify. -const packageVersion = '1.0.2'; +const packageVersion = '2.0.0'; diff --git a/pubspec.yaml b/pubspec.yaml index fd5b5e365a..62c0cc8331 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -1,6 +1,6 @@ name: dartdoc # Run `grind build` after updating. -version: 1.0.2 +version: 2.0.0 description: A non-interactive HTML documentation generator for Dart source code. homepage: https://github.com/dart-lang/dartdoc environment: diff --git a/testing/test_package/lib/features/generalized_typedefs.dart b/testing/test_package/lib/features/generalized_typedefs.dart index e43a9d721b..220be96e82 100644 --- a/testing/test_package/lib/features/generalized_typedefs.dart +++ b/testing/test_package/lib/features/generalized_typedefs.dart @@ -10,6 +10,8 @@ library generalized_typedefs; typedef T0 = void; typedef T1 = Function; + +/// [List], [String] typedef T2 = List; typedef T3 = Map; typedef T4 = void Function(); diff --git a/tool/grind.dart b/tool/grind.dart index 5485e95383..d9723f8d91 100644 --- a/tool/grind.dart +++ b/tool/grind.dart @@ -1062,7 +1062,8 @@ final _generatedFilesList = [ 'src/generator/html_resources.g.dart', 'src/generator/templates.aot_renderers_for_html.dart', 'src/generator/templates.aot_renderers_for_md.dart', - 'src/generator/templates.runtime_renderers.dart', + // TODO(jcollins-g): https://github.com/dart-lang/dartdoc/issues/2751 + //'src/generator/templates.runtime_renderers.dart', 'src/version.dart', '../test/mustachio/foo.dart', ].map((s) => path.joinAll(path.posix.split(s))); From bcc00439661797ad1b13e5e71517f4e4eaeec31d Mon Sep 17 00:00:00 2001 From: Janice Collins Date: Mon, 23 Aug 2021 14:46:06 -0700 Subject: [PATCH 05/47] Migrate dartdoc_options.dart (#2749) * Switch to using CompilationUnitElement.classes (#2743) * Prepare dartdoc_options for migration (#2745) * more specific imports in options * do not allow autoinitialization * dartfmt * parameterize the valueWithContext type * Use alternative constructors instead of externalizing, didn't realize the autodetect was so widely used * more subclasses * flatten * Disable the unstable template checks and prepare for 2.14 stable. (#2752) * Disable one of the template checks? and add beta branch for testing * beta is the new stable * empty commit - force check reset * Add a blurb to the README about requiring analysis (#2753) * Allow comment references on generic typedefs (#2756) Co-authored-by: Janice Collins * Prepare for dartdoc 2.0.0 (#2754) * Prepare for dartdoc 2.0.0 * Update changelog for additional bugfix * review comments Co-authored-by: Simon Binder --- lib/options.dart | 26 +- lib/src/dartdoc_options.dart | 454 ++++++++---------- .../templates.runtime_renderers.dart | 2 +- lib/src/logging.dart | 2 +- lib/src/warnings.dart | 7 + test/dartdoc_options_test.dart | 16 +- test/documentation_comment_test.dart | 2 +- test/end2end/dartdoc_test.dart | 8 +- test/mustachio/renderers_output_test.dart | 2 +- test/package_test.dart | 2 +- test/src/utils.dart | 2 +- test/warnings_test.dart | 2 +- 12 files changed, 244 insertions(+), 281 deletions(-) diff --git a/lib/options.dart b/lib/options.dart index 85fdfa67e0..195510823e 100644 --- a/lib/options.dart +++ b/lib/options.dart @@ -10,8 +10,8 @@ import 'package:dartdoc/src/package_meta.dart'; /// Helper class that consolidates option contexts for instantiating generators. class DartdocGeneratorOptionContext extends DartdocOptionContext { - DartdocGeneratorOptionContext(DartdocOptionSet optionSet, Folder? dir, - ResourceProvider resourceProvider) + DartdocGeneratorOptionContext( + DartdocOptionSet optionSet, Folder dir, ResourceProvider resourceProvider) : super(optionSet, dir, resourceProvider); DartdocGeneratorOptionContext.fromDefaultContextLocation( DartdocOptionSet optionSet, ResourceProvider resourceProvider) @@ -51,8 +51,8 @@ class DartdocGeneratorOptionContext extends DartdocOptionContext { class DartdocProgramOptionContext extends DartdocGeneratorOptionContext with LoggingContext { - DartdocProgramOptionContext(DartdocOptionSet optionSet, Folder? dir, - ResourceProvider resourceProvider) + DartdocProgramOptionContext( + DartdocOptionSet optionSet, Folder dir, ResourceProvider resourceProvider) : super(optionSet, dir, resourceProvider); DartdocProgramOptionContext.fromDefaultContextLocation( DartdocOptionSet optionSet, ResourceProvider resourceProvider) @@ -84,7 +84,7 @@ Future parseOptions( List arguments, { OptionGenerator? additionalOptions, }) async { - var optionSet = await DartdocOptionSet.fromOptionGenerators( + var optionRoot = await DartdocOptionRoot.fromOptionGenerators( 'dartdoc', [ createDartdocOptions, @@ -96,22 +96,22 @@ Future parseOptions( packageMetaProvider); try { - optionSet.parseArguments(arguments); + optionRoot.parseArguments(arguments); } on FormatException catch (e) { stderr.writeln(' fatal error: ${e.message}'); stderr.writeln(''); - _printUsage(optionSet.argParser); + _printUsage(optionRoot.argParser); // Do not use exit() as this bypasses --pause-isolates-on-exit exitCode = 64; return null; } - if (optionSet['help'].valueAtCurrent()) { - _printHelp(optionSet.argParser); + if (optionRoot['help'].valueAtCurrent()) { + _printHelp(optionRoot.argParser); exitCode = 0; return null; } - if (optionSet['version'].valueAtCurrent()) { - _printVersion(optionSet.argParser); + if (optionRoot['version'].valueAtCurrent()) { + _printVersion(optionRoot.argParser); exitCode = 0; return null; } @@ -119,12 +119,12 @@ Future parseOptions( DartdocProgramOptionContext config; try { config = DartdocProgramOptionContext.fromDefaultContextLocation( - optionSet, packageMetaProvider.resourceProvider); + optionRoot, packageMetaProvider.resourceProvider); } on DartdocOptionError catch (e) { stderr.writeln(' fatal error: ${e.message}'); stderr.writeln(''); await stderr.flush(); - _printUsage(optionSet.argParser); + _printUsage(optionRoot.argParser); exitCode = 64; return null; } diff --git a/lib/src/dartdoc_options.dart b/lib/src/dartdoc_options.dart index a5ecfca71c..544e32dcdf 100644 --- a/lib/src/dartdoc_options.dart +++ b/lib/src/dartdoc_options.dart @@ -2,8 +2,6 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. -// @dart=2.9 - /// /// dartdoc's dartdoc_options.yaml configuration file follows similar loading /// semantics to that of analysis_options.yaml, @@ -43,7 +41,7 @@ const bool _kBoolVal = true; const String compileArgsTagName = 'compile_args'; -int get _usageLineLength => stdout.hasTerminal ? stdout.terminalColumns : null; +int get _usageLineLength => stdout.hasTerminal ? stdout.terminalColumns : 80; typedef ConvertYamlToType = T Function(YamlMap, String, ResourceProvider); @@ -63,11 +61,11 @@ class CategoryDefinition { final String name; /// Displayed name of the category in docs, or null if there is none. - final String _displayName; + final String? _displayName; /// Canonical path of the markdown file used to document this category /// (or null if undocumented). - final String documentationMarkdown; + final String? documentationMarkdown; CategoryDefinition(this.name, this._displayName, this.documentationMarkdown); @@ -92,12 +90,10 @@ class CategoryConfiguration { var newCategoryDefinitions = {}; for (var entry in yamlMap.entries) { var name = entry.key.toString(); - String displayName; - String documentationMarkdown; var categoryMap = entry.value; if (categoryMap is Map) { - displayName = categoryMap['displayName']?.toString(); - documentationMarkdown = categoryMap['markdown']?.toString(); + var displayName = categoryMap['displayName']?.toString(); + var documentationMarkdown = categoryMap['markdown']?.toString(); if (documentationMarkdown != null) { documentationMarkdown = resourceProvider.pathContext.canonicalize( resourceProvider.pathContext @@ -122,9 +118,7 @@ class ToolConfiguration { final ResourceProvider resourceProvider; - ToolRunner _runner; - - ToolRunner get runner => _runner ??= ToolRunner(this); + late ToolRunner runner = ToolRunner(this); ToolConfiguration._(this.tools, this.resourceProvider); @@ -140,14 +134,14 @@ class ToolConfiguration { for (var entry in yamlMap.entries) { var name = entry.key.toString(); var toolMap = entry.value; - List compileArgs; - String description; - List command; - List setupCommand; + String? description; + List? compileArgs; + List? command; + List? setupCommand; if (toolMap is Map) { - description = toolMap['description']?.toString(); - List findCommand([String prefix = '']) { - List command; + description = toolMap['description'].toString(); + List? findCommand([String prefix = '']) { + List? command; // If the command key is given, then it applies to all platforms. var commandFromKey = toolMap.containsKey('${prefix}command') ? '${prefix}command' @@ -183,8 +177,8 @@ class ToolConfiguration { command = findCommand(); setupCommand = findCommand('setup_'); - List findArgs() { - List args; + List? findArgs() { + List? args; if (toolMap.containsKey(compileArgsTagName)) { var compileArgs = toolMap[compileArgsTagName]; if (compileArgs is String) { @@ -289,7 +283,7 @@ class _OptionValueWithContext { String canonicalDirectoryPath; /// If non-null, the basename of the configuration file the value came from. - String definingFile; + String? definingFile; /// A [pathLib.Context] variable initialized with canonicalDirectoryPath. p.Context pathContext; @@ -298,10 +292,9 @@ class _OptionValueWithContext { /// /// [path] is the path where this value came from (not required to be /// canonical). - _OptionValueWithContext(this.value, String path, {this.definingFile}) { - canonicalDirectoryPath = p.canonicalize(path); - pathContext = p.Context(current: canonicalDirectoryPath); - } + _OptionValueWithContext(this.value, String path, {this.definingFile}) + : canonicalDirectoryPath = p.canonicalize(path), + pathContext = p.Context(current: p.canonicalize(path)); /// Assume value is a path, and attempt to resolve it. /// @@ -341,7 +334,7 @@ class _OptionValueWithContext { /// [DartdocOptionArgOnly], and [DartdocOptionFileOnly]. abstract class DartdocOption { /// This is the value returned if we couldn't find one otherwise. - final T defaultsTo; + final T? defaultsTo; /// Text string for help passed on in command line options. final String help; @@ -379,7 +372,7 @@ abstract class DartdocOption { } /// Closure to convert yaml data into some other structure. - ConvertYamlToType _convertYamlToType; + final ConvertYamlToType? _convertYamlToType; // The choice not to use reflection means there's some ugly type checking, // somewhat more ugly than we'd have to do anyway to automatically convert @@ -398,11 +391,6 @@ abstract class DartdocOption { bool get _isDouble => _kDoubleVal is T; - DartdocOption _parent; - - /// The parent of this DartdocOption, or null if this is the root. - DartdocOption get parent => _parent; - final Map __yamlAtCanonicalPathCache = {}; /// Implementation detail for [DartdocOptionFileOnly]. Make sure we use @@ -410,19 +398,6 @@ abstract class DartdocOption { Map get _yamlAtCanonicalPathCache => root.__yamlAtCanonicalPathCache; - final ArgParser __argParser = ArgParser(usageLineLength: _usageLineLength); - - ArgParser get argParser => root.__argParser; - - ArgResults __argResults; - - /// Parse these as string arguments (from argv) with the argument parser. - /// Call before calling [valueAt] for any [DartdocOptionArgOnly] or - /// [DartdocOptionArgFile] in this tree. - void _parseArguments(List arguments) { - __argResults = argParser.parse(arguments); - } - /// Throw [DartdocFileMissing] with a detailed error message indicating where /// the error came from when a file or directory option is missing. void _onMissing( @@ -432,14 +407,14 @@ abstract class DartdocOption { void _validatePaths(_OptionValueWithContext valueWithContext) { if (!mustExist) return; assert(isDir || isFile); - List resolvedPaths; + var resolvedPaths = []; var value = valueWithContext.value; if (value is String) { resolvedPaths = [valueWithContext.resolvedValue as String]; } else if (value is List) { resolvedPaths = valueWithContext.resolvedValue as List; } else if (value is Map) { - resolvedPaths = (valueWithContext.resolvedValue as Map).values.toList(); + resolvedPaths = [...(valueWithContext.resolvedValue as Map).values]; } else { assert( false, @@ -458,11 +433,11 @@ abstract class DartdocOption { /// For a [List] or [String] value, if [isDir] or [isFile] is set, /// resolve paths in value relative to canonicalPath. - T _handlePathsInContext(_OptionValueWithContext valueWithContext) { + T? _handlePathsInContext(_OptionValueWithContext? valueWithContext) { if (valueWithContext?.value == null || !(isDir || isFile || isGlob)) { return valueWithContext?.value; } - _validatePaths(valueWithContext); + _validatePaths(valueWithContext!); return valueWithContext.resolvedValue; } @@ -473,17 +448,14 @@ abstract class DartdocOption { ArgResults get _argResults => root.__argResults; - /// Set the parent of this [DartdocOption]. Do not call more than once. - set parent(DartdocOption newParent) { - assert(_parent == null); - _parent = newParent; - } + /// To avoid accessing early, call [add] on the option's parent before + /// looking up unless this is a [DartdocRootOption]. + late final DartdocOption parent; - /// The root [DartdocOption] containing this object, or [this] if the object - /// has no parent. - DartdocOption get root { + /// The [DartdocOptionRoot] containing this object. + DartdocOptionRoot get root { DartdocOption p = this; - while (p.parent != null) { + while (p is! DartdocOptionRoot) { p = p.parent; } return p; @@ -493,10 +465,11 @@ abstract class DartdocOption { Iterable get keys { var keyList = []; DartdocOption option = this; - while (option?.name != null) { + while (option is! DartdocOptionRoot) { keyList.add(option.name); option = option.parent; } + keyList.add(option.name); return keyList.reversed; } @@ -514,23 +487,15 @@ abstract class DartdocOption { /// type. If [mustExist] is true, will throw [DartdocFileMissing] for command /// line parameters and file paths in config files that don't point to /// corresponding files or directories. - T valueAt(Folder dir); + T? valueAt(Folder dir); /// Calls [valueAt] with the working directory at the start of the program. - T valueAtCurrent() => valueAt(_directoryCurrent); - - Folder __directoryCurrent; - Folder get _directoryCurrent => - __directoryCurrent ??= resourceProvider.getFolder(_directoryCurrentPath); - - String __directoryCurrentPath; - String get _directoryCurrentPath => - __directoryCurrentPath ??= resourceProvider.pathContext.current; + T? valueAtCurrent() => valueAt(_directoryCurrent); - /// Calls [valueAt] on the directory this element is defined in. - T valueAtElement(Element element) => - valueAt(resourceProvider.getFolder(resourceProvider.pathContext.normalize( - resourceProvider.pathContext.basename(element.source.fullName)))); + late final Folder _directoryCurrent = + resourceProvider.getFolder(_directoryCurrentPath); + late final String _directoryCurrentPath = + resourceProvider.pathContext.current; /// Adds a DartdocOption to the children of this DartdocOption. void add(DartdocOption option) { @@ -539,19 +504,20 @@ abstract class DartdocOption { 'Tried to add two children with the same name: ${option.name}'); } _children[option.name] = option; + // TODO(jcollins-g): Consider a stronger refactor that doesn't rely on + // post-construction setup for [parent]. option.parent = this; - option.traverse((option) => option._onAdd()); } - /// This method is guaranteed to be called when [this] or any parent is added. - void _onAdd() {} + /// This method is called when parsing options to set up the [ArgParser]. + void _addToArgParser(ArgParser argParser) {} /// Adds a list of dartdoc options to the children of this DartdocOption. void addAll(Iterable options) => options.forEach(add); /// Get the immediate child of this node named [name]. DartdocOption operator [](String name) { - return _children[name]; + return _children[name]!; } /// Apply the function [visit] to [this] and all children. @@ -565,7 +531,8 @@ abstract class DartdocOption { /// overridden by a file. class DartdocOptionFileSynth extends DartdocOption with DartdocSyntheticOption, _DartdocFileOption { - bool _parentDirOverridesChild; + @override + final bool parentDirOverridesChild; @override final T Function(DartdocSyntheticOption, Folder) _compute; @@ -574,15 +541,13 @@ class DartdocOptionFileSynth extends DartdocOption {bool mustExist = false, String help = '', OptionKind optionIs = OptionKind.other, - bool parentDirOverridesChild, - ConvertYamlToType convertYamlToType}) + this.parentDirOverridesChild = false, + ConvertYamlToType? convertYamlToType}) : super(name, null, help, optionIs, mustExist, convertYamlToType, - resourceProvider) { - _parentDirOverridesChild = parentDirOverridesChild; - } + resourceProvider); @override - T valueAt(Folder dir) { + T? valueAt(Folder dir) { var result = _valueAtFromFile(dir); if (result?.definingFile != null) { return _handlePathsInContext(result); @@ -599,37 +564,35 @@ class DartdocOptionFileSynth extends DartdocOption _onMissingFromSynthetic(valueWithContext, missingPath); } } - - @override - bool get parentDirOverridesChild => _parentDirOverridesChild; } /// A class that defaults to a value computed from a closure, but can /// be overridden on the command line. class DartdocOptionArgSynth extends DartdocOption with DartdocSyntheticOption, _DartdocArgOption { - String _abbr; - bool _hide; - bool _negatable; - bool _splitCommas; + @override + final String? abbr; + @override + final bool hide; + @override + final bool negatable; + @override + final bool splitCommas; @override final T Function(DartdocSyntheticOption, Folder) _compute; DartdocOptionArgSynth( String name, this._compute, ResourceProvider resourceProvider, - {String abbr, + {this.abbr, bool mustExist = false, String help = '', - bool hide = false, + this.hide = false, OptionKind optionIs = OptionKind.other, - bool negatable = false, - bool splitCommas}) + this.negatable = false, + this.splitCommas = false}) : super(name, null, help, optionIs, mustExist, null, resourceProvider) { - _hide = hide; - _negatable = negatable; - _splitCommas = splitCommas; - _abbr = abbr; + assert(T is! Iterable || splitCommas == true); } @override @@ -639,24 +602,12 @@ class DartdocOptionArgSynth extends DartdocOption } @override - T valueAt(Folder dir) { + T? valueAt(Folder dir) { if (_argResults.wasParsed(argName)) { return _valueAtFromArgs(); } return _valueAtFromSynthetic(dir); } - - @override - String get abbr => _abbr; - - @override - bool get hide => _hide; - - @override - bool get negatable => _negatable; - - @override - bool get splitCommas => _splitCommas; } /// A synthetic option takes a closure at construction time that computes @@ -681,9 +632,9 @@ abstract class DartdocSyntheticOption implements DartdocOption { T Function(DartdocSyntheticOption, Folder) get _compute; @override - T valueAt(Folder dir) => _valueAtFromSynthetic(dir); + T? valueAt(Folder dir) => _valueAtFromSynthetic(dir); - T _valueAtFromSynthetic(Folder dir) { + T? _valueAtFromSynthetic(Folder dir) { var context = _OptionValueWithContext(_compute(this, dir), dir.path); return _handlePathsInContext(context); } @@ -705,12 +656,13 @@ abstract class DartdocSyntheticOption implements DartdocOption { typedef OptionGenerator = Future> Function( PackageMetaProvider); -/// A [DartdocOption] that only contains other [DartdocOption]s and is not an -/// option itself. -class DartdocOptionSet extends DartdocOption { - DartdocOptionSet(String name, ResourceProvider resourceProvider) - : super( - name, null, null, OptionKind.other, false, null, resourceProvider); +/// This is a [DartdocOptionSet] used as a root node. +class DartdocOptionRoot extends DartdocOptionSet { + DartdocOptionRoot(String name, ResourceProvider resourceProvider) + : super(name, resourceProvider); + + late final ArgParser _argParser = + ArgParser(usageLineLength: _usageLineLength); /// Asynchronous factory that is the main entry point to initialize Dartdoc /// options for use. @@ -718,26 +670,37 @@ class DartdocOptionSet extends DartdocOption { /// [name] is the top level key for the option set. /// [optionGenerators] is a sequence of asynchronous functions that return /// [DartdocOption]s that will be added to the new option set. - static Future fromOptionGenerators( + static Future fromOptionGenerators( String name, Iterable optionGenerators, PackageMetaProvider packageMetaProvider) async { var optionSet = - DartdocOptionSet(name, packageMetaProvider.resourceProvider); + DartdocOptionRoot(name, packageMetaProvider.resourceProvider); for (var generator in optionGenerators) { optionSet.addAll(await generator(packageMetaProvider)); } return optionSet; } - /// [DartdocOptionSet] always has the null value. - @override - void valueAt(Folder dir) => null; + ArgParser get argParser => _argParser; - /// Since we have no value, [_onMissing] does nothing. - @override - void _onMissing( - _OptionValueWithContext valueWithContext, String missingFilename) {} + /// Initialized via [_parseArguments]. + late ArgResults __argResults; + + bool _argParserInitialized = false; + + /// Parse these as string arguments (from argv) with the argument parser. + /// Call before calling [valueAt] for any [DartdocOptionArgOnly] or + /// [DartdocOptionArgFile] in this tree. + void _parseArguments(List arguments) { + if (!_argParserInitialized) { + _argParserInitialized = true; + traverse((DartdocOption option) { + option._addToArgParser(argParser); + }); + } + __argResults = argParser.parse(arguments); + } /// Traverse skips this node, because it doesn't represent a real /// configuration object. @@ -745,75 +708,81 @@ class DartdocOptionSet extends DartdocOption { void traverse(void Function(DartdocOption option) visitor) { _children.values.forEach((d) => d.traverse(visitor)); } + + @override + DartdocOption get parent => + throw UnsupportedError('Root nodes have no parent'); +} + +/// A [DartdocOption] that only contains other [DartdocOption]s and is not an +/// option itself. +class DartdocOptionSet extends DartdocOption { + DartdocOptionSet(String name, ResourceProvider resourceProvider) + : super(name, null, '', OptionKind.other, false, null, resourceProvider); + + /// [DartdocOptionSet] always has the null value. + @override + void valueAt(Folder dir) => null; + + /// Since we have no value, [_onMissing] does nothing. + @override + void _onMissing( + _OptionValueWithContext valueWithContext, String missingFilename) {} } /// A [DartdocOption] that only exists as a command line argument. `--help` is a /// good example. class DartdocOptionArgOnly extends DartdocOption with _DartdocArgOption { - String _abbr; - bool _hide; - bool _negatable; - bool _splitCommas; + @override + final String? abbr; + @override + final bool hide; + @override + final bool negatable; + @override + final bool splitCommas; DartdocOptionArgOnly( String name, T defaultsTo, ResourceProvider resourceProvider, - {String abbr, + {this.abbr, bool mustExist = false, String help = '', - bool hide = false, + this.hide = false, OptionKind optionIs = OptionKind.other, - bool negatable = false, - bool splitCommas}) + this.negatable = false, + this.splitCommas = false}) : super(name, defaultsTo, help, optionIs, mustExist, null, - resourceProvider) { - _hide = hide; - _negatable = negatable; - _splitCommas = splitCommas; - _abbr = abbr; - } - - @override - String get abbr => _abbr; - - @override - bool get hide => _hide; - - @override - bool get negatable => _negatable; - - @override - bool get splitCommas => _splitCommas; + resourceProvider); } /// A [DartdocOption] that works with command line arguments and /// `dartdoc_options` files. class DartdocOptionArgFile extends DartdocOption with _DartdocArgOption, _DartdocFileOption { - String _abbr; - bool _hide; - bool _negatable; - bool _parentDirOverridesChild; - bool _splitCommas; + @override + final String? abbr; + @override + final bool hide; + @override + final bool negatable; + @override + final bool parentDirOverridesChild; + @override + final bool splitCommas; DartdocOptionArgFile( String name, T defaultsTo, ResourceProvider resourceProvider, - {String abbr, + {this.abbr, bool mustExist = false, String help = '', - bool hide = false, + this.hide = false, OptionKind optionIs = OptionKind.other, - bool negatable = false, - bool parentDirOverridesChild = false, - bool splitCommas}) + this.negatable = false, + this.parentDirOverridesChild = false, + this.splitCommas = false}) : super(name, defaultsTo, help, optionIs, mustExist, null, - resourceProvider) { - _abbr = abbr; - _hide = hide; - _negatable = negatable; - _parentDirOverridesChild = parentDirOverridesChild; - _splitCommas = splitCommas; - } + resourceProvider); @override void _onMissing( @@ -828,47 +797,28 @@ class DartdocOptionArgFile extends DartdocOption /// Try to find an explicit argument setting this value, but if not, fall back /// to files finally, the default. @override - T valueAt(Folder dir) { + T? valueAt(Folder dir) { var value = _valueAtFromArgs(); value ??= _valueAtFromFiles(dir); value ??= defaultsTo; return value; } - - @override - String get abbr => _abbr; - - @override - bool get hide => _hide; - - @override - bool get negatable => _negatable; - - @override - bool get parentDirOverridesChild => _parentDirOverridesChild; - - @override - bool get splitCommas => _splitCommas; } class DartdocOptionFileOnly extends DartdocOption with _DartdocFileOption { - bool _parentDirOverridesChild; + @override + final bool parentDirOverridesChild; DartdocOptionFileOnly( String name, T defaultsTo, ResourceProvider resourceProvider, {bool mustExist = false, String help = '', OptionKind optionIs = OptionKind.other, - bool parentDirOverridesChild = false, - ConvertYamlToType convertYamlToType}) + this.parentDirOverridesChild = false, + ConvertYamlToType? convertYamlToType}) : super(name, defaultsTo, help, optionIs, mustExist, convertYamlToType, - resourceProvider) { - _parentDirOverridesChild = parentDirOverridesChild; - } - - @override - bool get parentDirOverridesChild => _parentDirOverridesChild; + resourceProvider); } /// Implements checking for options contained in dartdoc.yaml. @@ -905,18 +855,18 @@ abstract class _DartdocFileOption implements DartdocOption { /// Searches for a value in configuration files relative to [dir], and if not /// found, returns [defaultsTo]. - T valueAt(Folder dir) { + T? valueAt(Folder dir) { return _valueAtFromFiles(dir) ?? defaultsTo; } - final Map __valueAtFromFiles = {}; + final Map __valueAtFromFiles = {}; // The value of this option from files will not change unless files are // modified during execution (not allowed in Dartdoc). - T _valueAtFromFiles(Folder dir) { + T? _valueAtFromFiles(Folder dir) { var key = resourceProvider.pathContext.canonicalize(dir.path); if (!__valueAtFromFiles.containsKey(key)) { - _OptionValueWithContext valueWithContext; + _OptionValueWithContext? valueWithContext; if (parentDirOverridesChild) { valueWithContext = _valueAtFromFilesLastFound(dir); } else { @@ -929,8 +879,8 @@ abstract class _DartdocFileOption implements DartdocOption { /// Searches all dartdoc_options files through parent directories, starting at /// [dir], for the option and returns one once found. - _OptionValueWithContext _valueAtFromFilesFirstFound(Folder folder) { - _OptionValueWithContext value; + _OptionValueWithContext? _valueAtFromFilesFirstFound(Folder folder) { + _OptionValueWithContext? value; for (var dir in folder.withAncestors) { value = _valueAtFromFile(dir); if (value != null) break; @@ -941,8 +891,8 @@ abstract class _DartdocFileOption implements DartdocOption { /// Searches all dartdoc_options files for the option, and returns the value /// in the top-most parent directory `dartdoc_options.yaml` file it is /// mentioned in. - _OptionValueWithContext _valueAtFromFilesLastFound(Folder folder) { - _OptionValueWithContext value; + _OptionValueWithContext? _valueAtFromFilesLastFound(Folder folder) { + _OptionValueWithContext? value; for (var dir in folder.withAncestors) { var tmpValue = _valueAtFromFile(dir); if (tmpValue != null) value = tmpValue; @@ -952,16 +902,16 @@ abstract class _DartdocFileOption implements DartdocOption { /// Returns null if not set in the YAML file in this directory (or its /// parents). - _OptionValueWithContext _valueAtFromFile(Folder dir) { + _OptionValueWithContext? _valueAtFromFile(Folder dir) { var yamlFileData = _yamlAtDirectory(dir); var contextPath = yamlFileData.canonicalDirectoryPath; - Object yamlData = yamlFileData.data ?? {}; + Object yamlData = yamlFileData.data; for (var key in keys) { if (yamlData is Map && !yamlData.containsKey(key)) return null; yamlData = (yamlData as Map)[key] ?? {}; } - Object returnData; + Object? returnData; if (_isListString) { if (yamlData is YamlList) { returnData = [ @@ -969,6 +919,7 @@ abstract class _DartdocFileOption implements DartdocOption { ]; } } else if (yamlData is YamlMap) { + var convertYamlToType = _convertYamlToType; // TODO(jcollins-g): This special casing is unfortunate. Consider // a refactor to extract yaml data conversion into closures 100% of the // time or find a cleaner way to do this. @@ -976,8 +927,8 @@ abstract class _DartdocFileOption implements DartdocOption { // A refactor probably would integrate resolvedValue for // _OptionValueWithContext into the return data here, and would not have // that be separate. - if (_isMapString && _convertYamlToType == null) { - _convertYamlToType = (YamlMap yamlMap, String canonicalYamlPath, + if (_isMapString && convertYamlToType == null) { + convertYamlToType = (YamlMap yamlMap, String canonicalYamlPath, ResourceProvider resourceProvider) { var returnData = {}; for (var entry in yamlMap.entries) { @@ -986,15 +937,15 @@ abstract class _DartdocFileOption implements DartdocOption { return returnData as T; }; } - if (_convertYamlToType == null) { + if (convertYamlToType == null) { throw DartdocOptionError( 'Unable to convert yaml to type for option: $fieldName, method not ' 'defined'); } var canonicalDirectoryPath = resourceProvider.pathContext.canonicalize(contextPath); - returnData = _convertYamlToType( - yamlData, canonicalDirectoryPath, resourceProvider); + returnData = + convertYamlToType(yamlData, canonicalDirectoryPath, resourceProvider); } else if (_isDouble) { if (yamlData is num) { returnData = yamlData.toDouble(); @@ -1018,7 +969,7 @@ abstract class _DartdocFileOption implements DartdocOption { var canonicalPath = resourceProvider.pathContext.canonicalize(folder.path); if (_yamlAtCanonicalPathCache.containsKey(canonicalPath)) { - yamlData = _yamlAtCanonicalPathCache[canonicalPath]; + yamlData = _yamlAtCanonicalPathCache[canonicalPath]!; break; } canonicalPaths.add(canonicalPath); @@ -1054,12 +1005,12 @@ abstract class _DartdocArgOption implements DartdocOption { /// For [ArgParser], set to a single character to have a short version of the /// command line argument. - String get abbr; + String? get abbr; /// valueAt for arguments ignores the [dir] parameter and only uses command /// line arguments and the current working directory to resolve the result. @override - T valueAt(Folder dir) => _valueAtFromArgs() ?? defaultsTo; + T? valueAt(Folder dir) => _valueAtFromArgs() ?? defaultsTo; /// For passing in to [int.parse] and [double.parse] `onError'. void _throwErrorForTypes(String value) { @@ -1070,6 +1021,9 @@ abstract class _DartdocArgOption implements DartdocOption { example = '32'; } else if (_isDouble) { example = '0.76'; + } else { + throw UnimplementedError( + 'Type for $name is not implemented in $_throwErrorForTypes'); } throw DartdocOptionError( 'Invalid argument value: --$argName, set to "$value", must be a ' @@ -1077,7 +1031,7 @@ abstract class _DartdocArgOption implements DartdocOption { } /// Returns null if no argument was given on the command line. - T _valueAtFromArgs() { + T? _valueAtFromArgs() { var valueWithContext = _valueAtFromArgsWithContext(); return _handlePathsInContext(valueWithContext); } @@ -1098,7 +1052,7 @@ abstract class _DartdocArgOption implements DartdocOption { /// the [argParser] and the working directory from [_directoryCurrent]. /// /// Throws [UnsupportedError] if [T] is not a supported type. - _OptionValueWithContext _valueAtFromArgsWithContext() { + _OptionValueWithContext? _valueAtFromArgsWithContext() { if (!_argResults.wasParsed(argName)) return null; T retval; @@ -1145,7 +1099,8 @@ abstract class _DartdocArgOption implements DartdocOption { final camelCaseRegexp = RegExp(r'([a-z])([A-Z])(?=([a-z]))'); argName = argName.replaceAllMapped(camelCaseRegexp, (Match m) { var before = m.group(1); - var after = m.group(2).toLowerCase(); + // Group 2 is not optional. + var after = m.group(2)!.toLowerCase(); return '$before-$after'; }); return argName; @@ -1155,14 +1110,14 @@ abstract class _DartdocArgOption implements DartdocOption { /// [ArgParser.addFlag], [ArgParser.addOption], or [ArgParser.addMultiOption] /// as appropriate for [T]. @override - void _onAdd() { + void _addToArgParser(ArgParser argParser) { if (_isBool) { argParser.addFlag(argName, abbr: abbr, defaultsTo: defaultsTo as bool, help: help, hide: hide, - negatable: negatable ?? false); + negatable: negatable); } else if (_isInt || _isDouble || _isString) { argParser.addOption(argName, abbr: abbr, @@ -1212,29 +1167,25 @@ class DartdocOptionContext extends DartdocOptionContextBase @override final DartdocOptionSet optionSet; @override - Folder context; + final Folder context; // TODO(jcollins-g): Allow passing in structured data to initialize a // [DartdocOptionContext]'s arguments instead of having to parse strings // via optionSet. DartdocOptionContext(this.optionSet, Resource contextLocation, - ResourceProvider resourceProvider) { - assert(contextLocation != null); - context = resourceProvider.getFolder(resourceProvider.pathContext - .canonicalize(contextLocation is File - ? contextLocation.parent2.path - : contextLocation.path)); - } + ResourceProvider resourceProvider) + : context = resourceProvider.getFolder(resourceProvider.pathContext + .canonicalize(contextLocation is File + ? contextLocation.parent2.path + : contextLocation.path)); /// Build a DartdocOptionContext via the 'inputDir' command line option. DartdocOptionContext.fromDefaultContextLocation( - this.optionSet, ResourceProvider resourceProvider) { - var current = resourceProvider.pathContext.current; - String inputDir = - optionSet['inputDir'].valueAt(resourceProvider.getFolder(current)) ?? - current; - context = resourceProvider.getFolder(inputDir); - } + this.optionSet, ResourceProvider resourceProvider) + : context = resourceProvider.getFolder(optionSet['inputDir'].valueAt( + resourceProvider + .getFolder(resourceProvider.pathContext.current)) ?? + resourceProvider.pathContext.current); /// Build a DartdocOptionContext from an analyzer element (using its source /// location). @@ -1282,13 +1233,9 @@ class DartdocOptionContext extends DartdocOptionContextBase String get examplePathPrefix => optionSet['examplePathPrefix'].valueAt(context); - /// A memoized calculation of exclusions. // TODO(srawlins): This memoization saved a lot of time in unit testing, but // is the first value in this class to be memoized. Memoize others? - /*late final*/ List _exclude; - - List get exclude => - _exclude ??= optionSet['exclude'].valueAt(context); + late final List exclude = optionSet['exclude'].valueAt(context); List get excludePackages => optionSet['excludePackages'].valueAt(context); @@ -1388,6 +1335,7 @@ Future> createDartdocOptions( 'in the current package or "include-external"', negatable: true), DartdocOptionArgFile>('categoryOrder', [], resourceProvider, + splitCommas: true, help: 'A list of categories (not package names) to place first when ' "grouping symbols on dartdoc's sidebar. Unmentioned categories are " 'sorted after these.'), @@ -1421,7 +1369,7 @@ Future> createDartdocOptions( return []; }, resourceProvider, help: 'Remove text from libraries with the following names.'), - DartdocOptionArgFile('examplePathPrefix', null, resourceProvider, + DartdocOptionArgFile('examplePathPrefix', null, resourceProvider, optionIs: OptionKind.dir, help: 'Prefix for @example paths.\n(defaults to the project root)', mustExist: true), @@ -1456,8 +1404,7 @@ Future> createDartdocOptions( negatable: true), DartdocOptionArgFile>('include', [], resourceProvider, help: 'Library names to generate docs for.', splitCommas: true), - DartdocOptionArgFile>( - 'includeExternal', null, resourceProvider, + DartdocOptionArgFile>('includeExternal', [], resourceProvider, optionIs: OptionKind.file, help: 'Additional (external) dart files to include; use "dir/fileName", ' @@ -1507,14 +1454,18 @@ Future> createDartdocOptions( // Prefer SDK check first, then pub cache check. var inSdk = packageMeta .sdkType(option.parent.parent['flutterRoot'].valueAt(dir)); + // Analyzer may be confused because package_meta still needs + // migrating. It can definitely return null. + // ignore: unnecessary_null_comparison if (inSdk != null) { Map sdks = option.parent['sdks'].valueAt(dir); - if (sdks.containsKey(inSdk)) return sdks[inSdk]; + if (sdks.containsKey(inSdk)) return sdks[inSdk]!; } var hostedAt = packageMeta.hostedAt; + // ignore: unnecessary_null_comparison if (hostedAt != null) { Map hostMap = option.parent['hosted'].valueAt(dir); - if (hostMap.containsKey(hostedAt)) return hostMap[hostedAt]; + if (hostMap.containsKey(hostedAt)) return hostMap[hostedAt]!; } return ''; }, resourceProvider, help: 'Url to use for this particular package.'), @@ -1534,6 +1485,7 @@ Future> createDartdocOptions( 'packageMeta', (DartdocSyntheticOption option, Folder dir) { var packageMeta = packageMetaProvider.fromDir(dir); + // ignore: unnecessary_null_comparison if (packageMeta == null) { throw DartdocOptionError( 'Unable to determine package for directory: ${dir.path}'); @@ -1543,17 +1495,18 @@ Future> createDartdocOptions( resourceProvider, ), DartdocOptionArgOnly>('packageOrder', [], resourceProvider, + splitCommas: true, help: 'A list of package names to place first when grouping libraries in ' 'packages. Unmentioned packages are sorted after these.'), DartdocOptionArgOnly('sdkDocs', false, resourceProvider, help: 'Generate ONLY the docs for the Dart SDK.'), - DartdocOptionArgSynth('sdkDir', - (DartdocSyntheticOption option, Folder dir) { + DartdocOptionArgSynth('sdkDir', + (DartdocSyntheticOption option, Folder dir) { if (!(option.parent['sdkDocs'].valueAt(dir) as bool) && (option.root['topLevelPackageMeta'].valueAt(dir) as PackageMeta) .requiresFlutter) { - String flutterRoot = option.root['flutterRoot'].valueAt(dir); + String? flutterRoot = option.root['flutterRoot'].valueAt(dir); if (flutterRoot == null) { // For now, return null. An error is reported in // [PackageBuilder.buildPackageGraph]. @@ -1574,6 +1527,7 @@ Future> createDartdocOptions( (DartdocSyntheticOption option, Folder dir) { var packageMeta = packageMetaProvider.fromDir( resourceProvider.getFolder(option.parent['inputDir'].valueAt(dir))); + // ignore: unnecessary_null_comparison if (packageMeta == null) { throw DartdocOptionError( 'Unable to generate documentation: no package found'); diff --git a/lib/src/generator/templates.runtime_renderers.dart b/lib/src/generator/templates.runtime_renderers.dart index 476d4695a1..578eaae7fc 100644 --- a/lib/src/generator/templates.runtime_renderers.dart +++ b/lib/src/generator/templates.runtime_renderers.dart @@ -14834,6 +14834,7 @@ const _invisibleGetters = { 'runtimeType', 'optionSet', 'context', + 'exclude', 'allowTools', 'ambiguousReexportScorerMinConfidence', 'autoIncludeDependencies', @@ -14841,7 +14842,6 @@ const _invisibleGetters = { 'categories', 'dropTextFrom', 'examplePathPrefix', - 'exclude', 'excludePackages', 'enhancedReferenceLookup', 'flutterRoot', diff --git a/lib/src/logging.dart b/lib/src/logging.dart index b56a8d39c1..6a673a0cd5 100644 --- a/lib/src/logging.dart +++ b/lib/src/logging.dart @@ -145,7 +145,7 @@ Future>> createLoggingOptions( negatable: true), DartdocOptionArgSynth('quiet', (DartdocSyntheticOption option, Folder dir) { - if (option.root['generateDocs']?.valueAt(dir) == false) { + if (option.parent['generateDocs'].valueAt(dir) == false) { return true; } return false; diff --git a/lib/src/warnings.dart b/lib/src/warnings.dart index f34b790e72..acd4aa272a 100644 --- a/lib/src/warnings.dart +++ b/lib/src/warnings.dart @@ -41,23 +41,28 @@ Future>> createPackageWarningOptions( // packages they don't control. DartdocOptionArgOnly>( 'allowWarningsInPackages', null, resourceProvider, + splitCommas: true, help: 'Package names to display warnings for (ignore all others if set).'), DartdocOptionArgOnly>( 'allowErrorsInPackages', null, resourceProvider, + splitCommas: true, help: 'Package names to display errors for (ignore all others if set)'), DartdocOptionArgOnly>( 'ignoreWarningsInPackages', null, resourceProvider, + splitCommas: true, help: 'Package names to ignore warnings for. Takes priority over ' 'allow-warnings-in-packages'), DartdocOptionArgOnly>( 'ignoreErrorsInPackages', null, resourceProvider, + splitCommas: true, help: 'Package names to ignore errors for. Takes priority over ' 'allow-errors-in-packages'), // Options for globally enabling/disabling warnings and errors across // packages. Loaded from dartdoc_options.yaml, but command line arguments // will override. DartdocOptionArgFile>('errors', null, resourceProvider, + splitCommas: true, help: 'Additional warning names to force as errors. Specify an empty ' 'list to force defaults (overriding dartdoc_options.yaml)\nDefaults:\n' + (packageWarningDefinitions.values @@ -68,6 +73,7 @@ Future>> createPackageWarningOptions( .map((d) => ' ${d.warningName}: ${d.shortHelp}') .join('\n')), DartdocOptionArgFile>('ignore', null, resourceProvider, + splitCommas: true, help: 'Additional warning names to ignore. Specify an empty list to ' 'force defaults (overriding dartdoc_options.yaml).\nDefaults:\n' + (packageWarningDefinitions.values @@ -78,6 +84,7 @@ Future>> createPackageWarningOptions( .map((d) => ' ${d.warningName}: ${d.shortHelp}') .join('\n')), DartdocOptionArgFile>('warnings', null, resourceProvider, + splitCommas: true, help: 'Additional warning names to show as warnings (instead of error or ' 'ignore, if not warning by default).\nDefaults:\n' + diff --git a/test/dartdoc_options_test.dart b/test/dartdoc_options_test.dart index 95f7d38bab..3f2a540962 100644 --- a/test/dartdoc_options_test.dart +++ b/test/dartdoc_options_test.dart @@ -43,10 +43,10 @@ class ConvertedOption { void main() { var resourceProvider = pubPackageMetaProvider.resourceProvider; - DartdocOptionSet dartdocOptionSetFiles; - DartdocOptionSet dartdocOptionSetArgs; - DartdocOptionSet dartdocOptionSetAll; - DartdocOptionSet dartdocOptionSetSynthetic; + DartdocOptionRoot dartdocOptionSetFiles; + DartdocOptionRoot dartdocOptionSetArgs; + DartdocOptionRoot dartdocOptionSetAll; + DartdocOptionRoot dartdocOptionSetSynthetic; Folder tempDir; Folder firstDir; Folder secondDir; @@ -59,7 +59,7 @@ void main() { File firstExisting; setUpAll(() { - dartdocOptionSetSynthetic = DartdocOptionSet('dartdoc', resourceProvider); + dartdocOptionSetSynthetic = DartdocOptionRoot('dartdoc', resourceProvider); dartdocOptionSetSynthetic.add( DartdocOptionArgFile('mySpecialInteger', 91, resourceProvider)); dartdocOptionSetSynthetic.add( @@ -86,7 +86,7 @@ void main() { return (option.root['vegetableLoader'].valueAt(dir) as List).first; }, resourceProvider, optionIs: OptionKind.file)); - dartdocOptionSetFiles = DartdocOptionSet('dartdoc', resourceProvider); + dartdocOptionSetFiles = DartdocOptionRoot('dartdoc', resourceProvider); dartdocOptionSetFiles.add(DartdocOptionFileOnly>( 'categoryOrder', [], resourceProvider)); dartdocOptionSetFiles @@ -122,7 +122,7 @@ void main() { convertYamlToType: ConvertedOption.fromYamlMap, )); - dartdocOptionSetArgs = DartdocOptionSet('dartdoc', resourceProvider); + dartdocOptionSetArgs = DartdocOptionRoot('dartdoc', resourceProvider); dartdocOptionSetArgs.add(DartdocOptionArgOnly( 'cauliflowerSystem', false, resourceProvider)); dartdocOptionSetArgs.add(DartdocOptionArgOnly( @@ -152,7 +152,7 @@ void main() { 'unimportantFile', 'whatever', resourceProvider, optionIs: OptionKind.file)); - dartdocOptionSetAll = DartdocOptionSet('dartdoc', resourceProvider); + dartdocOptionSetAll = DartdocOptionRoot('dartdoc', resourceProvider); dartdocOptionSetAll.add(DartdocOptionArgFile>( 'categoryOrder', [], resourceProvider)); dartdocOptionSetAll.add( diff --git a/test/documentation_comment_test.dart b/test/documentation_comment_test.dart index 1650f759d9..f297926ec7 100644 --- a/test/documentation_comment_test.dart +++ b/test/documentation_comment_test.dart @@ -53,7 +53,7 @@ void main() { sdkFolder, defaultSdk: mockSdk, ); - var optionSet = await DartdocOptionSet.fromOptionGenerators( + var optionSet = await DartdocOptionRoot.fromOptionGenerators( 'dartdoc', [createDartdocOptions], packageMetaProvider); optionSet.parseArguments([]); packageConfigProvider = FakePackageConfigProvider(); diff --git a/test/end2end/dartdoc_test.dart b/test/end2end/dartdoc_test.dart index 62f961e1cc..047dc158d8 100644 --- a/test/end2end/dartdoc_test.dart +++ b/test/end2end/dartdoc_test.dart @@ -49,7 +49,7 @@ final Folder _testPackageExperiments = /// the '--input' flag. Future _generatorContextFromArgv( List argv) async { - var optionSet = await DartdocOptionSet.fromOptionGenerators( + var optionSet = await DartdocOptionRoot.fromOptionGenerators( 'dartdoc', [ createDartdocOptions, @@ -73,8 +73,10 @@ void main() { Folder tempDir; setUpAll(() async { - var optionSet = await DartdocOptionSet.fromOptionGenerators( - 'dartdoc', [createLoggingOptions], pubPackageMetaProvider); + var optionSet = await DartdocOptionRoot.fromOptionGenerators( + 'dartdoc', + [createDartdocProgramOptions, createLoggingOptions], + pubPackageMetaProvider); optionSet.parseArguments([]); startLogging(DartdocLoggingOptionContext( optionSet, diff --git a/test/mustachio/renderers_output_test.dart b/test/mustachio/renderers_output_test.dart index 39c7dbf604..5f0071342f 100644 --- a/test/mustachio/renderers_output_test.dart +++ b/test/mustachio/renderers_output_test.dart @@ -21,7 +21,7 @@ import 'package:test/test.dart'; /// the '--input' flag. Future _generatorContextFromArgv( List argv) async { - var optionSet = await DartdocOptionSet.fromOptionGenerators( + var optionSet = await DartdocOptionRoot.fromOptionGenerators( 'dartdoc', [ createDartdocOptions, diff --git a/test/package_test.dart b/test/package_test.dart index 4c44da5178..183e00bb35 100644 --- a/test/package_test.dart +++ b/test/package_test.dart @@ -40,7 +40,7 @@ void main() { resourceProvider = packageMetaProvider.resourceProvider; sdkFolder = packageMetaProvider.defaultSdkDir; - optionSet = await DartdocOptionSet.fromOptionGenerators( + optionSet = await DartdocOptionRoot.fromOptionGenerators( 'dartdoc', [createDartdocOptions], packageMetaProvider); packageConfigProvider = utils.getTestPackageConfigProvider(sdkFolder.path); }); diff --git a/test/src/utils.dart b/test/src/utils.dart index 3636ddf3f3..46b0e60be7 100644 --- a/test/src/utils.dart +++ b/test/src/utils.dart @@ -36,7 +36,7 @@ final Folder testPackageToolError = _resourceProvider.getFolder(_pathContext /// [DartdocOptionSet] based on the current working directory. Future contextFromArgv( List argv, PackageMetaProvider packageMetaProvider) async { - var optionSet = await DartdocOptionSet.fromOptionGenerators( + var optionSet = await DartdocOptionRoot.fromOptionGenerators( 'dartdoc', [createDartdocOptions], packageMetaProvider); optionSet.parseArguments(argv); return DartdocOptionContext.fromDefaultContextLocation( diff --git a/test/warnings_test.dart b/test/warnings_test.dart index 6f63e6b497..f4f571abf9 100644 --- a/test/warnings_test.dart +++ b/test/warnings_test.dart @@ -56,7 +56,7 @@ dartdoc: }); setUp(() async { - optionSet = await DartdocOptionSet.fromOptionGenerators( + optionSet = await DartdocOptionRoot.fromOptionGenerators( 'dartdoc', [createDartdocOptions], pubPackageMetaProvider); }); From 056995dd32c601425b7b91c835dc3838f83587f2 Mon Sep 17 00:00:00 2001 From: Janice Collins Date: Tue, 24 Aug 2021 10:33:30 -0700 Subject: [PATCH 06/47] Migrate package_meta, io_utils, and utils. (#2760) * flatten * Review comments --- lib/src/dartdoc_options.dart | 12 +-- lib/src/io_utils.dart | 23 +++-- lib/src/model/accessor.dart | 12 ++- lib/src/package_meta.dart | 182 ++++++++++++++++------------------- lib/src/utils.dart | 13 +-- 5 files changed, 114 insertions(+), 128 deletions(-) diff --git a/lib/src/dartdoc_options.dart b/lib/src/dartdoc_options.dart index 544e32dcdf..fe05e6f79c 100644 --- a/lib/src/dartdoc_options.dart +++ b/lib/src/dartdoc_options.dart @@ -1388,12 +1388,12 @@ Future> createDartdocOptions( negatable: true), // This could be a ArgOnly, but trying to not provide too many ways // to set the flutter root. - DartdocOptionSyntheticOnly( - 'flutterRoot', - (DartdocSyntheticOption option, Folder dir) => resourceProvider - .pathContext - .resolveTildePath(Platform.environment['FLUTTER_ROOT']), - resourceProvider, + DartdocOptionSyntheticOnly('flutterRoot', + (DartdocSyntheticOption option, Folder dir) { + var envFlutterRoot = Platform.environment['FLUTTER_ROOT']; + if (envFlutterRoot == null) return null; + return resourceProvider.pathContext.resolveTildePath(envFlutterRoot); + }, resourceProvider, optionIs: OptionKind.dir, help: 'Root of the Flutter SDK, specified from environment.', mustExist: true), diff --git a/lib/src/io_utils.dart b/lib/src/io_utils.dart index 97a95c18a6..944bc36e1a 100644 --- a/lib/src/io_utils.dart +++ b/lib/src/io_utils.dart @@ -2,8 +2,6 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. -// @dart=2.9 - /// This is a helper library to make working with io easier. library dartdoc.io_utils; @@ -37,16 +35,16 @@ extension PathExtensions on path.Context { /// Return a resolved path including the home directory in place of tilde /// references. String resolveTildePath(String originalPath) { - if (originalPath == null || !originalPath.startsWith('~/')) { + if (!originalPath.startsWith('~/')) { return originalPath; } String homeDir; if (io.Platform.isWindows) { - homeDir = absolute(io.Platform.environment['USERPROFILE']); + homeDir = absolute(io.Platform.environment['USERPROFILE'] ?? '\''); } else { - homeDir = absolute(io.Platform.environment['HOME']); + homeDir = absolute(io.Platform.environment['HOME'] ?? '/'); } return join(homeDir, originalPath.substring(2)); @@ -67,8 +65,7 @@ extension ResourceProviderExtensions on ResourceProvider { if (this is PhysicalResourceProvider) { return io.Platform.resolvedExecutable; } else { - // TODO(srawlins): Return what is needed for tests. - return null; + throw UnimplementedError('resolvedExecutable not implemented'); } } @@ -77,8 +74,7 @@ extension ResourceProviderExtensions on ResourceProvider { var mode = io.File(file.path).statSync().mode; return (0x1 & ((mode >> 6) | (mode >> 3) | mode)) != 0; } else { - // TODO(srawlins) - return false; + throw UnimplementedError('isExecutable not implemented'); } } @@ -124,8 +120,11 @@ final RegExp newLinePartOfRegexp = RegExp('\npart of '); typedef TaskQueueClosure = Future Function(); +void _defaultOnComplete() {} + class _TaskQueueItem { - _TaskQueueItem(this._closure, this._completer, {this.onComplete}); + _TaskQueueItem(this._closure, this._completer, + {this.onComplete = _defaultOnComplete}); final TaskQueueClosure _closure; final Completer _completer; @@ -137,7 +136,7 @@ class _TaskQueueItem { } catch (e) { _completer.completeError(e); } finally { - onComplete?.call(); + onComplete.call(); } } } @@ -150,7 +149,7 @@ class TaskQueue { /// Creates a task queue with a maximum number of simultaneous jobs. /// The [maxJobs] parameter defaults to the number of CPU cores on the /// system. - TaskQueue({int maxJobs}) + TaskQueue({int? maxJobs}) : maxJobs = maxJobs ?? io.Platform.numberOfProcessors; /// The maximum number of jobs that this queue will run simultaneously. diff --git a/lib/src/model/accessor.dart b/lib/src/model/accessor.dart index 2d598809f9..968558a234 100644 --- a/lib/src/model/accessor.dart +++ b/lib/src/model/accessor.dart @@ -76,6 +76,7 @@ class Accessor extends ModelElement implements EnclosedElement { @override String computeDocumentationComment() { + String docComment; if (isSynthetic) { // If we're a setter, only display something if we have something different than the getter. // TODO(jcollins-g): modify analyzer to do this itself? @@ -85,12 +86,17 @@ class Accessor extends ModelElement implements EnclosedElement { definingCombo.hasGetter && definingCombo.getter.documentationComment != definingCombo.documentationComment)) { - return stripComments(definingCombo.documentationComment); + docComment = definingCombo.documentationComment; } else { - return ''; + docComment = ''; } + } else { + docComment = super.computeDocumentationComment(); + } + if (docComment != null) { + return stripComments(docComment); } - return stripComments(super.computeDocumentationComment()); + return null; } @override diff --git a/lib/src/package_meta.dart b/lib/src/package_meta.dart index d481f6019f..1dfc79105e 100644 --- a/lib/src/package_meta.dart +++ b/lib/src/package_meta.dart @@ -2,8 +2,6 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. -// @dart=2.9 - library dartdoc.package_meta; import 'dart:convert'; @@ -20,7 +18,7 @@ import 'package:yaml/yaml.dart'; import 'logging.dart'; -Map _packageMetaCache = {}; +Map _packageMetaCache = {}; Encoding utf8AllowMalformed = Utf8Codec(allowMalformed: true); @@ -30,7 +28,7 @@ class PackageMetaFailure extends DartdocFailure { /// For each list in this list, at least one of the given paths must exist /// for this to be detected as an SDK. -final List> __sdkDirFilePathsPosix = [ +final List> _sdkDirFilePathsPosix = [ ['bin/dart.bat', 'bin/dart.exe', 'bin/dart'], ['bin/pub.bat', 'bin/pub'], ['lib/core/core.dart'], @@ -58,17 +56,17 @@ final PackageMetaProvider pubPackageMetaProvider = PackageMetaProvider( class PackageMetaProvider { final ResourceProvider resourceProvider; final Folder defaultSdkDir; - final DartSdk defaultSdk; + final DartSdk? defaultSdk; - final PackageMeta Function(LibraryElement, String, ResourceProvider) + final PackageMeta? Function(LibraryElement, String, ResourceProvider) _fromElement; - final PackageMeta Function(String, ResourceProvider) _fromFilename; - final PackageMeta Function(Folder, ResourceProvider) _fromDir; + final PackageMeta? Function(String, ResourceProvider) _fromFilename; + final PackageMeta? Function(Folder, ResourceProvider) _fromDir; - PackageMeta fromElement(LibraryElement library, String s) => + PackageMeta? fromElement(LibraryElement library, String s) => _fromElement(library, s, resourceProvider); - PackageMeta fromFilename(String s) => _fromFilename(s, resourceProvider); - PackageMeta fromDir(Folder dir) => _fromDir(dir, resourceProvider); + PackageMeta? fromFilename(String s) => _fromFilename(s, resourceProvider); + PackageMeta? fromDir(Folder dir) => _fromDir(dir, resourceProvider); PackageMetaProvider(this._fromElement, this._fromFilename, this._fromDir, this.resourceProvider, this.defaultSdkDir, @@ -93,7 +91,7 @@ abstract class PackageMeta { @override bool operator ==(Object other) { if (other is! PackageMeta) return false; - PackageMeta otherMeta = other; + var otherMeta = other; return resourceProvider.pathContext.equals(dir.path, otherMeta.dir.path); } @@ -110,7 +108,7 @@ abstract class PackageMeta { /// Returns 'Dart' or 'Flutter' (preferentially, 'Flutter' when the answer is /// "both"), or null if this package is not part of a SDK. - String sdkType(String flutterRootPath); + String? sdkType(String flutterRootPath); bool get needsPubGet => false; @@ -122,7 +120,7 @@ abstract class PackageMeta { /// null if not a hosted pub package. If set, the hostname /// that the package is hosted at -- usually 'pub.dartlang.org'. - String get hostedAt; + String? get hostedAt; String get version; @@ -130,11 +128,11 @@ abstract class PackageMeta { String get homepage; - File getReadmeContents(); + File? getReadmeContents(); - File getLicenseContents(); + File? getLicenseContents(); - File getChangelogContents(); + File? getChangelogContents(); /// Returns true if we are a valid package, valid enough to generate docs. bool get isValid => getInvalidReasons().isEmpty; @@ -157,31 +155,28 @@ abstract class PubPackageMeta extends PackageMeta { PubPackageMeta(Folder dir, ResourceProvider resourceProvider) : super(dir, resourceProvider); - static List> __sdkDirFilePaths; - - static List> get _sdkDirFilePaths { - if (__sdkDirFilePaths == null) { - __sdkDirFilePaths = []; - if (Platform.isWindows) { - for (var paths in __sdkDirFilePathsPosix) { - var windowsPaths = [ - for (var path in paths) - p.joinAll(p.Context(style: p.Style.posix).split(path)), - ]; - __sdkDirFilePaths.add(windowsPaths); - } - } else { - __sdkDirFilePaths = __sdkDirFilePathsPosix; + static late final List> _sdkDirFilePaths = () { + var pathsToReturn = >[]; + if (Platform.isWindows) { + for (var paths in _sdkDirFilePathsPosix) { + var windowsPaths = [ + for (var path in paths) + p.joinAll(p.Context(style: p.Style.posix).split(path)), + ]; + pathsToReturn.add(windowsPaths); } + } else { + pathsToReturn = _sdkDirFilePathsPosix; } - return __sdkDirFilePaths; - } + return pathsToReturn; + }(); - static final _sdkDirParent = {}; + static final _sdkDirParent = {}; /// If [folder] is inside a Dart SDK, returns the directory of the SDK, and `null` /// otherwise. - static Folder sdkDirParent(Folder folder, ResourceProvider resourceProvider) { + static Folder? sdkDirParent( + Folder folder, ResourceProvider resourceProvider) { var pathContext = resourceProvider.pathContext; var dirPathCanonical = pathContext.canonicalize(folder.path); if (!_sdkDirParent.containsKey(dirPathCanonical)) { @@ -200,8 +195,8 @@ abstract class PubPackageMeta extends PackageMeta { } /// Use this instead of fromDir where possible. - static PubPackageMeta fromElement(LibraryElement libraryElement, - String sdkDir, ResourceProvider resourceProvider) { + static PackageMeta? fromElement(LibraryElement libraryElement, String sdkDir, + ResourceProvider resourceProvider) { if (libraryElement.isInSdk) { return PubPackageMeta.fromDir( resourceProvider.getFolder(sdkDir), resourceProvider); @@ -214,7 +209,7 @@ abstract class PubPackageMeta extends PackageMeta { resourceProvider); } - static PubPackageMeta fromFilename( + static PackageMeta? fromFilename( String filename, ResourceProvider resourceProvider) { return PubPackageMeta.fromDir( resourceProvider.getFile(filename).parent2, resourceProvider); @@ -224,7 +219,7 @@ abstract class PubPackageMeta extends PackageMeta { /// [dir.absolute.path]. Multiple [dir.absolute.path]s will resolve to the /// same object if they are part of the same package. Returns null /// if the directory is not part of a known package. - static PubPackageMeta fromDir( + static PackageMeta? fromDir( Folder folder, ResourceProvider resourceProvider) { var pathContext = resourceProvider.pathContext; var original = @@ -236,7 +231,7 @@ abstract class PubPackageMeta extends PackageMeta { } if (!_packageMetaCache.containsKey(folder.path)) { - PackageMeta packageMeta; + PackageMeta? packageMeta; // There are pubspec.yaml files inside the SDK. Ignore them. var parentSdkDir = sdkDirParent(folder, resourceProvider); if (parentSdkDir != null) { @@ -257,7 +252,7 @@ abstract class PubPackageMeta extends PackageMeta { } @override - String sdkType(String flutterRootPath) { + String? sdkType(String? flutterRootPath) { if (flutterRootPath != null) { var flutterPackages = pathContext.join(flutterRootPath, 'packages'); var flutterBinCache = pathContext.join(flutterRootPath, 'bin', 'cache'); @@ -274,61 +269,52 @@ abstract class PubPackageMeta extends PackageMeta { return isSdk ? 'Dart' : null; } - String _resolvedDir; - @override - String get resolvedDir { - _resolvedDir ??= dir.resolveSymbolicLinksSync().path; - return _resolvedDir; - } + late final String resolvedDir = dir.resolveSymbolicLinksSync().path; } class _FilePackageMeta extends PubPackageMeta { - File _readme; - File _license; - File _changelog; - Map _pubspec; + File? _readme; + File? _license; + File? _changelog; - _FilePackageMeta(Folder dir, ResourceProvider resourceProvider) - : super(dir, resourceProvider) { + late final Map _pubspec = () { var pubspec = dir.getChildAssumingFile('pubspec.yaml'); assert(pubspec.exists); - _pubspec = loadYaml(pubspec.readAsStringSync()); - } + return loadYaml(pubspec.readAsStringSync()); + }(); - bool _setHostedAt = false; - String _hostedAt; + _FilePackageMeta(Folder dir, ResourceProvider resourceProvider) + : super(dir, resourceProvider); @override - String get hostedAt { - if (!_setHostedAt) { - _setHostedAt = true; - // Search for 'hosted/host.domain' as the immediate parent directories, - // and verify that a directory "_temp" exists alongside "hosted". Those - // seem to be the only guaranteed things to exist if we're from a pub - // cache. - // - // TODO(jcollins-g): This is a funky heuristic. Make this better somehow, - // possibly by calculating hosting directly from pubspec.yaml or importing - // a pub library to do this. - // People could have a pub cache at root with Windows drive mappings. - if (pathContext.split(pathContext.canonicalize(dir.path)).length >= 3) { - var pubCacheRoot = dir.parent2.parent2.parent2.path; - // Check for directory structure too close to root. - if (pubCacheRoot != dir.parent2.parent2.path) { - var hosted = pathContext.canonicalize(dir.parent2.parent2.path); - var hostname = pathContext.canonicalize(dir.parent2.path); - if (pathContext.basename(hosted) == 'hosted' && - resourceProvider - .getFolder(pathContext.join(pubCacheRoot, '_temp')) - .exists) { - _hostedAt = pathContext.basename(hostname); - } + late final String? hostedAt = () { + String? _hostedAt; + // Search for 'hosted/host.domain' as the immediate parent directories, + // and verify that a directory "_temp" exists alongside "hosted". Those + // seem to be the only guaranteed things to exist if we're from a pub + // cache. + // + // TODO(jcollins-g): This is a funky heuristic. Make this better somehow, + // possibly by calculating hosting directly from pubspec.yaml or importing + // a pub library to do this. + // People could have a pub cache at root with Windows drive mappings. + if (pathContext.split(pathContext.canonicalize(dir.path)).length >= 3) { + var pubCacheRoot = dir.parent2.parent2.parent2.path; + // Check for directory structure too close to root. + if (pubCacheRoot != dir.parent2.parent2.path) { + var hosted = pathContext.canonicalize(dir.parent2.parent2.path); + var hostname = pathContext.canonicalize(dir.parent2.path); + if (pathContext.basename(hosted) == 'hosted' && + resourceProvider + .getFolder(pathContext.join(pubCacheRoot, '_temp')) + .exists) { + _hostedAt = pathContext.basename(hostname); } } } return _hostedAt; - } + }(); @override bool get isSdk => false; @@ -384,20 +370,20 @@ class _FilePackageMeta extends PubPackageMeta { _environment?.containsKey('flutter') == true || _dependencies?.containsKey('flutter') == true; - YamlMap /*?*/ get _environment => _pubspec['environment']; + YamlMap? get _environment => _pubspec['environment']; - YamlMap /*?*/ get _dependencies => _pubspec['environment']; + YamlMap? get _dependencies => _pubspec['environment']; @override - File getReadmeContents() => + File? getReadmeContents() => _readme ??= _locate(dir, ['readme.md', 'readme.txt', 'readme']); @override - File getLicenseContents() => + File? getLicenseContents() => _license ??= _locate(dir, ['license.md', 'license.txt', 'license']); @override - File getChangelogContents() => _changelog ??= + File? getChangelogContents() => _changelog ??= _locate(dir, ['changelog.md', 'changelog.txt', 'changelog']); /// Returns a list of reasons this package is invalid, or an @@ -405,7 +391,7 @@ class _FilePackageMeta extends PubPackageMeta { @override List getInvalidReasons() { var reasons = []; - if (_pubspec == null || _pubspec.isEmpty) { + if (_pubspec.isEmpty) { reasons.add('no pubspec.yaml found'); } else if (!_pubspec.containsKey('name')) { reasons.add('no name found in pubspec.yaml'); @@ -414,7 +400,7 @@ class _FilePackageMeta extends PubPackageMeta { } } -File _locate(Folder dir, List fileNames) { +File? _locate(Folder dir, List fileNames) { var files = dir.getChildren().whereType().toList(); for (var name in fileNames) { @@ -429,16 +415,14 @@ File _locate(Folder dir, List fileNames) { } class _SdkMeta extends PubPackageMeta { - String sdkReadmePath; + late final String sdkReadmePath = + resourceProvider.pathContext.join(dir.path, 'lib', 'api_readme.md'); _SdkMeta(Folder dir, ResourceProvider resourceProvider) - : super(dir, resourceProvider) { - sdkReadmePath = - resourceProvider.pathContext.join(dir.path, 'lib', 'api_readme.md'); - } + : super(dir, resourceProvider); @override - String get hostedAt => null; + String? get hostedAt => null; @override bool get isSdk => true; @@ -471,7 +455,7 @@ class _SdkMeta extends PubPackageMeta { bool get requiresFlutter => false; @override - File getReadmeContents() { + File? getReadmeContents() { var f = resourceProvider.getFile( resourceProvider.pathContext.join(dir.path, 'lib', 'api_readme.md')); if (!f.exists) { @@ -485,11 +469,11 @@ class _SdkMeta extends PubPackageMeta { List getInvalidReasons() => []; @override - File getLicenseContents() => null; + File? getLicenseContents() => null; // TODO: The changelog doesn't seem to be available in the sdk. @override - File getChangelogContents() => null; + File? getChangelogContents() => null; } @visibleForTesting diff --git a/lib/src/utils.dart b/lib/src/utils.dart index 5819b6d3c3..ab67154d47 100644 --- a/lib/src/utils.dart +++ b/lib/src/utils.dart @@ -2,8 +2,6 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. -// @dart=2.9 - library dartdoc.utils; final RegExp leadingWhiteSpace = RegExp(r'^([ \t]*)[^ ]'); @@ -11,14 +9,15 @@ final RegExp leadingWhiteSpace = RegExp(r'^([ \t]*)[^ ]'); Iterable stripCommonWhitespace(String str) sync* { if (str.isEmpty) return; final lines = str.split('\n'); - int /*?*/ minimumSeen; + int? minimumSeen; for (final line in lines) { if (line.isNotEmpty) { final match = leadingWhiteSpace.firstMatch(line); if (match != null) { - if (minimumSeen == null || match.group(1).length < minimumSeen) { - minimumSeen = match.group(1).length; + var groupLength = match.group(1)!.length; + if (minimumSeen == null || groupLength < minimumSeen) { + minimumSeen = groupLength; } } } @@ -34,8 +33,6 @@ Iterable stripCommonWhitespace(String str) sync* { } String stripComments(String str) { - // TODO(parlough): Once we migrate to null safety, prohibit null here - if (str == null) return null; if (str.isEmpty) return ''; final buf = StringBuffer(); @@ -72,7 +69,7 @@ String stripComments(String str) { } String truncateString(String str, int length) { - if (str != null && str.length > length) { + if (str.length > length) { // Do not call this on unsanitized HTML. assert(!str.contains('<')); return '${str.substring(0, length)}…'; From 2f11e3e844305472763179a6f778a9185a21f706 Mon Sep 17 00:00:00 2001 From: Janice Collins Date: Tue, 7 Sep 2021 17:12:33 -0700 Subject: [PATCH 07/47] opt-out for inheriting container --- lib/src/model/inheriting_container.dart | 2 ++ 1 file changed, 2 insertions(+) diff --git a/lib/src/model/inheriting_container.dart b/lib/src/model/inheriting_container.dart index 445c5f4a89..39a202ed1a 100644 --- a/lib/src/model/inheriting_container.dart +++ b/lib/src/model/inheriting_container.dart @@ -2,6 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. +// @dart=2.9 + import 'package:analyzer/dart/element/element.dart'; import 'package:analyzer/dart/element/type.dart'; import 'package:dartdoc/src/element_type.dart'; From c33b4f7f4e3be4f9a4ef4b1f0197f76e90cc5b2a Mon Sep 17 00:00:00 2001 From: Janice Collins Date: Tue, 14 Sep 2021 09:21:39 -0700 Subject: [PATCH 08/47] A few more libraries migrated --- lib/src/experiment_options.dart | 3 -- lib/src/generator/generator.dart | 10 +++---- lib/src/source_linker.dart | 48 +++++++++++++++----------------- lib/src/tool_definition.dart | 45 ++++++++++++------------------ test/source_linker_test.dart | 1 + 5 files changed, 45 insertions(+), 62 deletions(-) diff --git a/lib/src/experiment_options.dart b/lib/src/experiment_options.dart index fa22f5da2d..5201b86515 100644 --- a/lib/src/experiment_options.dart +++ b/lib/src/experiment_options.dart @@ -2,8 +2,6 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. -// @dart=2.9 - /// /// Implementation of Dart language experiment option handling for dartdoc. /// See https://github.com/dart-lang/sdk/blob/main/docs/process/experimental-flags.md. @@ -30,7 +28,6 @@ Future>> createExperimentOptions( 'enable-experiment', ['non-nullable'], resourceProvider, help: 'Enable or disable listed experiments.\n' + ExperimentStatus.knownFeatures.values - .where((e) => e.documentation != null) .map((e) => ' [no-]${e.enableString}: ${e.documentation} (default: ${e.isEnabledByDefault})') .join('\n')), diff --git a/lib/src/generator/generator.dart b/lib/src/generator/generator.dart index 2a5c2f319e..7246e61184 100644 --- a/lib/src/generator/generator.dart +++ b/lib/src/generator/generator.dart @@ -2,8 +2,6 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. -// @dart=2.9 - /// A library containing an abstract documentation generator. library dartdoc.generator; @@ -45,7 +43,7 @@ abstract class Generator { Future generate(PackageGraph packageGraph, FileWriter writer); } -Future>> createGeneratorOptions( +Future> createGeneratorOptions( PackageMetaProvider packageMetaProvider) async { var resourceProvider = packageMetaProvider.resourceProvider; return [ @@ -73,16 +71,16 @@ Future>> createGeneratorOptions( 'Generates `index.json` with indentation and newlines. The file is ' 'larger, but it\'s also easier to diff.', negatable: false), - DartdocOptionArgFile('favicon', null, resourceProvider, + DartdocOptionArgFile('favicon', null, resourceProvider, optionIs: OptionKind.file, help: 'A path to a favicon for the generated docs.', mustExist: true), - DartdocOptionArgOnly('relCanonicalPrefix', null, resourceProvider, + DartdocOptionArgOnly('relCanonicalPrefix', null, resourceProvider, help: 'If provided, add a rel="canonical" prefixed with provided value. ' 'Consider using if building many versions of the docs for public ' 'SEO; learn more at https://goo.gl/gktN6F.'), - DartdocOptionArgOnly('templatesDir', null, resourceProvider, + DartdocOptionArgOnly('templatesDir', null, resourceProvider, optionIs: OptionKind.dir, mustExist: true, hide: true, diff --git a/lib/src/source_linker.dart b/lib/src/source_linker.dart index 5fc2313ce1..97b8660136 100644 --- a/lib/src/source_linker.dart +++ b/lib/src/source_linker.dart @@ -2,37 +2,31 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. -// @dart=2.9 - /// A library for getting external source code links for Dartdoc. library dartdoc.source_linker; import 'package:analyzer/file_system/file_system.dart'; import 'package:dartdoc/src/dartdoc_options.dart'; import 'package:dartdoc/src/model/model.dart'; -import 'package:meta/meta.dart'; import 'package:path/path.dart' as path; final _uriTemplateRegExp = RegExp(r'(%[frl]%)'); -@Deprecated('Public variable intended to be private; will be removed as early ' - 'as Dartdoc 1.0.0') -RegExp get uriTemplateRegexp => _uriTemplateRegExp; abstract class SourceLinkerOptionContext implements DartdocOptionContextBase { List get linkToSourceExcludes => optionSet['linkToSource']['excludes'].valueAt(context); - String get linkToSourceRevision => + String? get linkToSourceRevision => optionSet['linkToSource']['revision'].valueAt(context); - String get linkToSourceRoot => + String? get linkToSourceRoot => optionSet['linkToSource']['root'].valueAt(context); - String get linkToSourceUriTemplate => + String? get linkToSourceUriTemplate => optionSet['linkToSource']['uriTemplate'].valueAt(context); } -Future>> createSourceLinkerOptions( +Future>> createSourceLinkerOptions( ResourceProvider resourceProvider) async { return [ DartdocOptionSet('linkToSource', resourceProvider) @@ -42,13 +36,13 @@ Future>> createSourceLinkerOptions( help: 'A list of directories to exclude from linking to a source code repository.'), // TODO(jcollins-g): Use [DartdocOptionArgSynth], possibly in combination with a repository type and the root directory, and get revision number automatically - DartdocOptionArgOnly('revision', null, resourceProvider, + DartdocOptionArgOnly('revision', null, resourceProvider, help: 'Revision number to insert into the URI.'), - DartdocOptionArgFile('root', null, resourceProvider, + DartdocOptionArgFile('root', null, resourceProvider, optionIs: OptionKind.dir, help: 'Path to a local directory that is the root of the repository we link to. All source code files under this directory will be linked.'), - DartdocOptionArgFile('uriTemplate', null, resourceProvider, + DartdocOptionArgFile('uriTemplate', null, resourceProvider, help: '''Substitute into this template to generate a uri for an element's source code. Dartdoc dynamically substitutes the following fields into the template: @@ -63,16 +57,16 @@ class SourceLinker { final List excludes; final int lineNumber; final String sourceFileName; - final String revision; - final String root; - final String uriTemplate; + final String? revision; + final String? root; + final String? uriTemplate; /// Most users of this class should use the [SourceLinker.fromElement] factory /// instead. This constructor is public for testing. SourceLinker( - {@required this.excludes, - this.lineNumber, - this.sourceFileName, + {required this.excludes, + required this.lineNumber, + required this.sourceFileName, this.revision, this.root, this.uriTemplate}) { @@ -81,7 +75,10 @@ class SourceLinker { throw DartdocOptionError( 'linkToSource root and uriTemplate must both be specified to generate repository links'); } - if (uriTemplate.contains('%r%') && revision == null) { + var uriTemplateValue = uriTemplate; + if (uriTemplateValue != null && + uriTemplateValue.contains('%r%') && + revision == null) { throw DartdocOptionError( r'%r% specified in uriTemplate, but no revision available'); } @@ -104,7 +101,9 @@ class SourceLinker { } String href() { - if (sourceFileName == null || root == null || uriTemplate == null) { + var root = this.root; + var uriTemplate = this.uriTemplate; + if (root == null || uriTemplate == null) { return ''; } if (!path.isWithin(root, sourceFileName) || @@ -118,15 +117,12 @@ class SourceLinker { var urlContext = path.Context(style: path.Style.url); return urlContext .joinAll(path.split(path.relative(sourceFileName, from: root))); - break; case '%r%': - return revision; - break; + return revision!; case '%l%': return lineNumber.toString(); - break; default: - return null; + return ''; } }); } diff --git a/lib/src/tool_definition.dart b/lib/src/tool_definition.dart index ba39692c45..9885dcd876 100644 --- a/lib/src/tool_definition.dart +++ b/lib/src/tool_definition.dart @@ -2,15 +2,12 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. -// @dart=2.9 - import 'dart:async'; import 'package:analyzer/file_system/file_system.dart'; import 'package:dartdoc/src/dartdoc_options.dart'; import 'package:dartdoc/src/io_utils.dart'; import 'package:dartdoc/src/tool_runner.dart'; -import 'package:meta/meta.dart'; import 'package:path/path.dart' as p show extension; /// Defines the attributes of a tool in the options file, corresponding to @@ -19,15 +16,15 @@ import 'package:path/path.dart' as p show extension; class ToolDefinition { /// A list containing the command and options to be run for this tool. The /// first argument in the command is the tool executable, and will have its - /// path evaluated relative to the `dartdoc_options.yaml` location. Must not - /// be an empty list, or be null. + /// path evaluated relative to the `dartdoc_options.yaml` location. Must + /// not be empty. final List command; /// A list containing the command and options to setup phase for this tool. /// The first argument in the command is the tool executable, and will have /// its path evaluated relative to the `dartdoc_options.yaml` location. May /// be null or empty, in which case it will be ignored at setup time. - final List setupCommand; + final List? setupCommand; /// A description of the defined tool. Must not be null. final String description; @@ -46,13 +43,11 @@ class ToolDefinition { /// given. factory ToolDefinition.fromCommand( List command, - List setupCommand, + List? setupCommand, String description, ResourceProvider resourceProvider, - {List compileArgs}) { - assert(command != null); + {List? compileArgs}) { assert(command.isNotEmpty); - assert(description != null); if (isDartExecutable(command[0])) { return DartToolDefinition( command, setupCommand, description, resourceProvider, @@ -69,12 +64,11 @@ class ToolDefinition { } ToolDefinition(this.command, this.setupCommand, this.description) - : assert(command != null), - assert(command.isNotEmpty), - assert(description != null); + : assert(command.isNotEmpty); @override String toString() { + var setupCommand = this.setupCommand; final commandString = '${this is DartToolDefinition ? '(Dart) ' : ''}"${command.join(' ')}"'; if (setupCommand == null) { @@ -86,7 +80,7 @@ class ToolDefinition { } Future toolStateForArgs(String toolName, List args, - {@required ToolErrorCallback toolErrorCallback}) async { + {required ToolErrorCallback toolErrorCallback}) async { var commandPath = args.removeAt(0); return ToolStateForArgs(commandPath, args, null); } @@ -107,7 +101,7 @@ class DartToolDefinition extends ToolDefinition { /// built. @override Future toolStateForArgs(String toolName, List args, - {@required ToolErrorCallback toolErrorCallback}) async { + {required ToolErrorCallback toolErrorCallback}) async { assert(args[0] == command.first); // Set up flags to create a new snapshot, if needed, and use the first run // as the training run. @@ -135,11 +129,9 @@ class DartToolDefinition extends ToolDefinition { } else { await snapshot._snapshotValid(); if (!snapshotFile.exists) { - if (toolErrorCallback != null) { - toolErrorCallback( - 'Snapshot creation failed for $toolName tool. $snapshotPath does ' - 'not exist. Will execute tool without snapshot.'); - } + toolErrorCallback( + 'Snapshot creation failed for $toolName tool. $snapshotPath does ' + 'not exist. Will execute tool without snapshot.'); } else { // replace the first argument with the path to the snapshot. args[0] = snapshotPath; @@ -148,11 +140,10 @@ class DartToolDefinition extends ToolDefinition { } } - DartToolDefinition(List command, List setupCommand, + DartToolDefinition(List command, List? setupCommand, String description, this._resourceProvider, {this.compileArgs = const []}) - : assert(compileArgs != null), - super(command, setupCommand, description); + : super(command, setupCommand, description); } /// Manages the creation of a single snapshot file in a context where multiple @@ -238,17 +229,17 @@ class SnapshotCache { _Snapshot getSnapshot(String toolPath) { if (snapshots.containsKey(toolPath)) { - return snapshots[toolPath]; + return snapshots[toolPath]!; } snapshots[toolPath] = _Snapshot(snapshotCache, toolPath, _serial, _resourceProvider); _serial++; - return snapshots[toolPath]; + return snapshots[toolPath]!; } void dispose() { _instances.remove(_resourceProvider); - if (snapshotCache != null && snapshotCache.exists) { + if (snapshotCache.exists) { return snapshotCache.delete(); } return null; @@ -258,7 +249,7 @@ class SnapshotCache { class ToolStateForArgs { final String commandPath; final List args; - final void Function() onProcessComplete; + final void Function()? onProcessComplete; ToolStateForArgs(this.commandPath, this.args, this.onProcessComplete); } diff --git a/test/source_linker_test.dart b/test/source_linker_test.dart index adc591e34a..bf581e710a 100644 --- a/test/source_linker_test.dart +++ b/test/source_linker_test.dart @@ -53,6 +53,7 @@ void main() { excludes: [], lineNumber: 20, revision: '12345', + sourceFileName: 'path/to/file.dart', ).href(); expect(sourceLinkerHref, throwsA(TypeMatcher())); }); From 8a8972c8ddd9d7920d89af0224fac688c0d56470 Mon Sep 17 00:00:00 2001 From: Sam Rawlins Date: Thu, 16 Sep 2021 13:05:27 -0700 Subject: [PATCH 09/47] Migrate warnings.dart (#2787) --- lib/src/dartdoc_options.dart | 7 +- lib/src/model/accessor.dart | 10 +- lib/src/warnings.dart | 264 +++++++++++++++++++---------------- 3 files changed, 158 insertions(+), 123 deletions(-) diff --git a/lib/src/dartdoc_options.dart b/lib/src/dartdoc_options.dart index 6d8143667b..f4e8da6326 100644 --- a/lib/src/dartdoc_options.dart +++ b/lib/src/dartdoc_options.dart @@ -450,7 +450,7 @@ abstract class DartdocOption { /// To avoid accessing early, call [add] on the option's parent before /// looking up unless this is a [DartdocRootOption]. - late final DartdocOption parent; + late final DartdocOption parent; /// The [DartdocOptionRoot] containing this object. DartdocOptionRoot get root { @@ -516,10 +516,13 @@ abstract class DartdocOption { void addAll(Iterable options) => options.forEach(add); /// Get the immediate child of this node named [name]. - DartdocOption operator [](String name) { + DartdocOption operator [](String name) { return _children[name]!; } + /// Get the immediate child of this node named [name] as a [DartdocOption]. + DartdocOption getAs(String name) => _children[name] as DartdocOption; + /// Apply the function [visit] to [this] and all children. void traverse(void Function(DartdocOption option) visit) { visit(this); diff --git a/lib/src/model/accessor.dart b/lib/src/model/accessor.dart index 0ac4bb091e..d37f70aa2c 100644 --- a/lib/src/model/accessor.dart +++ b/lib/src/model/accessor.dart @@ -100,10 +100,12 @@ class Accessor extends ModelElement implements EnclosedElement { } @override - void warn(PackageWarning kind, - {String message, - Iterable referredFrom, - Iterable extendedDebug}) { + void warn( + PackageWarning kind, { + String message, + Iterable referredFrom = const [], + Iterable extendedDebug = const [], + }) { enclosingCombo.warn(kind, message: message, referredFrom: referredFrom, diff --git a/lib/src/warnings.dart b/lib/src/warnings.dart index 46669104a7..ddf05aa2fd 100644 --- a/lib/src/warnings.dart +++ b/lib/src/warnings.dart @@ -2,8 +2,6 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. -// @dart=2.9 - import 'dart:collection'; import 'package:analyzer/dart/element/element.dart'; @@ -14,19 +12,22 @@ import 'package:dartdoc/src/model/comment_referable.dart'; import 'package:dartdoc/src/model/model.dart'; import 'package:dartdoc/src/package_meta.dart'; +const _namePlaceholder = '@@name@@'; + abstract class PackageWarningOptionContext implements DartdocOptionContextBase { bool get allowNonLocalWarnings => optionSet['allowNonLocalWarnings'].valueAt(context); - // allowWarningsInPackages, ignoreWarningsInPackages, errors, warnings, and ignore - // are only used indirectly via the synthetic packageWarningOptions option. + // allowWarningsInPackages, ignoreWarningsInPackages, errors, warnings, and + // ignore are only used indirectly via the synthetic packageWarningOptions + // option. PackageWarningOptions get packageWarningOptions => optionSet['packageWarningOptions'].valueAt(context); bool get verboseWarnings => optionSet['verboseWarnings'].valueAt(context); } -Future>> createPackageWarningOptions( +Future>> createPackageWarningOptions( PackageMetaProvider packageMetaProvider, ) async { var resourceProvider = packageMetaProvider.resourceProvider; @@ -39,21 +40,21 @@ Future>> createPackageWarningOptions( // for individual packages are command-line only. This will allow // meta-packages like Flutter to control whether warnings are displayed for // packages they don't control. - DartdocOptionArgOnly>( + DartdocOptionArgOnly?>( 'allowWarningsInPackages', null, resourceProvider, splitCommas: true, help: - 'Package names to display warnings for (ignore all others if set).'), - DartdocOptionArgOnly>( + 'Package names to display warnings for (ignore all others if set)'), + DartdocOptionArgOnly?>( 'allowErrorsInPackages', null, resourceProvider, splitCommas: true, help: 'Package names to display errors for (ignore all others if set)'), - DartdocOptionArgOnly>( + DartdocOptionArgOnly?>( 'ignoreWarningsInPackages', null, resourceProvider, splitCommas: true, help: 'Package names to ignore warnings for. Takes priority over ' 'allow-warnings-in-packages'), - DartdocOptionArgOnly>( + DartdocOptionArgOnly?>( 'ignoreErrorsInPackages', null, resourceProvider, splitCommas: true, help: 'Package names to ignore errors for. Takes priority over ' @@ -61,40 +62,24 @@ Future>> createPackageWarningOptions( // Options for globally enabling/disabling warnings and errors across // packages. Loaded from dartdoc_options.yaml, but command line arguments // will override. - DartdocOptionArgFile>('errors', null, resourceProvider, + DartdocOptionArgFile?>('errors', null, resourceProvider, splitCommas: true, help: 'Additional warning names to force as errors. Specify an empty ' - 'list to force defaults (overriding dartdoc_options.yaml)\nDefaults:\n' + - (packageWarningDefinitions.values - .where( - (d) => d.defaultWarningMode == PackageWarningMode.error) - .toList() - ..sort()) - .map((d) => ' ${d.warningName}: ${d.shortHelp}') - .join('\n')), - DartdocOptionArgFile>('ignore', null, resourceProvider, + 'list to force defaults (overriding ' + 'dartdoc_options.yaml)\nDefaults:\n' + + _warningsListHelpText(PackageWarningMode.error)), + DartdocOptionArgFile?>('ignore', null, resourceProvider, splitCommas: true, help: 'Additional warning names to ignore. Specify an empty list to ' - 'force defaults (overriding dartdoc_options.yaml).\nDefaults:\n' + - (packageWarningDefinitions.values - .where((d) => - d.defaultWarningMode == PackageWarningMode.ignore) - .toList() - ..sort()) - .map((d) => ' ${d.warningName}: ${d.shortHelp}') - .join('\n')), - DartdocOptionArgFile>('warnings', null, resourceProvider, + 'force defaults (overriding ' + 'dartdoc_options.yaml).\nDefaults:\n' + + _warningsListHelpText(PackageWarningMode.ignore)), + DartdocOptionArgFile?>('warnings', null, resourceProvider, splitCommas: true, help: 'Additional warning names to show as warnings (instead of error or ' 'ignore, if not warning by default).\nDefaults:\n' + - (packageWarningDefinitions.values - .where((d) => - d.defaultWarningMode == PackageWarningMode.warn) - .toList() - ..sort()) - .map((d) => ' ${d.warningName}: ${d.shortHelp}') - .join('\n')), + _warningsListHelpText(PackageWarningMode.warn)), // Synthetic option uses a factory to build a PackageWarningOptions from all the above flags. DartdocOptionSyntheticOnly( 'packageWarningOptions', @@ -105,6 +90,15 @@ Future>> createPackageWarningOptions( ]; } +String _warningsListHelpText(PackageWarningMode mode) { + return (packageWarningDefinitions.values + .where((d) => d.defaultWarningMode == mode) + .toList() + ..sort()) + .map((d) => ' ${d.warningName}: ${d.shortHelp}') + .join('\n'); +} + class PackageWarningDefinition implements Comparable { final String warningName; final String shortHelp; @@ -112,10 +106,13 @@ class PackageWarningDefinition implements Comparable { final PackageWarning kind; final PackageWarningMode defaultWarningMode; - const PackageWarningDefinition(this.kind, this.warningName, this.shortHelp, - {List longHelp, PackageWarningMode defaultWarningMode}) - : longHelp = longHelp ?? const [], - defaultWarningMode = defaultWarningMode ?? PackageWarningMode.warn; + const PackageWarningDefinition( + this.kind, + this.warningName, + this.shortHelp, { + this.longHelp = const [], + this.defaultWarningMode = PackageWarningMode.warn, + }); @override int compareTo(PackageWarningDefinition other) { @@ -140,14 +137,16 @@ const Map packageWarningDefinitions = PackageWarning.ambiguousReexport: PackageWarningDefinition( PackageWarning.ambiguousReexport, 'ambiguous-reexport', - 'A symbol is exported from private to public in more than one library and dartdoc can not determine which one is canonical', + 'A symbol is exported from private to public in more than one library ' + 'and dartdoc can not determine which one is canonical', longHelp: [ - "Use {@canonicalFor @@name@@} in the desired library's documentation to resolve", - "the ambiguity and/or override dartdoc's decision, or structure your package ", - 'so the reexport is less ambiguous. The symbol will still be referenced in ', - 'all candidates -- this only controls the location where it will be written ', - 'and which library will be displayed in navigation for the relevant pages.', - 'The flag --ambiguous-reexport-scorer-min-confidence allows you to set the', + "Use {@canonicalFor $_namePlaceholder} in the desired library's", + "documentation to resolve the ambiguity and/or override dartdoc's", + 'decision, or structure your package so the reexport is less', + 'ambiguous. The symbol will still be referenced in all candidates --', + 'this only controls the location where it will be written and which', + 'library will be displayed in navigation for the relevant pages. The', + 'flag --ambiguous-reexport-scorer-min-confidence allows you to set the', 'threshold at which this warning will appear.' ]), PackageWarning.ignoredCanonicalFor: PackageWarningDefinition( @@ -176,10 +175,10 @@ const Map packageWarningDefinitions = 'no-documentable-libraries', 'The package is to be documented but has no Dart libraries to document', longHelp: [ - 'Dartdoc could not find any public libraries to document in @@name@@, ', - 'but documentation was requested. This might be expected for an ', - 'asset only package, in which case, disable this warning in your ', - 'dartdoc_options.yaml file.', + 'Dartdoc could not find any public libraries to document in', + '$_namePlaceholder, but documentation was requested. This might be', + 'expected for an asset only package, in which case, disable this', + 'warning in your dartdoc_options.yaml file.', ], ), PackageWarning.noLibraryLevelDocs: PackageWarningDefinition( @@ -243,14 +242,15 @@ const Map packageWarningDefinitions = PackageWarning.duplicateFile: PackageWarningDefinition( PackageWarning.duplicateFile, 'duplicate-file', - 'Dartdoc is trying to write to a duplicate filename based on the names of Dart symbols.', + 'Dartdoc is trying to write to a duplicate filename based on the names ' + 'of Dart symbols.', longHelp: [ 'Dartdoc generates a path and filename to write to for each symbol.', - '@@name@@ conflicts with another symbol in the generated path, and', - 'therefore can not be written out. Changing the name, library name, or', - 'class name (if appropriate) of one of the conflicting items can resolve', - "the conflict. Alternatively, use the @nodoc tag in one symbol's", - 'documentation comments to hide it.' + '$_namePlaceholder conflicts with another symbol in the generated', + 'path, and therefore can not be written out. Changing the name,', + 'library name, or class name (if appropriate) of one of the', + 'conflicting items can resolve the conflict. Alternatively, use the', + "@nodoc tag in one symbol's documentation comments to hide it." ], defaultWarningMode: PackageWarningMode.error), PackageWarning.missingConstantConstructor: PackageWarningDefinition( @@ -260,8 +260,8 @@ const Map packageWarningDefinitions = longHelp: [ 'To resolve a constant into its literal value, Dartdoc relies on the', "analyzer to resolve the constructor. The analyzer didn't provide", - 'the constructor for @@name@@, which is usually due to an error in the', - 'code. Use the analyzer to find missing imports.', + 'the constructor for $_namePlaceholder, which is usually due to an', + 'error in the code. Use the analyzer to find missing imports.', ], // Defaults to ignore as this doesn't impact the docs severely but is // useful for debugging package structure. @@ -289,10 +289,12 @@ mixin Warnable implements Canonicalization, CommentReferable { Package get package; - void warn(PackageWarning kind, - {String message, - Iterable referredFrom, - Iterable extendedDebug}) { + void warn( + PackageWarning kind, { + String? message, + Iterable referredFrom = const [], + Iterable extendedDebug = const [], + }) { packageGraph.warnOnElement(this, kind, message: message, referredFrom: referredFrom, @@ -354,19 +356,13 @@ class PackageWarningOptions { for (var definition in packageWarningDefinitions.values) { switch (definition.defaultWarningMode) { case PackageWarningMode.warn: - { - warn(definition.kind); - } + warn(definition.kind); break; case PackageWarningMode.error: - { - error(definition.kind); - } + error(definition.kind); break; case PackageWarningMode.ignore: - { - ignore(definition.kind); - } + ignore(definition.kind); break; } } @@ -379,42 +375,55 @@ class PackageWarningOptions { ) { // First, initialize defaults. var newOptions = PackageWarningOptions(); - var packageMeta = packageMetaProvider.fromDir(dir); - - // Interpret errors/warnings/ignore options. In the event of conflict, warning overrides error and - // ignore overrides warning. - for (String warningName in option.parent['errors'].valueAt(dir) ?? []) { - if (packageWarningsByName[warningName] != null) { - newOptions.error(packageWarningsByName[warningName].kind); + var packageMeta = packageMetaProvider.fromDir(dir)!; + + // Interpret errors/warnings/ignore options. In the event of conflict, + // warning overrides error and ignore overrides warning. + var errorsForDir = + option.parent.getAs?>('errors').valueAt(dir) ?? []; + for (var warningName in errorsForDir) { + var packageWarnings = packageWarningsByName[warningName]; + if (packageWarnings != null) { + newOptions.error(packageWarnings.kind); } } - for (String warningName in option.parent['warnings'].valueAt(dir) ?? []) { - if (packageWarningsByName[warningName] != null) { - newOptions.warn(packageWarningsByName[warningName].kind); + var warningsForDir = + option.parent.getAs?>('warnings').valueAt(dir) ?? []; + for (var warningName in warningsForDir) { + var packageWarnings = packageWarningsByName[warningName]; + if (packageWarnings != null) { + newOptions.warn(packageWarnings.kind); } } - for (String warningName in option.parent['ignore'].valueAt(dir) ?? []) { - if (packageWarningsByName[warningName] != null) { - newOptions.ignore(packageWarningsByName[warningName].kind); + var ignoredForDir = + option.parent.getAs?>('ignore').valueAt(dir) ?? []; + for (var warningName in ignoredForDir) { + var packageWarnings = packageWarningsByName[warningName]; + if (packageWarnings != null) { + newOptions.ignore(packageWarnings.kind); } } // Check whether warnings are allowed at all in this package. - List allowWarningsInPackages = - option.parent['allowWarningsInPackages'].valueAt(dir); - List allowErrorsInPackages = - option.parent['allowErrorsInPackages'].valueAt(dir); - List ignoreWarningsInPackages = - option.parent['ignoreWarningsInPackages'].valueAt(dir); - List ignoreErrorsInPackages = - option.parent['ignoreErrorsInPackages'].valueAt(dir); + var allowWarningsInPackages = option.parent + .getAs?>('allowWarningsInPackages') + .valueAt(dir); + var allowErrorsInPackages = option.parent + .getAs?>('allowErrorsInPackages') + .valueAt(dir); + var ignoreWarningsInPackages = option.parent + .getAs?>('ignoreWarningsInPackages') + .valueAt(dir); + var ignoreErrorsInPackages = option.parent + .getAs?>('ignoreErrorsInPackages') + .valueAt(dir); if (allowWarningsInPackages != null && !allowWarningsInPackages.contains(packageMeta.name)) { PackageWarning.values .forEach((PackageWarning kind) => newOptions.ignore(kind)); } if (allowErrorsInPackages != null && - !allowWarningsInPackages.contains(packageMeta.name)) { + !allowErrorsInPackages.contains(packageMeta.name)) { PackageWarning.values .forEach((PackageWarning kind) => newOptions.ignore(kind)); } @@ -440,7 +449,7 @@ class PackageWarningOptions { void error(PackageWarning kind) => warningModes[kind] = PackageWarningMode.error; - PackageWarningMode getMode(PackageWarning kind) => warningModes[kind]; + PackageWarningMode? getMode(PackageWarning kind) => warningModes[kind]; } class PackageWarningCounter { @@ -466,13 +475,15 @@ class PackageWarningCounter { PackageWarningCounter(this.packageGraph); - /// Actually write out the warning. Assumes it is already counted with add. - void _writeWarning(PackageWarning kind, PackageWarningMode mode, + /// Actually write out the warning. + /// + /// Assumes it is already counted with [addWarning]. + void _writeWarning(PackageWarning kind, PackageWarningMode? mode, bool verboseWarnings, String name, String fullMessage) { if (mode == PackageWarningMode.ignore) { return; } - String type; + String? type; if (mode == PackageWarningMode.error) { type = 'error'; } else if (mode == PackageWarningMode.warn) { @@ -480,17 +491,16 @@ class PackageWarningCounter { } if (type != null) { var entry = ' $type: $fullMessage'; - _displayedWarningCounts.putIfAbsent(kind, () => 0); - _displayedWarningCounts[kind] += 1; - if (_displayedWarningCounts[kind] == 1 && + var displayedWarningCount = _displayedWarningCounts.increment(kind); + var packageWarningDefinition = packageWarningDefinitions[kind]!; + if (displayedWarningCount == 1 && verboseWarnings && - packageWarningDefinitions[kind].longHelp.isNotEmpty) { + packageWarningDefinition.longHelp.isNotEmpty) { // First time we've seen this warning. Give a little extra info. final separator = '\n '; - final nameSub = r'@@name@@'; var verboseOut = - '$separator${packageWarningDefinitions[kind].longHelp.join(separator)}' - .replaceAll(nameSub, name); + '$separator${packageWarningDefinition.longHelp.join(separator)}' + .replaceAll(_namePlaceholder, name); entry = '$entry$verboseOut'; } assert(entry == entry.trimRight()); @@ -507,8 +517,11 @@ class PackageWarningCounter { /// Returns `true` if we've already warned for this /// combination of [element], [kind], and [message]. - bool hasWarning(Warnable element, PackageWarning kind, String message) { - final warning = _countedWarnings[element?.element]; + bool hasWarning(Warnable? element, PackageWarning kind, String message) { + if (element == null) { + return false; + } + final warning = _countedWarnings[element.element]; if (warning != null) { final messages = warning[kind]; return messages != null && messages.contains(message); @@ -518,27 +531,32 @@ class PackageWarningCounter { /// Adds the warning to the counter, and writes out the fullMessage string /// if configured to do so. - void addWarning(Warnable element, PackageWarning kind, String message, + void addWarning(Warnable? element, PackageWarning kind, String message, String fullMessage) { assert(!hasWarning(element, kind, message)); // TODO(jcollins-g): Make addWarning not accept nulls for element. PackageWarningOptionContext config = element?.config ?? packageGraph.defaultPackage.config; - var warningMode = config.packageWarningOptions.getMode(kind); - if (!config.allowNonLocalWarnings && !(element?.package?.isLocal ?? true)) { + PackageWarningMode? warningMode; + var isLocal = element?.package.isLocal ?? true; + if (!config.allowNonLocalWarnings && !isLocal) { warningMode = PackageWarningMode.ignore; + } else { + warningMode = config.packageWarningOptions.getMode(kind); } if (warningMode == PackageWarningMode.warn) { _warningCount += 1; } else if (warningMode == PackageWarningMode.error) { _errorCount += 1; } - _countedWarnings - .putIfAbsent(element?.element, () => {}) - .putIfAbsent(kind, () => {}) - .add(message); - _writeWarning(kind, warningMode, config.verboseWarnings, - element?.fullyQualifiedName, fullMessage); + if (element != null) { + _countedWarnings + .putIfAbsent(element.element, () => {}) + .putIfAbsent(kind, () => {}) + .add(message); + _writeWarning(kind, warningMode, config.verboseWarnings, + element.fullyQualifiedName, fullMessage); + } } @override @@ -563,8 +581,20 @@ class _JsonWarning extends Jsonable { @override Map toJson() => { 'type': type, - 'kind': packageWarningDefinitions[kind].warningName, + 'kind': packageWarningDefinitions[kind]!.warningName, 'message': message, 'text': text }; } + +extension on Map { + int increment(PackageWarning kind) { + if (this[kind] == null) { + this[kind] = 1; + return 1; + } else { + this[kind] = this[kind]! + 1; + return this[kind]!; + } + } +} From ec523925d36ecc96396a6cc7b2c80483a504971c Mon Sep 17 00:00:00 2001 From: Sam Rawlins Date: Tue, 21 Sep 2021 20:05:47 -0700 Subject: [PATCH 10/47] Migrate mustachio to null safety (#2801) --- lib/src/mustachio/annotations.dart | 8 +- lib/src/mustachio/parser.dart | 37 ++++---- lib/src/mustachio/renderer_base.dart | 87 +++++++++--------- tool/mustachio/builder.dart | 41 ++++----- tool/mustachio/codegen_aot_compiler.dart | 43 ++++----- tool/mustachio/codegen_runtime_renderer.dart | 93 +++++++++----------- tool/mustachio/utilities.dart | 2 - 7 files changed, 145 insertions(+), 166 deletions(-) diff --git a/lib/src/mustachio/annotations.dart b/lib/src/mustachio/annotations.dart index e7854432ec..a0c57e8689 100644 --- a/lib/src/mustachio/annotations.dart +++ b/lib/src/mustachio/annotations.dart @@ -2,8 +2,6 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. -// @dart=2.9 - // See the Mustachio README at tool/mustachio/README.md for high-level // documentation. @@ -95,7 +93,7 @@ class RendererSpec { final String standardMdTemplate; - final Map standardTemplateUris; + final Map standardTemplateUris; RendererSpec( this.name, @@ -111,8 +109,8 @@ class RendererSpec { /// Parses a URI from a String which comes from a const annotation object. /// /// The String value may be the literal value, 'null'. - static Uri _parseUriFromAnnotation(String unparsed) => - unparsed == 'null' || unparsed == null ? null : Uri.parse(unparsed); + static Uri? _parseUriFromAnnotation(String unparsed) => + unparsed == 'null' ? null : Uri.parse(unparsed); ClassElement get contextElement => contextType.element; } diff --git a/lib/src/mustachio/parser.dart b/lib/src/mustachio/parser.dart index a33e3c10f7..fbd4136ef5 100644 --- a/lib/src/mustachio/parser.dart +++ b/lib/src/mustachio/parser.dart @@ -2,8 +2,6 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. -// @dart=2.9 - // See the Mustachio README at tool/mustachio/README.md for high-level // documentation. @@ -50,7 +48,7 @@ class MustachioParser { /// [sectionKey], the end tag is treated as plain text, not a tag. /// * if [sectionKey] is null, the end tag is treated as plain text, not a /// tag. - List _parseBlock({String /*?*/ sectionKey}) { + List _parseBlock({String? sectionKey}) { var children = []; var textStartIndex = _index; var textEndIndex = _index; @@ -128,7 +126,7 @@ class MustachioParser { trimTextRight(); } addTextNode(textStartIndex, textEndIndex); - children.add(result.node); + children.add(result.node!); textStartIndex = _index; continue; } @@ -193,7 +191,7 @@ class MustachioParser { /// /// [_index] should be at the character immediately following the `>` /// character which opens a possible partial tag. - _TagParseResult _parsePartial({@required int tagStartIndex}) { + _TagParseResult _parsePartial({required int tagStartIndex}) { var startIndex = _index; int endIndex; while (true) { @@ -229,7 +227,7 @@ class MustachioParser { /// [_index] should be at the character immediately following the `#` /// character which opens a possible section tag. _TagParseResult _parseSection( - {@required bool invert, @required int tagStartIndex}) { + {required bool invert, required int tagStartIndex}) { var parsedKey = _parseKey(); if (parsedKey.type == _KeyParseResultType.notKey) { return _TagParseResult.notTag; @@ -239,6 +237,7 @@ class MustachioParser { var children = _parseBlock(sectionKey: parsedKey.joinedNames); var span = _sourceFile.span(tagStartIndex, _index); + var parsedKeySpan = parsedKey.span!; if (parsedKey.names.length > 1) { // Desugar section with dots into nested sections. @@ -252,7 +251,7 @@ class MustachioParser { // [three] section is the singular child node of the [two] section, and // the [two] section is the singular child of the [one] section. var lastName = parsedKey.names.last; - var keySpanEndOffset = parsedKey.span.end.offset; + var keySpanEndOffset = parsedKeySpan.end.offset; var lastNameSpan = _sourceFile.span( keySpanEndOffset - lastName.length, keySpanEndOffset); var section = Section([lastName], children, @@ -262,7 +261,7 @@ class MustachioParser { // To find the start offset of the ith name, take the length of all of // the names 0 through `i - 1` re-joined with '.', and a final '.' at // the end. - var sectionKeyStartOffset = parsedKey.span.start.offset + + var sectionKeyStartOffset = parsedKeySpan.start.offset + (i == 0 ? 0 : parsedKey.names.take(i).join('.').length + 1); var keySpan = _sourceFile.span( sectionKeyStartOffset, sectionKeyStartOffset + sectionKey.length); @@ -273,7 +272,7 @@ class MustachioParser { } return _TagParseResult.ok(Section(parsedKey.names, children, - invert: invert, span: span, keySpan: parsedKey.span)); + invert: invert, span: span, keySpan: parsedKeySpan)); } /// Tries to parse an end tag at [_index]. @@ -295,7 +294,7 @@ class MustachioParser { /// /// [_index] should be at the character immediately following the `{{` /// characters which open a possible variable tag. - _TagParseResult _parseVariable({@required int tagStartIndex}) { + _TagParseResult _parseVariable({required int tagStartIndex}) { var escape = true; if (_thisChar == $lbrace) { escape = false; @@ -311,7 +310,7 @@ class MustachioParser { var span = _sourceFile.span(tagStartIndex, _index); return _TagParseResult.ok(Variable(parsedKey.names, - escape: escape, span: span, keySpan: parsedKey.span)); + escape: escape, span: span, keySpan: parsedKey.span!)); } /// Tries to parse a key at [_index]. @@ -436,7 +435,7 @@ class Text implements MustachioNode { @override final SourceSpan span; - Text(this.content, {@required this.span}); + Text(this.content, {required this.span}); @override String toString() => 'Text["$content"]'; @@ -457,7 +456,7 @@ class Variable with HasMultiNamedKey implements MustachioNode { final SourceSpan keySpan; Variable(this.key, - {@required this.escape, @required this.span, @required this.keySpan}); + {required this.escape, required this.span, required this.keySpan}); @override String toString() => 'Variable[$key, escape=$escape]'; @@ -481,7 +480,7 @@ class Section with HasMultiNamedKey implements MustachioNode { final SourceSpan keySpan; Section(this.key, this.children, - {@required this.invert, @required this.span, @required this.keySpan}); + {required this.invert, required this.span, required this.keySpan}); @override String toString() => 'Section[$key, invert=$invert]'; @@ -497,7 +496,7 @@ class Partial implements MustachioNode { final SourceSpan keySpan; - Partial(this.key, {@required this.span, @required this.keySpan}); + Partial(this.key, {required this.span, required this.keySpan}); } /// An enumeration of types of tag parse results. @@ -519,10 +518,10 @@ class _TagParseResult { /// This field is `null` if EOF was reached, or if a tag was not parsed /// (perhaps it started out like a tag, but was malformed, and so is read as /// text). - final MustachioNode /*?*/ node; + final MustachioNode? node; /// The key of an end tag, if an end tag was parsed. - final String /*?*/ endTagKey; + final String? endTagKey; _TagParseResult(this.type, this.node, this.endTagKey); @@ -564,12 +563,12 @@ class _KeyParseResult { /// The source span from where this key was parsed, if this represents a /// parsed key, othwerwise `null`. - final SourceSpan /*?*/ span; + final SourceSpan? span; const _KeyParseResult._(this.type, this.names, {this.span}); factory _KeyParseResult(_KeyParseResultType type, String key, - {@required SourceSpan span}) { + {required SourceSpan span}) { if (key == '.') { return _KeyParseResult._(type, [key], span: span); } else { diff --git a/lib/src/mustachio/renderer_base.dart b/lib/src/mustachio/renderer_base.dart index 072594a264..77d1db8f69 100644 --- a/lib/src/mustachio/renderer_base.dart +++ b/lib/src/mustachio/renderer_base.dart @@ -2,8 +2,6 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. -// @dart=2.9 - // See the Mustachio README at tool/mustachio/README.md for high-level // documentation. @@ -48,9 +46,9 @@ class Template { final Map partialTemplates; Template._( - {@required this.ast, - @required this.partials, - @required this.partialTemplates}); + {required this.ast, + required this.partials, + required this.partialTemplates}); /// Parses [file] as a Mustache template, returning a [Template]. /// @@ -69,8 +67,8 @@ class Template { /// the directory containing `p1.html`, not relative to the top-level /// template), as `/foo/partials/p2.html`. static Future