Merge package:json_rpc_2 into the tools monorepo
diff --git a/.github/ISSUE_TEMPLATE/boolean_selector.md b/.github/ISSUE_TEMPLATE/boolean_selector.md
new file mode 100644
index 0000000..5686d2a
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/boolean_selector.md
@@ -0,0 +1,5 @@
+---
+name: "package:boolean_selector"
+about: "Create a bug or file a feature request against package:boolean_selector."
+labels: "package:boolean_selector"
+---
\ No newline at end of file
diff --git a/.github/ISSUE_TEMPLATE/cli_config.md b/.github/ISSUE_TEMPLATE/cli_config.md
new file mode 100644
index 0000000..c47fbcf
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/cli_config.md
@@ -0,0 +1,5 @@
+---
+name: "package:cli_config"
+about: "Create a bug or file a feature request against package:cli_config."
+labels: "package:cli_config"
+---
diff --git a/.github/ISSUE_TEMPLATE/coverage.md b/.github/ISSUE_TEMPLATE/coverage.md
new file mode 100644
index 0000000..d0b0fb7
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/coverage.md
@@ -0,0 +1,5 @@
+---
+name: "package:coverage"
+about: "Create a bug or file a feature request against package:coverage."
+labels: "package:coverage"
+---
diff --git a/.github/ISSUE_TEMPLATE/extension_discovery.md b/.github/ISSUE_TEMPLATE/extension_discovery.md
new file mode 100644
index 0000000..165b7cb
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/extension_discovery.md
@@ -0,0 +1,5 @@
+---
+name: "package:extension_discovery"
+about: "Create a bug or file a feature request against package:extension_discovery."
+labels: "package:extension_discovery"
+---
diff --git a/.github/ISSUE_TEMPLATE/file.md b/.github/ISSUE_TEMPLATE/file.md
new file mode 100644
index 0000000..3430d7e
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/file.md
@@ -0,0 +1,5 @@
+---
+name: "package:file"
+about: "Create a bug or file a feature request against package:file."
+labels: "package:file"
+---
diff --git a/.github/ISSUE_TEMPLATE/graphs.md b/.github/ISSUE_TEMPLATE/graphs.md
new file mode 100644
index 0000000..b4cb60f
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/graphs.md
@@ -0,0 +1,5 @@
+---
+name: "package:graphs"
+about: "Create a bug or file a feature request against package:graphs."
+labels: "package:graphs"
+---
diff --git a/.github/ISSUE_TEMPLATE/unified_analytics.md b/.github/ISSUE_TEMPLATE/unified_analytics.md
new file mode 100644
index 0000000..163951e
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/unified_analytics.md
@@ -0,0 +1,5 @@
+---
+name: "package:unified_analytics - bug or enhancement"
+about: "Create a bug or file a feature request against package:unified_analytics."
+labels: "package:unified_analytics"
+---
diff --git a/.github/ISSUE_TEMPLATE/unified_analytics_event.yml b/.github/ISSUE_TEMPLATE/unified_analytics_event.yml
new file mode 100644
index 0000000..52c8d83
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/unified_analytics_event.yml
@@ -0,0 +1,47 @@
+name: "package:unified_analytics - request a new event"
+description: "Create a request for collecting a new event or new event data."
+labels: "package:unified_analytics"
+body:
+  - type: markdown
+    attributes:
+      value: |
+        An event is an action that a user, or the tool, performs. 
+        You can see the events that are being collected [here](../../pkgs/unified_analytics/lib/src/enums.dart)
+        and the data associated with those events [here](../../pkgs/unified_analytics/lib/src/event.dart).
+  - type: checkboxes
+    attributes:
+      label: Has this already been approved in the privacy design documentation?
+      options:
+        - label: This field is already covered in the PDD 
+      description: |
+        You can request that a new event be added to the package 
+        regardless of whether it's included in the privacy design documentation. 
+        However, the privacy team will need to approve before it is added.
+            
+  - type: textarea
+    attributes:
+      label: Event name
+      description: |
+        If the event already exists, please tell us the name of the event 
+        you would like to add data to.
+
+        If this is a new event, tell us the name, description, and tool owner. 
+        Possible tool owners can be found in the `DashTool` enum [here](../../pkgs/unified_analytics/lib/src/enums.dart).
+
+        For example, pub_get represents pub package resolution details. The owner is the Dart tool.
+    validations:
+      required: true
+
+  - type: textarea
+    attributes:
+      label: Event data
+      description: |
+        Event data are key-value pairs that are associated with an event.
+        Please list the different event data associated with this event. 
+        You should also include a description of the event data values.
+
+        For example, if the event is pub_get, one event data may be 
+        the packageName. The values would be the name of the package 
+        as a string.
+    validations:
+      required: true
diff --git a/.github/ISSUE_TEMPLATE/unified_analytics_user_property.yml b/.github/ISSUE_TEMPLATE/unified_analytics_user_property.yml
new file mode 100644
index 0000000..3fc960e
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/unified_analytics_user_property.yml
@@ -0,0 +1,37 @@
+name: "package:unified_analytics - request a new user property"
+description: "Create a request for collecting a new user property."
+labels: "package:unified_analytics"
+body:
+  - type: markdown
+    attributes:
+      value: |
+        A user property is a key-value pair that is used to segment users. 
+        For example, the Flutter channel that the user is on. You can see 
+        which user properties are being collected 
+        [here](../../pkgs/unified_analytics/lib/src/user_property.dart).
+
+  - type: checkboxes
+    attributes:
+      label: Has this already been approved in the privacy design documentation?
+      options:
+        - label: This field is already covered in the PDD 
+      description: |
+        You can request that a new user property be added to the package 
+        regardless of whether it's included in the privacy design documentation. 
+        However, the privacy team will need to approve before it is added.
+          
+  - type: textarea
+    attributes:
+      label: User property name
+      description: |
+        Please tell us the name of the user property you would like to add (e.g. flutter_channel).
+    validations:
+      required: true
+
+  - type: textarea
+    attributes:
+      label: User property values
+      description: |
+        Please list or describe the unique values for this property (e.g. master, beta, stable).
+    validations:
+      required: true
diff --git a/.github/dependabot.yaml b/.github/dependabot.yaml
new file mode 100644
index 0000000..bf6b38a
--- /dev/null
+++ b/.github/dependabot.yaml
@@ -0,0 +1,14 @@
+# Dependabot configuration file.
+version: 2
+
+updates:
+  - package-ecosystem: github-actions
+    directory: /
+    schedule:
+      interval: monthly
+    labels:
+      - autosubmit
+    groups:
+      github-actions:
+        patterns:
+          - "*"
diff --git a/.github/labeler.yml b/.github/labeler.yml
new file mode 100644
index 0000000..c3d5de0
--- /dev/null
+++ b/.github/labeler.yml
@@ -0,0 +1,49 @@
+# Configuration for .github/workflows/pull_request_label.yml.
+
+'type-infra':
+  - changed-files:
+      - any-glob-to-any-file: '.github/**'
+
+'package:boolean_selector':
+  - changed-files:
+      - any-glob-to-any-file: 'pkgs/boolean_selector/**'
+
+'package:cli_config':
+  - changed-files:
+      - any-glob-to-any-file: 'pkgs/cli_config/**'
+
+'package:coverage':
+  - changed-files:
+      - any-glob-to-any-file: 'pkgs/coverage/**'
+
+'package:extension_discovery':
+  - changed-files:
+      - any-glob-to-any-file: 'pkgs/extension_discovery/**'
+
+'package:file':
+  - changed-files:
+      - any-glob-to-any-file: 'pkgs/file/**'
+
+'package:file_testing':
+  - changed-files:
+      - any-glob-to-any-file: 'pkgs/file_testing/**'
+
+'package:graphs':
+  - changed-files:
+      - any-glob-to-any-file: 'pkgs/graphs/**'
+
+'package:mime':
+  - changed-files:
+      - any-glob-to-any-file: 'pkgs/mime/**'
+
+'package:oauth2':
+  - changed-files:
+      - any-glob-to-any-file: 'pkgs/oauth2/**'
+
+'package:source_map_stack_trace':
+  - changed-files:
+      - any-glob-to-any-file: 'pkgs/source_map_stack_trace/**'
+
+'package:unified_analytics':
+  - changed-files:
+      - any-glob-to-any-file: 'pkgs/unified_analytics/**'
diff --git a/.github/workflows/boolean_selector.yaml b/.github/workflows/boolean_selector.yaml
new file mode 100644
index 0000000..9d90c41
--- /dev/null
+++ b/.github/workflows/boolean_selector.yaml
@@ -0,0 +1,72 @@
+name: package:boolean_selector
+
+on:
+  # Run on PRs and pushes to the default branch.
+  push:
+    branches: [ main ]
+    paths:
+      - '.github/workflows/boolean_selector.yml'
+      - 'pkgs/boolean_selector/**'
+  pull_request:
+    branches: [ main ]
+    paths:
+      - '.github/workflows/boolean_selector.yml'
+      - 'pkgs/boolean_selector/**'
+  schedule:
+    - cron: "0 0 * * 0"
+
+env:
+  PUB_ENVIRONMENT: bot.github
+
+
+defaults:
+  run:
+    working-directory: pkgs/boolean_selector/
+
+jobs:
+  # Check code formatting and static analysis on a single OS (linux)
+  # against Dart dev.
+  analyze:
+    runs-on: ubuntu-latest
+    strategy:
+      fail-fast: false
+      matrix:
+        sdk: [dev]
+    steps:
+      - uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938
+      - uses: dart-lang/setup-dart@0a8a0fc875eb934c15d08629302413c671d3f672
+        with:
+          sdk: ${{ matrix.sdk }}
+      - id: install
+        name: Install dependencies
+        run: dart pub get
+      - name: Check formatting
+        run: dart format --output=none --set-exit-if-changed .
+        if: always() && steps.install.outcome == 'success'
+      - name: Analyze code
+        run: dart analyze --fatal-infos
+        if: always() && steps.install.outcome == 'success'
+
+  test:
+    needs: analyze
+    runs-on: ${{ matrix.os }}
+    strategy:
+      fail-fast: false
+      matrix:
+        # Add macos-latest and/or windows-latest if relevant for this package.
+        os: [ubuntu-latest]
+        sdk: [3.1, dev]
+    steps:
+      - uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938
+      - uses: dart-lang/setup-dart@0a8a0fc875eb934c15d08629302413c671d3f672
+        with:
+          sdk: ${{ matrix.sdk }}
+      - id: install
+        name: Install dependencies
+        run: dart pub get
+      - name: Run VM tests
+        run: dart test --platform vm
+        if: always() && steps.install.outcome == 'success'
+      - name: Run Chrome tests
+        run: dart test --platform chrome
+        if: always() && steps.install.outcome == 'success'
diff --git a/.github/workflows/cli_config.yml b/.github/workflows/cli_config.yml
new file mode 100644
index 0000000..78eed42
--- /dev/null
+++ b/.github/workflows/cli_config.yml
@@ -0,0 +1,80 @@
+name: package:cli_config
+permissions: read-all
+
+on:
+  pull_request:
+    branches: [main]
+    paths:
+      - ".github/workflows/cli_config.yml"
+      - "pkgs/cli_config/**"
+  push:
+    branches: [main]
+    paths:
+      - ".github/workflows/cli_config.yml"
+      - "pkgs/cli_config/**"
+  schedule:
+    - cron: "0 0 * * 0" # weekly
+
+jobs:
+  build_linux:
+    runs-on: ubuntu-latest
+    defaults:
+      run:
+        working-directory: pkgs/cli_config
+    strategy:
+      matrix:
+        sdk: [stable, dev] # {pkgs.versions}
+        include:
+          - sdk: stable
+            run-tests: true
+    steps:
+      - uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938
+      - uses: dart-lang/setup-dart@0a8a0fc875eb934c15d08629302413c671d3f672
+        with:
+          sdk: ${{matrix.sdk}}
+
+      - run: dart pub get
+
+      - run: dart analyze --fatal-infos
+
+      - run: dart format --output=none --set-exit-if-changed .
+        if: ${{matrix.run-tests}}
+
+      - run: dart test
+        if: ${{matrix.run-tests}}
+
+      - name: Install coverage
+        run: dart pub global activate coverage
+        if: ${{ matrix.sdk == 'stable' }}
+      - name: Collect coverage
+        run: dart pub global run coverage:test_with_coverage
+        if: ${{ matrix.sdk == 'stable' }}
+      - name: Upload coverage
+        uses: coverallsapp/github-action@643bc377ffa44ace6394b2b5d0d3950076de9f63
+        with:
+          github-token: ${{ secrets.GITHUB_TOKEN }}
+          flag-name: cli_config_linux
+          path-to-lcov: ./pkgs/cli_config/coverage/lcov.info
+        if: ${{ matrix.sdk == 'stable' }}
+
+  build_windows:
+    runs-on: windows-latest
+    defaults:
+      run:
+        working-directory: pkgs/cli_config
+    strategy:
+      matrix:
+        sdk: [stable, dev] # {pkgs.versions}
+        include:
+          - sdk: stable
+            run-tests: true
+    steps:
+      - uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938
+      - uses: dart-lang/setup-dart@0a8a0fc875eb934c15d08629302413c671d3f672
+        with:
+          sdk: ${{matrix.sdk}}
+
+      - run: dart pub get
+
+      - run: dart test
+        if: ${{matrix.run-tests}}
diff --git a/.github/workflows/coverage.yml b/.github/workflows/coverage.yml
new file mode 100644
index 0000000..a66a53c
--- /dev/null
+++ b/.github/workflows/coverage.yml
@@ -0,0 +1,99 @@
+name: Dart CI
+
+on:
+  # Run on PRs and pushes to the default branch.
+  push:
+    branches: [ main ]
+    paths:
+      - '.github/workflows/coverage.yml'
+      - 'pkgs/coverage/**'
+  pull_request:
+    branches: [ main ]
+    paths:
+      - '.github/workflows/coverage.yml'
+      - 'pkgs/coverage/**'
+  schedule:
+    - cron: "0 0 * * 0"
+
+env:
+  PUB_ENVIRONMENT: bot.github
+
+jobs:
+  # Check code formatting and static analysis on a single OS (linux)
+  # against Dart dev.
+  analyze:
+    runs-on: ubuntu-latest
+    defaults:
+      run:
+        working-directory: pkgs/coverage/
+    strategy:
+      fail-fast: false
+      matrix:
+        sdk: [dev]
+    steps:
+      - uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938
+      - uses: dart-lang/setup-dart@0a8a0fc875eb934c15d08629302413c671d3f672
+        with:
+          sdk: ${{ matrix.sdk }}
+      - id: install
+        name: Install dependencies
+        run: dart pub get
+      - name: Check formatting
+        run: dart format --output=none --set-exit-if-changed .
+        if: always() && steps.install.outcome == 'success'
+      - name: Analyze code
+        run: dart analyze --fatal-infos
+        if: always() && steps.install.outcome == 'success'
+
+  # Run tests on a matrix consisting of two dimensions:
+  # 1. OS: ubuntu-latest, macos-latest, windows-latest
+  # 2. release channel: dev
+  test:
+    needs: analyze
+    runs-on: ${{ matrix.os }}
+    defaults:
+      run:
+        working-directory: pkgs/coverage/
+    strategy:
+      fail-fast: false
+      matrix:
+        os: [ubuntu-latest, macos-latest, windows-latest]
+        sdk: [3.4, dev]
+        exclude:
+          # VM service times out on windows before Dart 3.5
+          # https://github.com/dart-lang/coverage/issues/490
+          - os: windows-latest
+            sdk: 3.4
+    steps:
+      - uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938
+      - uses: dart-lang/setup-dart@0a8a0fc875eb934c15d08629302413c671d3f672
+        with:
+          sdk: ${{ matrix.sdk }}
+      - id: install
+        name: Install dependencies
+        run: dart pub get
+      - name: Run VM tests
+        run: dart test --platform vm
+        if: always() && steps.install.outcome == 'success'
+
+  coverage:
+    needs: test
+    runs-on: ubuntu-latest
+    defaults:
+      run:
+        working-directory: pkgs/coverage/
+    steps:
+      - uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938
+      - uses: dart-lang/setup-dart@0a8a0fc875eb934c15d08629302413c671d3f672
+        with:
+          sdk: dev
+      - id: install
+        name: Install dependencies
+        run: dart pub get
+      - name: Collect and report coverage
+        run: dart run bin/test_with_coverage.dart --port=9292
+      - name: Upload coverage
+        uses: coverallsapp/github-action@643bc377ffa44ace6394b2b5d0d3950076de9f63
+        with:
+          github-token: ${{ secrets.GITHUB_TOKEN }}
+          path-to-lcov: pkgs/coverage/coverage/lcov.info
diff --git a/.github/workflows/extension_discovery.yml b/.github/workflows/extension_discovery.yml
new file mode 100644
index 0000000..b92fddf
--- /dev/null
+++ b/.github/workflows/extension_discovery.yml
@@ -0,0 +1,48 @@
+name: package:extension_discovery
+permissions: read-all
+
+on:
+  pull_request:
+    branches: [ main ]
+    paths:
+      - '.github/workflows/unified_analytics.yml'
+      - 'pkgs/extension_discovery/**'
+  push:
+    branches: [ main ]
+    paths:
+      - '.github/workflows/extension_discovery.yml'
+      - 'pkgs/extension_discovery/**'
+  schedule:
+    - cron: '0 0 * * 0' # weekly
+
+jobs:
+  build:
+    runs-on: ubuntu-latest
+    defaults:
+      run:
+        working-directory: pkgs/extension_discovery
+    strategy:
+      fail-fast: false
+      matrix:
+        sdk: [stable, dev] # {pkgs.versions}
+        include:
+          - sdk: stable
+            check-formatting: true
+    steps:
+      - uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938
+      - uses: dart-lang/setup-dart@0a8a0fc875eb934c15d08629302413c671d3f672
+        with:
+          sdk: ${{matrix.sdk}}
+
+      - run: dart pub get
+      - run: |
+          (cd example/hello_world && dart pub get)
+          (cd example/hello_world_app && dart pub get)
+          (cd example/hello_world_german && dart pub get)
+
+      - run: dart analyze --fatal-infos
+
+      - run: dart format --output=none --set-exit-if-changed .
+        if: ${{matrix.check-formatting}}
+
+      - run: dart test
diff --git a/.github/workflows/file.yml b/.github/workflows/file.yml
new file mode 100644
index 0000000..06ce285
--- /dev/null
+++ b/.github/workflows/file.yml
@@ -0,0 +1,66 @@
+name: package:file
+permissions: read-all
+
+on:
+  # Run on PRs and pushes to the default branch.
+  push:
+    branches: [ main ]
+    paths:
+      - '.github/workflows/file.yml'
+      - 'pkgs/file/**'
+      - 'pkgs/file_testing/**'
+  pull_request:
+    branches: [ main ]
+    paths:
+      - '.github/workflows/file.yml'
+      - 'pkgs/file/**'
+      - 'pkgs/file_testing/**'
+  schedule:
+    - cron: "0 0 * * 0"
+
+jobs:
+  correctness:
+    runs-on: ubuntu-latest
+    strategy:
+      matrix:
+        package: [file, file_testing]
+
+    steps:
+      - uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938
+      - uses: dart-lang/setup-dart@0a8a0fc875eb934c15d08629302413c671d3f672
+        with:
+          sdk: dev
+
+      - name: Install ${{ matrix.package }} dependencies
+        working-directory: pkgs/${{ matrix.package }}
+        run: dart pub get
+
+      - name: Verify formatting in ${{ matrix.package }}
+        working-directory: pkgs/${{ matrix.package }}
+        run: dart format --output=none --set-exit-if-changed .
+
+      - name: Analyze package ${{ matrix.package }} source
+        working-directory: pkgs/${{ matrix.package }}
+        run: dart analyze --fatal-infos
+
+  test:
+    runs-on: ${{ matrix.os }}
+    strategy:
+      matrix:
+        package: [file]
+        os: [ubuntu-latest, macos-latest, windows-latest]
+        sdk: [stable, dev]
+
+    steps:
+      - uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938
+      - uses: dart-lang/setup-dart@0a8a0fc875eb934c15d08629302413c671d3f672
+        with:
+          sdk: ${{ matrix.sdk }}
+
+      - name: Install ${{ matrix.package }} dependencies
+        working-directory: pkgs/${{ matrix.package }}
+        run: dart pub get
+
+      - name: Run ${{ matrix.package }} Tests
+        working-directory: pkgs/${{ matrix.package }}
+        run: dart pub run test -j1
diff --git a/.github/workflows/graphs.yml b/.github/workflows/graphs.yml
new file mode 100644
index 0000000..8de9cf5
--- /dev/null
+++ b/.github/workflows/graphs.yml
@@ -0,0 +1,67 @@
+name: package:graphs
+permissions: read-all
+
+on:
+  # Run on PRs and pushes to the default branch.
+  push:
+    branches: [ main ]
+    paths:
+      - '.github/workflows/graphs.yml'
+      - 'pkgs/graphs/**'
+  pull_request:
+    branches: [ main ]
+    paths:
+      - '.github/workflows/graphs.yml'
+      - 'pkgs/graphs/**'
+  schedule:
+    - cron: "0 0 * * 0"
+
+env:
+  PUB_ENVIRONMENT: bot.github
+
+jobs:
+  # Check code formatting and static analysis on a single OS (linux)
+  # against Dart beta.
+  analyze:
+    runs-on: ubuntu-latest
+    defaults:
+      run:
+        working-directory: pkgs/graphs/
+    strategy:
+      fail-fast: false
+      matrix:
+        sdk: [dev]
+    steps:
+      - uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938
+      - uses: dart-lang/setup-dart@0a8a0fc875eb934c15d08629302413c671d3f672
+        with:
+          sdk: ${{ matrix.sdk }}
+      - id: install
+        run: dart pub get
+      - run: dart format --output=none --set-exit-if-changed .
+        if: always() && steps.install.outcome == 'success'
+      - run: dart analyze --fatal-infos
+        if: always() && steps.install.outcome == 'success'
+
+  test:
+    needs: analyze
+    runs-on: ${{ matrix.os }}
+    defaults:
+      run:
+        working-directory: pkgs/graphs/
+    strategy:
+      fail-fast: false
+      matrix:
+        os: [ubuntu-latest]
+        sdk: [3.4, dev]
+    steps:
+      - uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938
+      - uses: dart-lang/setup-dart@0a8a0fc875eb934c15d08629302413c671d3f672
+        with:
+          sdk: ${{ matrix.sdk }}
+      - id: install
+        run: dart pub get
+      - run: dart test --platform vm
+        if: always() && steps.install.outcome == 'success'
+      - run: dart test --platform chrome
+        if: always() && steps.install.outcome == 'success'
diff --git a/.github/workflows/health.yaml b/.github/workflows/health.yaml
new file mode 100644
index 0000000..f258f8b
--- /dev/null
+++ b/.github/workflows/health.yaml
@@ -0,0 +1,14 @@
+name: Health
+on:
+  pull_request:
+    branches: [ main ]
+    types: [opened, synchronize, reopened, labeled, unlabeled]
+
+jobs:
+  health:
+    uses: dart-lang/ecosystem/.github/workflows/health.yaml@main
+    with:
+      ignore_coverage: "**.mock.dart,**.g.dart"
+      ignore_license: "**.mock.dart,**.g.dart,**.mocks.dart"
+    permissions:
+      pull-requests: write
diff --git a/.github/workflows/mime.yml b/.github/workflows/mime.yml
new file mode 100644
index 0000000..fe07a21
--- /dev/null
+++ b/.github/workflows/mime.yml
@@ -0,0 +1,45 @@
+name: Dart CI
+
+on:
+  schedule:
+    # “At 00:00 (UTC) on Sunday.”
+    - cron: '0 0 * * 0'
+  push:
+    branches: [ main ]
+    paths:
+      - '.github/workflows/mime.yml'
+      - 'pkgs/mime/**'
+  pull_request:
+    branches: [ main ]
+    paths:
+      - '.github/workflows/mime.yml'
+      - 'pkgs/mime/**'
+
+jobs:
+  build:
+    runs-on: ubuntu-latest
+    defaults:
+      run:
+        working-directory: pkgs/mime/
+
+    strategy:
+      matrix:
+        os: [ubuntu-latest]
+        sdk: [3.2, dev]
+    steps:
+      # These are the latest versions of the github actions; dependabot will
+      # send PRs to keep these up-to-date.
+      - uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938
+      - uses: dart-lang/setup-dart@0a8a0fc875eb934c15d08629302413c671d3f672
+
+      - name: Install dependencies
+        run: dart pub get
+  
+      - name: Verify formatting
+        run: dart format --output=none --set-exit-if-changed .
+
+      - name: Analyze project source
+        run: dart analyze --fatal-infos
+
+      - name: Run tests
+        run: dart test
diff --git a/.github/workflows/no-response.yml b/.github/workflows/no-response.yml
new file mode 100644
index 0000000..ab1ac49
--- /dev/null
+++ b/.github/workflows/no-response.yml
@@ -0,0 +1,37 @@
+# A workflow to close issues where the author hasn't responded to a request for
+# more information; see https://github.com/actions/stale.
+
+name: No Response
+
+# Run as a daily cron.
+on:
+  schedule:
+    # Every day at 8am
+    - cron: '0 8 * * *'
+
+# All permissions not specified are set to 'none'.
+permissions:
+  issues: write
+  pull-requests: write
+
+jobs:
+  no-response:
+    runs-on: ubuntu-latest
+    if: ${{ github.repository_owner == 'dart-lang' }}
+    steps:
+      - uses: actions/stale@28ca1036281a5e5922ead5184a1bbf96e5fc984e
+        with:
+          # Don't automatically mark inactive issues+PRs as stale.
+          days-before-stale: -1
+          # Close needs-info issues and PRs after 14 days of inactivity.
+          days-before-close: 14
+          stale-issue-label: "needs-info"
+          close-issue-message: >
+            Without additional information we're not able to resolve this issue.
+            Feel free to add more info or respond to any questions above and we
+            can reopen the case. Thanks for your contribution!
+          stale-pr-label: "needs-info"
+          close-pr-message: >
+            Without additional information we're not able to resolve this PR.
+            Feel free to add more info or respond to any questions above.
+            Thanks for your contribution!
diff --git a/.github/workflows/oauth2.yml b/.github/workflows/oauth2.yml
new file mode 100644
index 0000000..fa5d2de
--- /dev/null
+++ b/.github/workflows/oauth2.yml
@@ -0,0 +1,79 @@
+name: Dart CI
+
+on:
+  # Run on PRs and pushes to the default branch.
+  push:
+    branches: [ main ]
+    paths:
+      - '.github/workflows/oauth2.yml'
+      - 'pkgs/oauth2/**'
+  pull_request:
+    branches: [ main ]
+    paths:
+      - '.github/workflows/oauth2.yml'
+      - 'pkgs/oauth2/**'
+  schedule:
+    - cron: "0 0 * * 0"
+
+env:
+  PUB_ENVIRONMENT: bot.github
+
+jobs:
+  # Check code formatting and lints against Dart dev, check analyzer warnings
+  # against the oldest supported SDK.
+  analyze:
+    runs-on: ubuntu-latest
+    defaults:
+      run:
+        working-directory: pkgs/oauth2/
+    strategy:
+      fail-fast: false
+      matrix:
+        sdk: [dev]
+    steps:
+      - uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938
+      - uses: dart-lang/setup-dart@0a8a0fc875eb934c15d08629302413c671d3f672
+        with:
+          sdk: ${{ matrix.sdk }}
+      - id: install
+        name: Install dependencies
+        run: dart pub get
+      - name: Check formatting
+        run: dart format --output=none --set-exit-if-changed .
+        if: matrix.sdk == 'dev' && steps.install.outcome == 'success'
+      - name: Analyze code
+        run: dart analyze --fatal-infos
+        if: matrix.sdk == 'dev' && steps.install.outcome == 'success'
+      - name: Analyze code
+        run: dart analyze
+        if: matrix.sdk != 'dev' && steps.install.outcome == 'success'
+
+  # Run tests on a matrix consisting of two dimensions:
+  # 1. OS: ubuntu-latest, (macos-latest, windows-latest)
+  # 2. release channel: dev
+  test:
+    needs: analyze
+    runs-on: ${{ matrix.os }}
+    defaults:
+      run:
+        working-directory: pkgs/oauth2/
+    strategy:
+      fail-fast: false
+      matrix:
+        # Add macos-latest and/or windows-latest if relevant for this package.
+        os: [ubuntu-latest]
+        sdk: [3.4, dev]
+    steps:
+      - uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938
+      - uses: dart-lang/setup-dart@0a8a0fc875eb934c15d08629302413c671d3f672
+        with:
+          sdk: ${{ matrix.sdk }}
+      - id: install
+        name: Install dependencies
+        run: dart pub get
+      - name: Run VM tests
+        run: dart test --platform vm
+        if: always() && steps.install.outcome == 'success'
+      - name: Run Chrome tests
+        run: dart test --platform chrome
+        if: always() && steps.install.outcome == 'success'
diff --git a/.github/workflows/post_summaries.yaml b/.github/workflows/post_summaries.yaml
new file mode 100644
index 0000000..f5c8be8
--- /dev/null
+++ b/.github/workflows/post_summaries.yaml
@@ -0,0 +1,17 @@
+name: Comment on the pull request
+
+on:
+  # Trigger this workflow after the Health workflow completes. This workflow will have permissions to
+  # do things like create comments on the PR, even if the original workflow couldn't.
+  workflow_run:
+    workflows: 
+      - Publish
+      - Health
+    types:
+      - completed
+
+jobs:
+  upload:
+    uses: dart-lang/ecosystem/.github/workflows/post_summaries.yaml@main
+    permissions:
+      pull-requests: write
diff --git a/.github/workflows/publish.yaml b/.github/workflows/publish.yaml
new file mode 100644
index 0000000..2ec45aa
--- /dev/null
+++ b/.github/workflows/publish.yaml
@@ -0,0 +1,16 @@
+# A CI configuration to auto-publish pub packages.
+
+name: Publish
+
+on:
+  pull_request:
+    branches: [ main ]
+  push:
+    tags: [ '[A-z]+-v[0-9]+.[0-9]+.[0-9]+' ]
+
+jobs:
+  publish:
+    if: ${{ github.repository_owner == 'dart-lang' }}
+    uses: dart-lang/ecosystem/.github/workflows/publish.yaml@main
+    with:
+      write-comments: false
diff --git a/.github/workflows/pull_request_label.yml b/.github/workflows/pull_request_label.yml
new file mode 100644
index 0000000..54e3df5
--- /dev/null
+++ b/.github/workflows/pull_request_label.yml
@@ -0,0 +1,22 @@
+# This workflow applies labels to pull requests based on the paths that are
+# modified in the pull request.
+#
+# Edit `.github/labeler.yml` to configure labels. For more information, see
+# https://github.com/actions/labeler.
+
+name: Pull Request Labeler
+permissions: read-all
+
+on:
+  pull_request_target
+
+jobs:
+  label:
+    permissions:
+      pull-requests: write
+    runs-on: ubuntu-latest
+    steps:
+      - uses: actions/labeler@8558fd74291d67161a8a78ce36a881fa63b766a9
+        with:
+          repo-token: "${{ secrets.GITHUB_TOKEN }}"
+          sync-labels: true
diff --git a/.github/workflows/source_map_stack_trace.yml b/.github/workflows/source_map_stack_trace.yml
new file mode 100644
index 0000000..9d3f0c7
--- /dev/null
+++ b/.github/workflows/source_map_stack_trace.yml
@@ -0,0 +1,76 @@
+name: Dart CI
+
+on:
+  # Run on PRs and pushes to the default branch.
+  push:
+    branches: [ main ]
+    paths:
+      - '.github/workflows/source_map_stack_trace.yml'
+      - 'pkgs/source_map_stack_trace/**'
+  pull_request:
+    branches: [ main ]
+    paths:
+      - '.github/workflows/source_map_stack_trace.yml'
+      - 'pkgs/source_map_stack_trace/**'
+  schedule:
+    - cron: "0 0 * * 0"
+
+env:
+  PUB_ENVIRONMENT: bot.github
+
+jobs:
+  # Check code formatting and static analysis on a single OS (linux)
+  # against Dart dev.
+  analyze:
+    runs-on: ubuntu-latest
+    defaults:
+      run:
+        working-directory: pkgs/source_map_stack_trace/
+    strategy:
+      fail-fast: false
+      matrix:
+        sdk: [dev]
+    steps:
+      - uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938
+      - uses: dart-lang/setup-dart@0a8a0fc875eb934c15d08629302413c671d3f672
+        with:
+          sdk: ${{ matrix.sdk }}
+      - id: install
+        name: Install dependencies
+        run: dart pub get
+      - name: Check formatting
+        run: dart format --output=none --set-exit-if-changed .
+        if: always() && steps.install.outcome == 'success'
+      - name: Analyze code
+        run: dart analyze --fatal-infos
+        if: always() && steps.install.outcome == 'success'
+
+  # Run tests on a matrix consisting of two dimensions:
+  # 1. OS: ubuntu-latest, (macos-latest, windows-latest)
+  # 2. release channel: dev
+  test:
+    needs: analyze
+    runs-on: ${{ matrix.os }}
+    defaults:
+      run:
+        working-directory: pkgs/source_map_stack_trace/
+    strategy:
+      fail-fast: false
+      matrix:
+        # Add macos-latest and/or windows-latest if relevant for this package.
+        os: [ubuntu-latest]
+        sdk: [3.3, dev]
+    steps:
+      - uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938
+      - uses: dart-lang/setup-dart@0a8a0fc875eb934c15d08629302413c671d3f672
+        with:
+          sdk: ${{ matrix.sdk }}
+      - id: install
+        name: Install dependencies
+        run: dart pub get
+      - name: Run VM tests
+        run: dart test --platform vm
+        if: always() && steps.install.outcome == 'success'
+      - name: Run Chrome tests
+        run: dart test --platform chrome
+        if: always() && steps.install.outcome == 'success'
diff --git a/.github/workflows/unified_analytics.yml b/.github/workflows/unified_analytics.yml
new file mode 100644
index 0000000..4b1c33e
--- /dev/null
+++ b/.github/workflows/unified_analytics.yml
@@ -0,0 +1,44 @@
+name: package:unified_analytics
+permissions: read-all
+
+on:
+  pull_request:
+    branches: [ main ]
+    paths:
+      - '.github/workflows/unified_analytics.yml'
+      - 'pkgs/unified_analytics/**'
+  push:
+    branches: [ main ]
+    paths:
+      - '.github/workflows/unified_analytics.yml'
+      - 'pkgs/unified_analytics/**'
+  schedule:
+    - cron: '0 0 * * 0' # weekly
+
+jobs:
+  build:
+    runs-on: ubuntu-latest
+    defaults:
+      run:
+        working-directory: pkgs/unified_analytics
+    strategy:
+      matrix:
+        sdk: [stable, dev] # {pkgs.versions}
+        include:
+          - sdk: stable
+            run-tests: true
+    steps:
+      - uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938
+      - uses: dart-lang/setup-dart@0a8a0fc875eb934c15d08629302413c671d3f672
+        with:
+          sdk: ${{matrix.sdk}}
+
+      - run: dart pub get
+
+      - run: dart analyze --fatal-infos
+
+      - run: dart format --output=none --set-exit-if-changed .
+        if: ${{matrix.run-tests}}
+
+      - run: dart test
+        if: ${{matrix.run-tests}}
diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..5509140
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1 @@
+*.DS_Store
diff --git a/CODEOWNERS b/CODEOWNERS
new file mode 100644
index 0000000..7694822
--- /dev/null
+++ b/CODEOWNERS
@@ -0,0 +1,5 @@
+# The CODEOWNERS file helps to define individuals or teams that responsible
+# for code within the repository
+# https://docs.github.com/en/repositories/managing-your-repositorys-settings-and-features/customizing-your-repository/about-code-owners
+
+/pkgs/unified_analytics/ @andrewkolos
diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
new file mode 100644
index 0000000..3c28563
--- /dev/null
+++ b/CONTRIBUTING.md
@@ -0,0 +1,51 @@
+# How to Contribute
+
+We'd love to accept your patches and contributions to this project. There are
+just a few small guidelines you need to follow.
+
+## Contributor License Agreement
+
+Contributions to this project must be accompanied by a Contributor License
+Agreement (CLA). You (or your employer) retain the copyright to your
+contribution; this simply gives us permission to use and redistribute your
+contributions as part of the project. Head over to
+<https://cla.developers.google.com/> to see your current agreements on file or
+to sign a new one.
+
+You generally only need to submit a CLA once, so if you've already submitted one
+(even if it was for a different project), you probably don't need to do it
+again.
+
+## Code Reviews
+
+All submissions, including submissions by project members, require review. We
+use GitHub pull requests for this purpose. Consult
+[GitHub Help](https://help.github.com/articles/about-pull-requests/) for more
+information on using pull requests.
+
+## Coding style
+
+The Dart source code in this repo follows the:
+
+  * [Dart style guide](https://dart.dev/guides/language/effective-dart/style)
+
+You should familiarize yourself with those guidelines.
+
+## File headers
+
+All files in the Dart project must start with the following header; if you add a
+new file please also add this. The year should be a single number stating the
+year the file was created (don't use a range like "2011-2012"). Additionally, if
+you edit an existing file, you shouldn't update the year.
+
+    // Copyright (c) 2023, 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.
+
+## Community Guidelines
+
+This project follows
+[Google's Open Source Community Guidelines](https://opensource.google/conduct/).
+
+We pledge to maintain an open and welcoming environment. For details, see our
+[code of conduct](https://dart.dev/code-of-conduct).
diff --git a/LICENSE b/LICENSE
new file mode 100644
index 0000000..4fd5739
--- /dev/null
+++ b/LICENSE
@@ -0,0 +1,27 @@
+Copyright 2023, the Dart project authors.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+    * Redistributions of source code must retain the above copyright
+      notice, this list of conditions and the following disclaimer.
+    * Redistributions in binary form must reproduce the above
+      copyright notice, this list of conditions and the following
+      disclaimer in the documentation and/or other materials provided
+      with the distribution.
+    * Neither the name of Google LLC nor the names of its
+      contributors may be used to endorse or promote products derived
+      from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
diff --git a/README.md b/README.md
new file mode 100644
index 0000000..ac4edf2
--- /dev/null
+++ b/README.md
@@ -0,0 +1,35 @@
+<!-- [![Dart CI](https://github.com/dart-lang/tools/actions/workflows/dart.yml/badge.svg)](https://github.com/dart-lang/tools/actions/workflows/dart.yml) -->
+
+## Overview
+
+This repository is home to tooling related Dart packages. Generally, this means
+packages published through the
+[tools.dart.dev](https://pub.dev/publishers/tools.dart.dev) publisher that
+don't naturally belong to other topic monorepos (like
+[dart-lang/build](https://github.com/dart-lang/build),
+[dart-lang/test](https://github.com/dart-lang/test), or
+[dart-lang/shelf](https://github.com/dart-lang/shelf)).
+
+## Packages
+
+| Package | Description | Version |
+| --- | --- | --- |
+| [boolean_selector](pkgs/boolean_selector/) | A flexible syntax for boolean expressions, based on a simplified version of Dart's expression syntax. | [![pub package](https://img.shields.io/pub/v/boolean_selector.svg)](https://pub.dev/packages/boolean_selector) |
+| [cli_config](pkgs/cli_config/) | A library to take config values from configuration files, CLI arguments, and environment variables. | [![pub package](https://img.shields.io/pub/v/cli_config.svg)](https://pub.dev/packages/cli_config) |
+| [coverage](pkgs/coverage/) | Coverage data manipulation and formatting. | [![pub package](https://img.shields.io/pub/v/coverage.svg)](https://pub.dev/packages/coverage) |
+| [extension_discovery](pkgs/extension_discovery/) | A convention and utilities for package extension discovery. | [![pub package](https://img.shields.io/pub/v/extension_discovery.svg)](https://pub.dev/packages/extension_discovery) |
+| [file](pkgs/file/) | A pluggable, mockable file system abstraction for Dart. | [![pub package](https://img.shields.io/pub/v/file.svg)](https://pub.dev/packages/file) |
+| [file_testing](pkgs/file_testing/) | Testing utilities for package:file (published but unlisted). | [![pub package](https://img.shields.io/pub/v/file_testing.svg)](https://pub.dev/packages/file_testing) |
+| [graphs](pkgs/graphs/) | Graph algorithms that operate on graphs in any representation | [![pub package](https://img.shields.io/pub/v/graphs.svg)](https://pub.dev/packages/graphs) |
+| [mime](pkgs/mime/) | Utilities for handling media (MIME) types. | [![pub package](https://img.shields.io/pub/v/mime.svg)](https://pub.dev/packages/mime) |
+| [oauth2](pkgs/oauth2/) | A client library for authenticatingand making requests via OAuth2. | [![pub package](https://img.shields.io/pub/v/oauth2.svg)](https://pub.dev/packages/oauth2) |
+| [source_map_stack_trace](pkgs/source_map_stack_trace/) | A package for applying source maps to stack traces. | [![pub package](https://img.shields.io/pub/v/source_map_stack_trace.svg)](https://pub.dev/packages/source_map_stack_trace) |
+| [unified_analytics](pkgs/unified_analytics/) | A package for logging analytics for all Dart and Flutter related tooling to Google Analytics. | [![pub package](https://img.shields.io/pub/v/unified_analytics.svg)](https://pub.dev/packages/unified_analytics) |
+
+## Publishing automation
+
+For information about our publishing automation and release process, see
+https://github.com/dart-lang/ecosystem/wiki/Publishing-automation.
+
+For additional information about contributing, see our
+[contributing](CONTRIBUTING.md) page.
diff --git a/pkgs/boolean_selector/.gitignore b/pkgs/boolean_selector/.gitignore
new file mode 100644
index 0000000..49ce72d
--- /dev/null
+++ b/pkgs/boolean_selector/.gitignore
@@ -0,0 +1,3 @@
+.dart_tool/
+.packages
+pubspec.lock
diff --git a/pkgs/boolean_selector/AUTHORS b/pkgs/boolean_selector/AUTHORS
new file mode 100644
index 0000000..e8063a8
--- /dev/null
+++ b/pkgs/boolean_selector/AUTHORS
@@ -0,0 +1,6 @@
+# Below is a list of people and organizations that have contributed
+# to the project. Names should be added to the list like so:
+#
+#   Name/Organization <email address>
+
+Google Inc.
diff --git a/pkgs/boolean_selector/CHANGELOG.md b/pkgs/boolean_selector/CHANGELOG.md
new file mode 100644
index 0000000..f870787
--- /dev/null
+++ b/pkgs/boolean_selector/CHANGELOG.md
@@ -0,0 +1,44 @@
+## 2.1.2
+
+* Increase the SDK minimum to `3.1.0`.
+* Move to `dart-lang/tools` monorepo.
+
+## 2.1.1
+
+* Increase the SDK minimum to `2.17.0`.
+* Populate the pubspec `repository` field.
+
+## 2.1.0
+
+* Stable release for null safety.
+
+## 2.0.0
+
+* Breaking: `BooleanSelector.evaluate` always takes a `bool Function(String)`.
+  For use cases previously passing a `Set<String>`, tear off the `.contains`
+  method. For use cases passing an `Iterable<String>` it may be worthwhile to
+  first use `.toSet()` before tearing off `.contains`.
+
+## 1.0.5
+
+* Update package metadata & add `example/` folder
+
+## 1.0.4
+
+* Now requires Dart 2.
+
+## 1.0.3
+
+* Work around an inference bug in the new common front-end.
+
+## 1.0.2
+
+* Declare compatibility with `string_scanner` 1.0.0.
+
+## 1.0.1
+
+* Fix all strong mode warnings.
+
+## 1.0.0
+
+* Initial release.
diff --git a/pkgs/boolean_selector/LICENSE b/pkgs/boolean_selector/LICENSE
new file mode 100644
index 0000000..ac7d7af
--- /dev/null
+++ b/pkgs/boolean_selector/LICENSE
@@ -0,0 +1,27 @@
+Copyright 2016, the Dart project authors.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+    * Redistributions of source code must retain the above copyright
+      notice, this list of conditions and the following disclaimer.
+    * Redistributions in binary form must reproduce the above
+      copyright notice, this list of conditions and the following
+      disclaimer in the documentation and/or other materials provided
+      with the distribution.
+    * Neither the name of Google LLC nor the names of its
+      contributors may be used to endorse or promote products derived
+      from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
diff --git a/pkgs/boolean_selector/README.md b/pkgs/boolean_selector/README.md
new file mode 100644
index 0000000..8d58dbb
--- /dev/null
+++ b/pkgs/boolean_selector/README.md
@@ -0,0 +1,42 @@
+[![Build Status](https://github.com/dart-lang/tools/actions/workflows/boolean_selector.yaml/badge.svg)](https://github.com/dart-lang/tools/actions/workflows/boolean_selector.yaml)
+[![Pub Package](https://img.shields.io/pub/v/boolean_selector.svg)](https://pub.dev/packages/boolean_selector)
+[![package publisher](https://img.shields.io/pub/publisher/boolean_selector.svg)](https://pub.dev/packages/boolean_selector/publisher)
+
+The `boolean_selector` package defines a simple and flexible syntax for boolean
+expressions. It can be used for filtering based on user-defined expressions. For
+example, the [`test`][test] package uses boolean selectors to allow users to
+define what platforms their tests support.
+
+[test]: https://github.com/dart-lang/test
+
+The boolean selector syntax is based on a simplified version of Dart's
+expression syntax. Selectors can contain identifiers, parentheses, and boolean
+operators, including `||`, `&&`, `!`, and `? :`. Any valid Dart identifier is
+allowed, and identifiers may also contain hyphens. For example, `chrome`,
+`chrome || content-shell`, and `js || (vm && linux)` are all valid boolean
+selectors.
+
+A boolean selector is parsed from a string using
+[`BooleanSelector.parse()`][parse], and evaluated against a set of variables
+using [`BooleanSelector.evaluate()`][evaluate]. The variables are supplied as
+a function that takes a variable name and returns its value. For example:
+
+[parse]: https://pub.dev/documentation/boolean_selector/latest/boolean_selector/BooleanSelector/BooleanSelector.parse.html
+
+[evaluate]: https://pub.dev/documentation/boolean_selector/latest/boolean_selector/BooleanSelector/evaluate.html
+
+```dart
+import 'package:boolean_selector/boolean_selector.dart';
+
+void main(List<String> args) {
+  var selector = BooleanSelector.parse("(x && y) || z");
+  print(selector.evaluate((variable) => args.contains(variable)));
+}
+```
+
+## Versioning
+
+If this package adds new features to the boolean selector syntax, it will
+increment its major version number. This ensures that packages that expose the
+syntax to their users will be able to update their own minor versions, so their
+users can indicate that they rely on the new syntax.
diff --git a/pkgs/boolean_selector/analysis_options.yaml b/pkgs/boolean_selector/analysis_options.yaml
new file mode 100644
index 0000000..178039f
--- /dev/null
+++ b/pkgs/boolean_selector/analysis_options.yaml
@@ -0,0 +1,7 @@
+include: package:dart_flutter_team_lints/analysis_options.yaml
+
+linter:
+  rules:
+    - avoid_unused_constructor_parameters
+    - cancel_subscriptions
+    - package_api_docs
diff --git a/pkgs/boolean_selector/example/example.dart b/pkgs/boolean_selector/example/example.dart
new file mode 100644
index 0000000..a4f7879
--- /dev/null
+++ b/pkgs/boolean_selector/example/example.dart
@@ -0,0 +1,6 @@
+import 'package:boolean_selector/boolean_selector.dart';
+
+void main(List<String> args) {
+  var selector = BooleanSelector.parse('(x && y) || z');
+  print(selector.evaluate((variable) => args.contains(variable)));
+}
diff --git a/pkgs/boolean_selector/lib/boolean_selector.dart b/pkgs/boolean_selector/lib/boolean_selector.dart
new file mode 100644
index 0000000..1c42641
--- /dev/null
+++ b/pkgs/boolean_selector/lib/boolean_selector.dart
@@ -0,0 +1,56 @@
+// Copyright (c) 2016, 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.
+
+import 'package:source_span/source_span.dart';
+
+import 'src/all.dart';
+import 'src/impl.dart';
+import 'src/none.dart';
+
+/// A boolean expression that evaluates to `true` or `false` based on certain
+/// inputs.
+///
+/// The syntax is mostly Dart's expression syntax restricted to boolean
+/// operations. See [the README][] for full details.
+///
+/// [the README]: https://github.com/dart-lang/boolean_selector/blob/master/README.md
+///
+/// Boolean selectors support structural equality. Two selectors that have the
+/// same parsed structure are considered equal.
+abstract class BooleanSelector {
+  /// A selector that accepts all inputs.
+  static const all = All();
+
+  /// A selector that accepts no inputs.
+  static const none = None();
+
+  /// All the variables in this selector, in the order they appear.
+  Iterable<String> get variables;
+
+  /// Parses [selector].
+  ///
+  /// This will throw a [SourceSpanFormatException] if the selector is
+  /// malformed or if it uses an undefined variable.
+  factory BooleanSelector.parse(String selector) = BooleanSelectorImpl.parse;
+
+  /// Returns whether the selector matches the given [semantics].
+  ///
+  /// The [semantics] define which variables evaluate to `true` or `false`. When
+  /// passed a variable name it should return the value of that variable.
+  bool evaluate(bool Function(String variable) semantics);
+
+  /// Returns a new [BooleanSelector] that matches only inputs matched by both
+  /// `this` and [other].
+  BooleanSelector intersection(BooleanSelector other);
+
+  /// Returns a new [BooleanSelector] that matches all inputs matched by either
+  /// `this` or [other].
+  BooleanSelector union(BooleanSelector other);
+
+  /// Throws a [FormatException] if any variables are undefined.
+  ///
+  /// The [isDefined] function should return `true` for any variables that are
+  /// considered valid, and `false` for any invalid or undefined variables.
+  void validate(bool Function(String variable) isDefined);
+}
diff --git a/pkgs/boolean_selector/lib/src/all.dart b/pkgs/boolean_selector/lib/src/all.dart
new file mode 100644
index 0000000..3424319
--- /dev/null
+++ b/pkgs/boolean_selector/lib/src/all.dart
@@ -0,0 +1,30 @@
+// Copyright (c) 2016, 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.
+
+import '../boolean_selector.dart';
+
+/// A selector that matches all inputs.
+class All implements BooleanSelector {
+  // TODO(nweiz): Stop explicitly providing a type argument when sdk#32412 is
+  // fixed.
+  @override
+  final Iterable<String> variables = const <String>[];
+
+  const All();
+
+  @override
+  bool evaluate(bool Function(String variable) semantics) => true;
+
+  @override
+  BooleanSelector intersection(BooleanSelector other) => other;
+
+  @override
+  BooleanSelector union(BooleanSelector other) => this;
+
+  @override
+  void validate(bool Function(String variable) isDefined) {}
+
+  @override
+  String toString() => '<all>';
+}
diff --git a/pkgs/boolean_selector/lib/src/ast.dart b/pkgs/boolean_selector/lib/src/ast.dart
new file mode 100644
index 0000000..d0d8583
--- /dev/null
+++ b/pkgs/boolean_selector/lib/src/ast.dart
@@ -0,0 +1,210 @@
+// Copyright (c) 2016, 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.
+
+import 'package:source_span/source_span.dart';
+
+import 'visitor.dart';
+
+/// The superclass of nodes in the boolean selector abstract syntax tree.
+abstract class Node {
+  /// The span indicating where this node came from.
+  ///
+  /// This is a [FileSpan] because the nodes are parsed from a single continuous
+  /// string, but the string itself isn't actually a file. It might come from a
+  /// statically-parsed annotation or from a parameter.
+  ///
+  /// This may be `null` for nodes without source information.
+  FileSpan? get span;
+
+  /// All the variables in this node, in the order they appear.
+  Iterable<String> get variables;
+
+  /// Calls the appropriate [Visitor] method on `this` and returns the result.
+  T accept<T>(Visitor<T> visitor);
+}
+
+/// A single variable.
+class VariableNode implements Node {
+  @override
+  final FileSpan? span;
+
+  /// The variable name.
+  final String name;
+
+  @override
+  Iterable<String> get variables => [name];
+
+  VariableNode(this.name, [this.span]);
+
+  @override
+  T accept<T>(Visitor<T> visitor) => visitor.visitVariable(this);
+
+  @override
+  String toString() => name;
+
+  @override
+  bool operator ==(Object other) => other is VariableNode && name == other.name;
+
+  @override
+  int get hashCode => name.hashCode;
+}
+
+/// A negation expression.
+class NotNode implements Node {
+  @override
+  final FileSpan? span;
+
+  /// The expression being negated.
+  final Node child;
+
+  @override
+  Iterable<String> get variables => child.variables;
+
+  NotNode(this.child, [this.span]);
+
+  @override
+  T accept<T>(Visitor<T> visitor) => visitor.visitNot(this);
+
+  @override
+  String toString() =>
+      child is VariableNode || child is NotNode ? '!$child' : '!($child)';
+
+  @override
+  bool operator ==(Object other) => other is NotNode && child == other.child;
+
+  @override
+  int get hashCode => ~child.hashCode;
+}
+
+/// An or expression.
+class OrNode implements Node {
+  @override
+  FileSpan? get span => _expandSafe(left.span, right.span);
+
+  /// The left-hand branch of the expression.
+  final Node left;
+
+  /// The right-hand branch of the expression.
+  final Node right;
+
+  @override
+  Iterable<String> get variables sync* {
+    yield* left.variables;
+    yield* right.variables;
+  }
+
+  OrNode(this.left, this.right);
+
+  @override
+  T accept<T>(Visitor<T> visitor) => visitor.visitOr(this);
+
+  @override
+  String toString() {
+    var string1 = left is AndNode || left is ConditionalNode ? '($left)' : left;
+    var string2 =
+        right is AndNode || right is ConditionalNode ? '($right)' : right;
+
+    return '$string1 || $string2';
+  }
+
+  @override
+  bool operator ==(Object other) =>
+      other is OrNode && left == other.left && right == other.right;
+
+  @override
+  int get hashCode => left.hashCode ^ right.hashCode;
+}
+
+/// An and expression.
+class AndNode implements Node {
+  @override
+  FileSpan? get span => _expandSafe(left.span, right.span);
+
+  /// The left-hand branch of the expression.
+  final Node left;
+
+  /// The right-hand branch of the expression.
+  final Node right;
+
+  @override
+  Iterable<String> get variables sync* {
+    yield* left.variables;
+    yield* right.variables;
+  }
+
+  AndNode(this.left, this.right);
+
+  @override
+  T accept<T>(Visitor<T> visitor) => visitor.visitAnd(this);
+
+  @override
+  String toString() {
+    var string1 = left is OrNode || left is ConditionalNode ? '($left)' : left;
+    var string2 =
+        right is OrNode || right is ConditionalNode ? '($right)' : right;
+
+    return '$string1 && $string2';
+  }
+
+  @override
+  bool operator ==(Object other) =>
+      other is AndNode && left == other.left && right == other.right;
+
+  @override
+  int get hashCode => left.hashCode ^ right.hashCode;
+}
+
+/// A ternary conditional expression.
+class ConditionalNode implements Node {
+  @override
+  FileSpan? get span => _expandSafe(condition.span, whenFalse.span);
+
+  /// The condition expression to check.
+  final Node condition;
+
+  /// The branch to run if the condition is true.
+  final Node whenTrue;
+
+  /// The branch to run if the condition is false.
+  final Node whenFalse;
+
+  @override
+  Iterable<String> get variables sync* {
+    yield* condition.variables;
+    yield* whenTrue.variables;
+    yield* whenFalse.variables;
+  }
+
+  ConditionalNode(this.condition, this.whenTrue, this.whenFalse);
+
+  @override
+  T accept<T>(Visitor<T> visitor) => visitor.visitConditional(this);
+
+  @override
+  String toString() {
+    var conditionString =
+        condition is ConditionalNode ? '($condition)' : condition;
+    var trueString = whenTrue is ConditionalNode ? '($whenTrue)' : whenTrue;
+    return '$conditionString ? $trueString : $whenFalse';
+  }
+
+  @override
+  bool operator ==(Object other) =>
+      other is ConditionalNode &&
+      condition == other.condition &&
+      whenTrue == other.whenTrue &&
+      whenFalse == other.whenFalse;
+
+  @override
+  int get hashCode =>
+      condition.hashCode ^ whenTrue.hashCode ^ whenFalse.hashCode;
+}
+
+/// Like [FileSpan.expand], except if [start] and [end] are `null` or from
+/// different files it returns `null` rather than throwing an error.
+FileSpan? _expandSafe(FileSpan? start, FileSpan? end) {
+  if (start == null || end == null) return null;
+  if (start.file != end.file) return null;
+  return start.expand(end);
+}
diff --git a/pkgs/boolean_selector/lib/src/evaluator.dart b/pkgs/boolean_selector/lib/src/evaluator.dart
new file mode 100644
index 0000000..ee57149
--- /dev/null
+++ b/pkgs/boolean_selector/lib/src/evaluator.dart
@@ -0,0 +1,33 @@
+// Copyright (c) 2016, 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.
+
+import 'ast.dart';
+import 'visitor.dart';
+
+/// A visitor for evaluating boolean selectors against a specific set of
+/// semantics.
+class Evaluator implements Visitor<bool> {
+  final bool Function(String variable) _semantics;
+
+  Evaluator(this._semantics);
+
+  @override
+  bool visitVariable(VariableNode node) => _semantics(node.name);
+
+  @override
+  bool visitNot(NotNode node) => !node.child.accept(this);
+
+  @override
+  bool visitOr(OrNode node) =>
+      node.left.accept(this) || node.right.accept(this);
+
+  @override
+  bool visitAnd(AndNode node) =>
+      node.left.accept(this) && node.right.accept(this);
+
+  @override
+  bool visitConditional(ConditionalNode node) => node.condition.accept(this)
+      ? node.whenTrue.accept(this)
+      : node.whenFalse.accept(this);
+}
diff --git a/pkgs/boolean_selector/lib/src/impl.dart b/pkgs/boolean_selector/lib/src/impl.dart
new file mode 100644
index 0000000..cafb1a4
--- /dev/null
+++ b/pkgs/boolean_selector/lib/src/impl.dart
@@ -0,0 +1,72 @@
+// Copyright (c) 2016, 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.
+
+import 'package:source_span/source_span.dart';
+
+import '../boolean_selector.dart';
+import 'ast.dart';
+import 'evaluator.dart';
+import 'intersection_selector.dart';
+import 'parser.dart';
+import 'union_selector.dart';
+import 'validator.dart';
+
+/// The concrete implementation of a [BooleanSelector] parsed from a string.
+///
+/// This is separate from [BooleanSelector] so that [intersection] and [union]
+/// can check to see whether they're passed a [BooleanSelectorImpl] or a
+/// different class that implements [BooleanSelector].
+class BooleanSelectorImpl implements BooleanSelector {
+  /// The parsed AST.
+  final Node _selector;
+
+  /// Parses [selector].
+  ///
+  /// This will throw a [SourceSpanFormatException] if the selector is
+  /// malformed or if it uses an undefined variable.
+  BooleanSelectorImpl.parse(String selector)
+      : _selector = Parser(selector).parse();
+
+  BooleanSelectorImpl._(this._selector);
+
+  @override
+  Iterable<String> get variables => _selector.variables;
+
+  @override
+  bool evaluate(bool Function(String variable) semantics) =>
+      _selector.accept(Evaluator(semantics));
+
+  @override
+  BooleanSelector intersection(BooleanSelector other) {
+    if (other == BooleanSelector.all) return this;
+    if (other == BooleanSelector.none) return other;
+    return other is BooleanSelectorImpl
+        ? BooleanSelectorImpl._(AndNode(_selector, other._selector))
+        : IntersectionSelector(this, other);
+  }
+
+  @override
+  BooleanSelector union(BooleanSelector other) {
+    if (other == BooleanSelector.all) return other;
+    if (other == BooleanSelector.none) return this;
+    return other is BooleanSelectorImpl
+        ? BooleanSelectorImpl._(OrNode(_selector, other._selector))
+        : UnionSelector(this, other);
+  }
+
+  @override
+  void validate(bool Function(String variable) isDefined) {
+    _selector.accept(Validator(isDefined));
+  }
+
+  @override
+  String toString() => _selector.toString();
+
+  @override
+  bool operator ==(Object other) =>
+      other is BooleanSelectorImpl && _selector == other._selector;
+
+  @override
+  int get hashCode => _selector.hashCode;
+}
diff --git a/pkgs/boolean_selector/lib/src/intersection_selector.dart b/pkgs/boolean_selector/lib/src/intersection_selector.dart
new file mode 100644
index 0000000..3bf468c
--- /dev/null
+++ b/pkgs/boolean_selector/lib/src/intersection_selector.dart
@@ -0,0 +1,49 @@
+// Copyright (c) 2016, 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.
+
+import '../boolean_selector.dart';
+import 'union_selector.dart';
+
+/// A selector that matches inputs that both of its sub-selectors match.
+class IntersectionSelector implements BooleanSelector {
+  final BooleanSelector _selector1;
+  final BooleanSelector _selector2;
+
+  @override
+  Iterable<String> get variables sync* {
+    yield* _selector1.variables;
+    yield* _selector2.variables;
+  }
+
+  IntersectionSelector(this._selector1, this._selector2);
+
+  @override
+  bool evaluate(bool Function(String variable) semantics) =>
+      _selector1.evaluate(semantics) && _selector2.evaluate(semantics);
+
+  @override
+  BooleanSelector intersection(BooleanSelector other) =>
+      IntersectionSelector(this, other);
+
+  @override
+  BooleanSelector union(BooleanSelector other) => UnionSelector(this, other);
+
+  @override
+  void validate(bool Function(String variable) isDefined) {
+    _selector1.validate(isDefined);
+    _selector2.validate(isDefined);
+  }
+
+  @override
+  String toString() => '($_selector1) && ($_selector2)';
+
+  @override
+  bool operator ==(Object other) =>
+      other is IntersectionSelector &&
+      _selector1 == other._selector1 &&
+      _selector2 == other._selector2;
+
+  @override
+  int get hashCode => _selector1.hashCode ^ _selector2.hashCode;
+}
diff --git a/pkgs/boolean_selector/lib/src/none.dart b/pkgs/boolean_selector/lib/src/none.dart
new file mode 100644
index 0000000..08ac08a
--- /dev/null
+++ b/pkgs/boolean_selector/lib/src/none.dart
@@ -0,0 +1,28 @@
+// Copyright (c) 2016, 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.
+
+import '../boolean_selector.dart';
+
+/// A selector that matches no inputs.
+class None implements BooleanSelector {
+  @override
+  final Iterable<String> variables = const [];
+
+  const None();
+
+  @override
+  bool evaluate(bool Function(String variable) semantics) => false;
+
+  @override
+  BooleanSelector intersection(BooleanSelector other) => this;
+
+  @override
+  BooleanSelector union(BooleanSelector other) => other;
+
+  @override
+  void validate(bool Function(String) isDefined) {}
+
+  @override
+  String toString() => '<none>';
+}
diff --git a/pkgs/boolean_selector/lib/src/parser.dart b/pkgs/boolean_selector/lib/src/parser.dart
new file mode 100644
index 0000000..368ce5e
--- /dev/null
+++ b/pkgs/boolean_selector/lib/src/parser.dart
@@ -0,0 +1,103 @@
+// Copyright (c) 2016, 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.
+
+import 'package:source_span/source_span.dart';
+
+import 'ast.dart';
+import 'scanner.dart';
+import 'token.dart';
+
+/// A class for parsing a boolean selector.
+///
+/// Boolean selectors use a stripped-down version of the Dart expression syntax
+/// that only contains variables, parentheses, and boolean operators. Variables
+/// may also contain dashes, contrary to Dart's syntax; this allows consistency
+/// with command-line arguments.
+class Parser {
+  /// The scanner that tokenizes the selector.
+  final Scanner _scanner;
+
+  Parser(String selector) : _scanner = Scanner(selector);
+
+  /// Parses the selector.
+  ///
+  /// This must only be called once per parser.
+  Node parse() {
+    var selector = _conditional();
+
+    if (_scanner.peek().type != TokenType.endOfFile) {
+      throw SourceSpanFormatException(
+          'Expected end of input.', _scanner.peek().span);
+    }
+
+    return selector;
+  }
+
+  /// Parses a conditional:
+  ///
+  ///     conditionalExpression:
+  ///       logicalOrExpression ("?" conditionalExpression ":"
+  ///           conditionalExpression)?
+  Node _conditional() {
+    var condition = _or();
+    if (!_scanner.scan(TokenType.questionMark)) return condition;
+
+    var whenTrue = _conditional();
+    if (!_scanner.scan(TokenType.colon)) {
+      throw SourceSpanFormatException('Expected ":".', _scanner.peek().span);
+    }
+
+    var whenFalse = _conditional();
+    return ConditionalNode(condition, whenTrue, whenFalse);
+  }
+
+  /// Parses a logical or:
+  ///
+  ///     logicalOrExpression:
+  ///       logicalAndExpression ("||" logicalOrExpression)?
+  Node _or() {
+    var left = _and();
+    if (!_scanner.scan(TokenType.or)) return left;
+    return OrNode(left, _or());
+  }
+
+  /// Parses a logical and:
+  ///
+  ///     logicalAndExpression:
+  ///       simpleExpression ("&&" logicalAndExpression)?
+  Node _and() {
+    var left = _simpleExpression();
+    if (!_scanner.scan(TokenType.and)) return left;
+    return AndNode(left, _and());
+  }
+
+  /// Parses a simple expression:
+  ///
+  ///     simpleExpression:
+  ///       "!" simpleExpression |
+  ///           "(" conditionalExpression ")" |
+  ///           IDENTIFIER
+  Node _simpleExpression() {
+    var token = _scanner.next();
+    switch (token.type) {
+      case TokenType.not:
+        var child = _simpleExpression();
+        return NotNode(child, token.span.expand(child.span!));
+
+      case TokenType.leftParen:
+        var child = _conditional();
+        if (!_scanner.scan(TokenType.rightParen)) {
+          throw SourceSpanFormatException(
+              'Expected ")".', _scanner.peek().span);
+        }
+        return child;
+
+      case TokenType.identifier:
+        return VariableNode((token as IdentifierToken).name, token.span);
+
+      default:
+        throw SourceSpanFormatException('Expected expression.', token.span);
+    }
+  }
+}
diff --git a/pkgs/boolean_selector/lib/src/scanner.dart b/pkgs/boolean_selector/lib/src/scanner.dart
new file mode 100644
index 0000000..25c4a11
--- /dev/null
+++ b/pkgs/boolean_selector/lib/src/scanner.dart
@@ -0,0 +1,144 @@
+// Copyright (c) 2016, 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.
+
+import 'package:string_scanner/string_scanner.dart';
+
+import 'token.dart';
+
+/// A regular expression matching both whitespace and single-line comments.
+///
+/// This will only match if consumes at least one character.
+final _whitespaceAndSingleLineComments = RegExp(r'([ \t\n]+|//[^\n]*(\n|$))+');
+
+/// A regular expression matching the body of a multi-line comment, after `/*`
+/// but before `*/` or a nested `/*`.
+///
+/// This will only match if it consumes at least one character.
+final _multiLineCommentBody = RegExp(r'([^/*]|/[^*]|\*[^/])+');
+
+/// A regular expression matching a hyphenated identifier.
+///
+/// This is like a standard Dart identifier, except that it can also contain
+/// hyphens.
+final _hyphenatedIdentifier = RegExp(r'[a-zA-Z_-][a-zA-Z0-9_-]*');
+
+/// A scanner that converts a boolean selector string into a stream of tokens.
+class Scanner {
+  /// The underlying string scanner.
+  final SpanScanner _scanner;
+
+  /// The next token to emit.
+  Token? _next;
+
+  /// Whether the scanner has emitted a [TokenType.endOfFile] token.
+  bool _endOfFileEmitted = false;
+
+  Scanner(String selector) : _scanner = SpanScanner(selector);
+
+  /// Returns the next token that will be returned by [next].
+  ///
+  /// Throws a [StateError] if a [TokenType.endOfFile] token has already been
+  /// consumed.
+  Token peek() => _next ??= _readNext();
+
+  /// Consumes and returns the next token in the stream.
+  ///
+  /// Throws a [StateError] if a [TokenType.endOfFile] token has already been
+  /// consumed.
+  Token next() {
+    var token = _next ?? _readNext();
+    _endOfFileEmitted = token.type == TokenType.endOfFile;
+    _next = null;
+    return token;
+  }
+
+  /// If the next token matches [type], consumes it and returns `true`;
+  /// otherwise, returns `false`.
+  ///
+  /// Throws a [StateError] if a [TokenType.endOfFile] token has already been
+  /// consumed.
+  bool scan(TokenType type) {
+    if (peek().type != type) return false;
+    next();
+    return true;
+  }
+
+  /// Scan and return the next token in the stream.
+  Token _readNext() {
+    if (_endOfFileEmitted) throw StateError('No more tokens.');
+
+    _consumeWhitespace();
+    if (_scanner.isDone) {
+      return Token(TokenType.endOfFile, _scanner.spanFrom(_scanner.state));
+    }
+
+    return switch (_scanner.peekChar()) {
+      0x28 /* ( */ => _scanOperator(TokenType.leftParen),
+      0x29 /* ) */ => _scanOperator(TokenType.rightParen),
+      0x3F /* ? */ => _scanOperator(TokenType.questionMark),
+      0x3A /* : */ => _scanOperator(TokenType.colon),
+      0x21 /* ! */ => _scanOperator(TokenType.not),
+      0x7C /* | */ => _scanOr(),
+      0x26 /* & */ => _scanAnd(),
+      _ => _scanIdentifier()
+    };
+  }
+
+  /// Scans a single-character operator and returns a token of type [type].
+  ///
+  /// This assumes that the caller has already verified that the next character
+  /// is correct for the given operator.
+  Token _scanOperator(TokenType type) {
+    var start = _scanner.state;
+    _scanner.readChar();
+    return Token(type, _scanner.spanFrom(start));
+  }
+
+  /// Scans a `||` operator and returns the appropriate token.
+  ///
+  /// This validates that the next two characters are `||`.
+  Token _scanOr() {
+    var start = _scanner.state;
+    _scanner.expect('||');
+    return Token(TokenType.or, _scanner.spanFrom(start));
+  }
+
+  /// Scans a `&&` operator and returns the appropriate token.
+  ///
+  /// This validates that the next two characters are `&&`.
+  Token _scanAnd() {
+    var start = _scanner.state;
+    _scanner.expect('&&');
+    return Token(TokenType.and, _scanner.spanFrom(start));
+  }
+
+  /// Scans and returns an identifier token.
+  Token _scanIdentifier() {
+    _scanner.expect(_hyphenatedIdentifier, name: 'expression');
+    return IdentifierToken(_scanner.lastMatch![0]!, _scanner.lastSpan!);
+  }
+
+  /// Consumes all whitespace and comments immediately following the cursor's
+  /// current position.
+  void _consumeWhitespace() {
+    while (_scanner.scan(_whitespaceAndSingleLineComments) ||
+        _multiLineComment()) {
+      // Do nothing.
+    }
+  }
+
+  /// Consumes a single multi-line comment.
+  ///
+  /// Returns whether or not a comment was consumed.
+  bool _multiLineComment() {
+    if (!_scanner.scan('/*')) return false;
+
+    while (_scanner.scan(_multiLineCommentBody) || _multiLineComment()) {
+      // Do nothing.
+    }
+    _scanner.expect('*/');
+
+    return true;
+  }
+}
diff --git a/pkgs/boolean_selector/lib/src/token.dart b/pkgs/boolean_selector/lib/src/token.dart
new file mode 100644
index 0000000..19e6864
--- /dev/null
+++ b/pkgs/boolean_selector/lib/src/token.dart
@@ -0,0 +1,74 @@
+// Copyright (c) 2016, 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.
+
+import 'package:source_span/source_span.dart';
+
+/// A token in a boolean selector.
+class Token {
+  /// The type of the token.
+  final TokenType type;
+
+  /// The span indicating where this token came from.
+  ///
+  /// This is a [FileSpan] because the tokens are parsed from a single
+  /// continuous string, but the string itself isn't actually a file. It might
+  /// come from a statically-parsed annotation or from a parameter.
+  final FileSpan span;
+
+  Token(this.type, this.span);
+}
+
+/// A token representing an identifier.
+class IdentifierToken implements Token {
+  @override
+  final type = TokenType.identifier;
+  @override
+  final FileSpan span;
+
+  /// The name of the identifier.
+  final String name;
+
+  IdentifierToken(this.name, this.span);
+
+  @override
+  String toString() => 'identifier "$name"';
+}
+
+/// An enumeration of types of tokens.
+class TokenType {
+  /// A `(` character.
+  static const leftParen = TokenType._('left paren');
+
+  /// A `)` character.
+  static const rightParen = TokenType._('right paren');
+
+  /// A `||` sequence.
+  static const or = TokenType._('or');
+
+  /// A `&&` sequence.
+  static const and = TokenType._('and');
+
+  /// A `!` character.
+  static const not = TokenType._('not');
+
+  /// A `?` character.
+  static const questionMark = TokenType._('question mark');
+
+  /// A `:` character.
+  static const colon = TokenType._('colon');
+
+  /// A named identifier.
+  static const identifier = TokenType._('identifier');
+
+  /// The end of the selector.
+  static const endOfFile = TokenType._('end of file');
+
+  /// The name of the token type.
+  final String name;
+
+  const TokenType._(this.name);
+
+  @override
+  String toString() => name;
+}
diff --git a/pkgs/boolean_selector/lib/src/union_selector.dart b/pkgs/boolean_selector/lib/src/union_selector.dart
new file mode 100644
index 0000000..e355eb2
--- /dev/null
+++ b/pkgs/boolean_selector/lib/src/union_selector.dart
@@ -0,0 +1,47 @@
+// Copyright (c) 2016, 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.
+
+import '../boolean_selector.dart';
+import 'intersection_selector.dart';
+
+/// A selector that matches inputs that either of its sub-selectors match.
+class UnionSelector implements BooleanSelector {
+  final BooleanSelector _selector1;
+  final BooleanSelector _selector2;
+
+  UnionSelector(this._selector1, this._selector2);
+
+  @override
+  List<String> get variables =>
+      _selector1.variables.toList()..addAll(_selector2.variables);
+
+  @override
+  bool evaluate(bool Function(String variable) semantics) =>
+      _selector1.evaluate(semantics) || _selector2.evaluate(semantics);
+
+  @override
+  BooleanSelector intersection(BooleanSelector other) =>
+      IntersectionSelector(this, other);
+
+  @override
+  BooleanSelector union(BooleanSelector other) => UnionSelector(this, other);
+
+  @override
+  void validate(bool Function(String variable) isDefined) {
+    _selector1.validate(isDefined);
+    _selector2.validate(isDefined);
+  }
+
+  @override
+  String toString() => '($_selector1) && ($_selector2)';
+
+  @override
+  bool operator ==(Object other) =>
+      other is UnionSelector &&
+      _selector1 == other._selector1 &&
+      _selector2 == other._selector2;
+
+  @override
+  int get hashCode => _selector1.hashCode ^ _selector2.hashCode;
+}
diff --git a/pkgs/boolean_selector/lib/src/validator.dart b/pkgs/boolean_selector/lib/src/validator.dart
new file mode 100644
index 0000000..a7f49f2
--- /dev/null
+++ b/pkgs/boolean_selector/lib/src/validator.dart
@@ -0,0 +1,23 @@
+// Copyright (c) 2016, 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.
+
+import 'package:source_span/source_span.dart';
+
+import 'ast.dart';
+import 'visitor.dart';
+
+typedef _IsDefined = bool Function(String variable);
+
+/// An AST visitor that ensures that all variables are valid.
+class Validator extends RecursiveVisitor {
+  final _IsDefined _isDefined;
+
+  Validator(this._isDefined);
+
+  @override
+  void visitVariable(VariableNode node) {
+    if (_isDefined(node.name)) return;
+    throw SourceSpanFormatException('Undefined variable.', node.span);
+  }
+}
diff --git a/pkgs/boolean_selector/lib/src/visitor.dart b/pkgs/boolean_selector/lib/src/visitor.dart
new file mode 100644
index 0000000..c6808c2
--- /dev/null
+++ b/pkgs/boolean_selector/lib/src/visitor.dart
@@ -0,0 +1,49 @@
+// Copyright (c) 2016, 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.
+
+import 'ast.dart';
+
+/// The interface for visitors of the boolean selector AST.
+abstract class Visitor<T> {
+  T visitVariable(VariableNode node);
+  T visitNot(NotNode node);
+  T visitOr(OrNode node);
+  T visitAnd(AndNode node);
+  T visitConditional(ConditionalNode node);
+}
+
+/// An abstract superclass for side-effect-based visitors.
+///
+/// The default implementations of this visitor's methods just traverse the AST
+/// and do nothing with it.
+abstract class RecursiveVisitor implements Visitor<void> {
+  const RecursiveVisitor();
+
+  @override
+  void visitVariable(VariableNode node) {}
+
+  @override
+  void visitNot(NotNode node) {
+    node.child.accept(this);
+  }
+
+  @override
+  void visitOr(OrNode node) {
+    node.left.accept(this);
+    node.right.accept(this);
+  }
+
+  @override
+  void visitAnd(AndNode node) {
+    node.left.accept(this);
+    node.right.accept(this);
+  }
+
+  @override
+  void visitConditional(ConditionalNode node) {
+    node.condition.accept(this);
+    node.whenTrue.accept(this);
+    node.whenFalse.accept(this);
+  }
+}
diff --git a/pkgs/boolean_selector/pubspec.yaml b/pkgs/boolean_selector/pubspec.yaml
new file mode 100644
index 0000000..8d9a8b6
--- /dev/null
+++ b/pkgs/boolean_selector/pubspec.yaml
@@ -0,0 +1,17 @@
+name: boolean_selector
+version: 2.1.2
+description: >-
+  A flexible syntax for boolean expressions, based on a simplified version of
+  Dart's expression syntax.
+repository: https://github.com/dart-lang/tools/tree/main/pkgs/boolean_selector
+
+environment:
+  sdk: ^3.1.0
+
+dependencies:
+  source_span: ^1.8.0
+  string_scanner: ^1.1.0
+
+dev_dependencies:
+  dart_flutter_team_lints: ^3.0.0
+  test: ^1.16.0
diff --git a/pkgs/boolean_selector/test/equality_test.dart b/pkgs/boolean_selector/test/equality_test.dart
new file mode 100644
index 0000000..c5ccb64
--- /dev/null
+++ b/pkgs/boolean_selector/test/equality_test.dart
@@ -0,0 +1,51 @@
+// Copyright (c) 2016, 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.
+
+import 'package:boolean_selector/boolean_selector.dart';
+import 'package:test/test.dart';
+
+void main() {
+  test('variable', () {
+    _expectEqualsSelf('foo');
+  });
+
+  test('not', () {
+    _expectEqualsSelf('!foo');
+  });
+
+  test('or', () {
+    _expectEqualsSelf('foo || bar');
+  });
+
+  test('and', () {
+    _expectEqualsSelf('foo && bar');
+  });
+
+  test('conditional', () {
+    _expectEqualsSelf('foo ? bar : baz');
+  });
+
+  test('all', () {
+    expect(BooleanSelector.all, equals(BooleanSelector.all));
+  });
+
+  test('none', () {
+    expect(BooleanSelector.none, equals(BooleanSelector.none));
+  });
+
+  test("redundant parens don't matter", () {
+    expect(BooleanSelector.parse('foo && (bar && baz)'),
+        equals(BooleanSelector.parse('foo && (bar && baz)')));
+  });
+
+  test('meaningful parens do matter', () {
+    expect(BooleanSelector.parse('(foo && bar) || baz'),
+        equals(BooleanSelector.parse('foo && bar || baz')));
+  });
+}
+
+void _expectEqualsSelf(String selector) {
+  expect(
+      BooleanSelector.parse(selector), equals(BooleanSelector.parse(selector)));
+}
diff --git a/pkgs/boolean_selector/test/evaluate_test.dart b/pkgs/boolean_selector/test/evaluate_test.dart
new file mode 100644
index 0000000..2d94906
--- /dev/null
+++ b/pkgs/boolean_selector/test/evaluate_test.dart
@@ -0,0 +1,59 @@
+// Copyright (c) 2016, 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.
+
+import 'package:boolean_selector/boolean_selector.dart';
+import 'package:test/test.dart';
+
+void main() {
+  group('operator:', () {
+    test('conditional', () {
+      _expectEval('true ? true : false', true);
+      _expectEval('true ? false : true', false);
+      _expectEval('false ? true : false', false);
+      _expectEval('false ? false : true', true);
+    });
+
+    test('or', () {
+      _expectEval('true || true', true);
+      _expectEval('true || false', true);
+      _expectEval('false || true', true);
+      _expectEval('false || false', false);
+    });
+
+    test('and', () {
+      _expectEval('true && true', true);
+      _expectEval('true && false', false);
+      _expectEval('false && true', false);
+      _expectEval('false && false', false);
+    });
+
+    test('not', () {
+      _expectEval('!true', false);
+      _expectEval('!false', true);
+    });
+  });
+
+  test('with a semantics function', () {
+    _expectEval('foo', false, semantics: (variable) => variable.contains('a'));
+    _expectEval('bar', true, semantics: (variable) => variable.contains('a'));
+    _expectEval('baz', true, semantics: (variable) => variable.contains('a'));
+  });
+}
+
+/// Asserts that [expression] evaluates to [result] against [semantics].
+///
+/// By default, "true" is true and all other variables are "false".
+void _expectEval(String expression, bool result,
+    {bool Function(String variable)? semantics}) {
+  expect(_eval(expression, semantics: semantics), equals(result),
+      reason: 'Expected "$expression" to evaluate to $result.');
+}
+
+/// Returns the result of evaluating [expression] on [semantics].
+///
+/// By default, "true" is true and all other variables are "false".
+bool _eval(String expression, {bool Function(String variable)? semantics}) {
+  var selector = BooleanSelector.parse(expression);
+  return selector.evaluate(semantics ?? (v) => v == 'true');
+}
diff --git a/pkgs/boolean_selector/test/parser_test.dart b/pkgs/boolean_selector/test/parser_test.dart
new file mode 100644
index 0000000..ba55e70
--- /dev/null
+++ b/pkgs/boolean_selector/test/parser_test.dart
@@ -0,0 +1,298 @@
+// Copyright (c) 2016, 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.
+
+import 'package:boolean_selector/src/ast.dart';
+import 'package:boolean_selector/src/parser.dart';
+import 'package:test/test.dart';
+
+/// A matcher that asserts that a value is a [ConditionalNode].
+const _isConditionalNode = TypeMatcher<ConditionalNode>();
+
+/// A matcher that asserts that a value is an [OrNode].
+const _isOrNode = TypeMatcher<OrNode>();
+
+/// A matcher that asserts that a value is an [AndNode].
+const _isAndNode = TypeMatcher<AndNode>();
+
+/// A matcher that asserts that a value is a [NotNode].
+const _isNotNode = TypeMatcher<NotNode>();
+
+void main() {
+  group('parses a conditional expression', () {
+    test('with identifiers', () {
+      var node = _parse('  a ? b : c   ');
+      expect(node.toString(), equals('a ? b : c'));
+
+      expect(node.span, isNotNull);
+      expect(node.span!.text, equals('a ? b : c'));
+      expect(node.span!.start.offset, equals(2));
+      expect(node.span!.end.offset, equals(11));
+    });
+
+    test('with nested ors', () {
+      // Should parse as "(a || b) ? (c || d) : (e || f)".
+      // Should not parse as "a || (b ? (c || d) : (e || f))".
+      // Should not parse as "((a || b) ? (c || d) : e) || f".
+      // Should not parse as "a || (b ? (c || d) : e) || f".
+      _expectToString('a || b ? c || d : e || f', 'a || b ? c || d : e || f');
+    });
+
+    test('with a conditional expression as branch 1', () {
+      // Should parse as "a ? (b ? c : d) : e".
+      var node = _parse('a ? b ? c : d : e');
+      expect(node, _isConditionalNode);
+      node as ConditionalNode; // promote node
+
+      expect(node.condition, _isVar('a'));
+      expect(node.whenFalse, _isVar('e'));
+
+      expect(node.whenTrue, _isConditionalNode);
+      var whenTrue = node.whenTrue as ConditionalNode;
+      expect(whenTrue.condition, _isVar('b'));
+      expect(whenTrue.whenTrue, _isVar('c'));
+      expect(whenTrue.whenFalse, _isVar('d'));
+    });
+
+    test('with a conditional expression as branch 2', () {
+      // Should parse as "a ? b : (c ? d : e)".
+      // Should not parse as "(a ? b : c) ? d : e".
+      var node = _parse('a ? b : c ? d : e');
+      expect(node, _isConditionalNode);
+      node as ConditionalNode; //promote node
+
+      expect(node.condition, _isVar('a'));
+      expect(node.whenTrue, _isVar('b'));
+
+      expect(node.whenFalse, _isConditionalNode);
+      var whenFalse = node.whenFalse as ConditionalNode;
+      expect(whenFalse.condition, _isVar('c'));
+      expect(whenFalse.whenTrue, _isVar('d'));
+      expect(whenFalse.whenFalse, _isVar('e'));
+    });
+
+    group('which must have', () {
+      test('an expression after the ?', () {
+        expect(() => _parse('a ?'), throwsFormatException);
+        expect(() => _parse('a ? && b'), throwsFormatException);
+      });
+
+      test('a :', () {
+        expect(() => _parse('a ? b'), throwsFormatException);
+        expect(() => _parse('a ? b && c'), throwsFormatException);
+      });
+
+      test('an expression after the :', () {
+        expect(() => _parse('a ? b :'), throwsFormatException);
+        expect(() => _parse('a ? b : && c'), throwsFormatException);
+      });
+    });
+  });
+
+  group('parses an or expression', () {
+    test('with identifiers', () {
+      var node = _parse('  a || b   ');
+      expect(node, _isOrNode);
+      node as OrNode; //promote node
+
+      expect(node.left, _isVar('a'));
+      expect(node.right, _isVar('b'));
+
+      expect(node.span, isNotNull);
+      expect(node.span!.text, equals('a || b'));
+      expect(node.span!.start.offset, equals(2));
+      expect(node.span!.end.offset, equals(8));
+    });
+
+    test('with nested ands', () {
+      // Should parse as "(a && b) || (c && d)".
+      // Should not parse as "a && (b || c) && d".
+      var node = _parse('a && b || c && d');
+      expect(node, _isOrNode);
+      node as OrNode; //promote node
+
+      expect(node.left, _isAndNode);
+      var left = node.left as AndNode;
+      expect(left.left, _isVar('a'));
+      expect(left.right, _isVar('b'));
+
+      expect(node.right, _isAndNode);
+      var right = node.right as AndNode;
+      expect(right.left, _isVar('c'));
+      expect(right.right, _isVar('d'));
+    });
+
+    test('with trailing ors', () {
+      // Should parse as "a || (b || (c || d))", although it doesn't affect the
+      // semantics.
+      var node = _parse('a || b || c || d');
+
+      for (var variable in ['a', 'b', 'c']) {
+        expect(node, _isOrNode);
+        node as OrNode; //promote node
+
+        expect(node.left, _isVar(variable));
+        node = node.right;
+      }
+      expect(node, _isVar('d'));
+    });
+
+    test('which must have an expression after the ||', () {
+      expect(() => _parse('a ||'), throwsFormatException);
+      expect(() => _parse('a || && b'), throwsFormatException);
+    });
+  });
+
+  group('parses an and expression', () {
+    test('with identifiers', () {
+      var node = _parse('  a && b   ');
+      expect(node, _isAndNode);
+      node as AndNode; //promote node
+
+      expect(node.left, _isVar('a'));
+      expect(node.right, _isVar('b'));
+
+      expect(node.span, isNotNull);
+      expect(node.span!.text, equals('a && b'));
+      expect(node.span!.start.offset, equals(2));
+      expect(node.span!.end.offset, equals(8));
+    });
+
+    test('with nested nots', () {
+      // Should parse as "(!a) && (!b)", obviously.
+      // Should not parse as "!(a && (!b))".
+      var node = _parse('!a && !b');
+      expect(node, _isAndNode);
+      node as AndNode; //promote node
+
+      expect(node.left, _isNotNode);
+      var left = node.left as NotNode;
+      expect(left.child, _isVar('a'));
+
+      expect(node.right, _isNotNode);
+      var right = node.right as NotNode;
+      expect(right.child, _isVar('b'));
+    });
+
+    test('with trailing ands', () {
+      // Should parse as "a && (b && (c && d))", although it doesn't affect the
+      // semantics since .
+      var node = _parse('a && b && c && d');
+
+      for (var variable in ['a', 'b', 'c']) {
+        expect(node, _isAndNode);
+        node as AndNode; //promote node
+
+        expect(node.left, _isVar(variable));
+        node = node.right;
+      }
+      expect(node, _isVar('d'));
+    });
+
+    test('which must have an expression after the &&', () {
+      expect(() => _parse('a &&'), throwsFormatException);
+      expect(() => _parse('a && && b'), throwsFormatException);
+    });
+  });
+
+  group('parses a not expression', () {
+    test('with an identifier', () {
+      var node = _parse('  ! a    ');
+      expect(node, _isNotNode);
+      node as NotNode; //promote node
+      expect(node.child, _isVar('a'));
+
+      expect(node.span, isNotNull);
+      expect(node.span!.text, equals('! a'));
+      expect(node.span!.start.offset, equals(2));
+      expect(node.span!.end.offset, equals(5));
+    });
+
+    test('with a parenthesized expression', () {
+      var node = _parse('!(a || b)');
+      expect(node, _isNotNode);
+      node as NotNode; //promote node
+
+      expect(node.child, _isOrNode);
+      var child = node.child as OrNode;
+      expect(child.left, _isVar('a'));
+      expect(child.right, _isVar('b'));
+    });
+
+    test('with a nested not', () {
+      var node = _parse('!!a');
+      expect(node, _isNotNode);
+      node as NotNode; //promote node
+
+      expect(node.child, _isNotNode);
+      var child = node.child as NotNode;
+      expect(child.child, _isVar('a'));
+    });
+
+    test('which must have an expression after the !', () {
+      expect(() => _parse('!'), throwsFormatException);
+      expect(() => _parse('! && a'), throwsFormatException);
+    });
+  });
+
+  group('parses a parenthesized expression', () {
+    test('with an identifier', () {
+      var node = _parse('(a)');
+      expect(node, _isVar('a'));
+    });
+
+    test('controls precedence', () {
+      // Without parentheses, this would parse as "(a || b) ? c : d".
+      var node = _parse('a || (b ? c : d)');
+
+      expect(node, _isOrNode);
+      node as OrNode; //promote node
+
+      expect(node.left, _isVar('a'));
+
+      expect(node.right, _isConditionalNode);
+      var right = node.right as ConditionalNode;
+      expect(right.condition, _isVar('b'));
+      expect(right.whenTrue, _isVar('c'));
+      expect(right.whenFalse, _isVar('d'));
+    });
+
+    group('which must have', () {
+      test('an expression within the ()', () {
+        expect(() => _parse('()'), throwsFormatException);
+        expect(() => _parse('( && a )'), throwsFormatException);
+      });
+
+      test('a matching )', () {
+        expect(() => _parse('( a'), throwsFormatException);
+      });
+    });
+  });
+
+  group('disallows', () {
+    test('an empty selector', () {
+      expect(() => _parse(''), throwsFormatException);
+    });
+
+    test('too many expressions', () {
+      expect(() => _parse('a b'), throwsFormatException);
+    });
+  });
+}
+
+/// Parses [selector] and returns its root node.
+Node _parse(String selector) => Parser(selector).parse();
+
+/// A matcher that asserts that a value is a [VariableNode] with the given
+/// [name].
+Matcher _isVar(String name) => predicate(
+    (dynamic value) => value is VariableNode && value.name == name,
+    'is a variable named "$name"');
+
+void _expectToString(String selector, [String? result]) {
+  result ??= selector;
+  expect(_toString(selector), equals(result),
+      reason: 'Expected toString of "$selector" to be "$result".');
+}
+
+String _toString(String selector) => Parser(selector).parse().toString();
diff --git a/pkgs/boolean_selector/test/scanner_test.dart b/pkgs/boolean_selector/test/scanner_test.dart
new file mode 100644
index 0000000..7ad78e2
--- /dev/null
+++ b/pkgs/boolean_selector/test/scanner_test.dart
@@ -0,0 +1,279 @@
+// Copyright (c) 2016, 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.
+
+import 'package:boolean_selector/src/scanner.dart';
+import 'package:boolean_selector/src/token.dart';
+import 'package:test/test.dart';
+
+/// A matcher that asserts that a value is a [IdentifierToken].
+const _isIdentifierToken = TypeMatcher<IdentifierToken>();
+
+void main() {
+  group('peek()', () {
+    test('returns the next token without consuming it', () {
+      var scanner = Scanner('( )');
+      expect(scanner.peek().type, equals(TokenType.leftParen));
+      expect(scanner.peek().type, equals(TokenType.leftParen));
+      expect(scanner.peek().type, equals(TokenType.leftParen));
+    });
+
+    test('returns an end-of-file token at the end of a file', () {
+      var scanner = Scanner('( )');
+      scanner.next();
+      scanner.next();
+
+      var token = scanner.peek();
+      expect(token.type, equals(TokenType.endOfFile));
+      expect(token.span.start.offset, equals(3));
+      expect(token.span.end.offset, equals(3));
+    });
+
+    test('throws a StateError if called after end-of-file was consumed', () {
+      var scanner = Scanner('( )');
+      scanner.next();
+      scanner.next();
+      scanner.next();
+      expect(() => scanner.peek(), throwsStateError);
+    });
+  });
+
+  group('next()', () {
+    test('consumes and returns the next token', () {
+      var scanner = Scanner('( )');
+      expect(scanner.next().type, equals(TokenType.leftParen));
+      expect(scanner.peek().type, equals(TokenType.rightParen));
+      expect(scanner.next().type, equals(TokenType.rightParen));
+    });
+
+    test('returns an end-of-file token at the end of a file', () {
+      var scanner = Scanner('( )');
+      scanner.next();
+      scanner.next();
+
+      var token = scanner.next();
+      expect(token.type, equals(TokenType.endOfFile));
+      expect(token.span.start.offset, equals(3));
+      expect(token.span.end.offset, equals(3));
+    });
+
+    test('throws a StateError if called after end-of-file was consumed', () {
+      var scanner = Scanner('( )');
+      scanner.next();
+      scanner.next();
+      scanner.next();
+      expect(() => scanner.next(), throwsStateError);
+    });
+  });
+
+  group('scan()', () {
+    test('consumes a matching token and returns true', () {
+      var scanner = Scanner('( )');
+      expect(scanner.scan(TokenType.leftParen), isTrue);
+      expect(scanner.peek().type, equals(TokenType.rightParen));
+    });
+
+    test("doesn't consume a matching token and returns false", () {
+      var scanner = Scanner('( )');
+      expect(scanner.scan(TokenType.questionMark), isFalse);
+      expect(scanner.peek().type, equals(TokenType.leftParen));
+    });
+
+    test('throws a StateError called after end-of-file was consumed', () {
+      var scanner = Scanner('( )');
+      scanner.next();
+      scanner.next();
+      scanner.next();
+      expect(() => scanner.scan(TokenType.endOfFile), throwsStateError);
+    });
+  });
+
+  group('scans a simple token:', () {
+    test('left paren', () => _expectSimpleScan('(', TokenType.leftParen));
+    test('right paren', () => _expectSimpleScan(')', TokenType.rightParen));
+    test('or', () => _expectSimpleScan('||', TokenType.or));
+    test('and', () => _expectSimpleScan('&&', TokenType.and));
+    test('not', () => _expectSimpleScan('!', TokenType.not));
+    test('question mark', () => _expectSimpleScan('?', TokenType.questionMark));
+    test('colon', () => _expectSimpleScan(':', TokenType.colon));
+  });
+
+  group('scans an identifier that', () {
+    test('is simple', () {
+      var token = _scan('   foo  ');
+      expect(token, _isIdentifierToken);
+      token as IdentifierToken; // promote token
+
+      expect(token.name, equals('foo'));
+      expect(token.span.text, equals('foo'));
+      expect(token.span.start.offset, equals(3));
+      expect(token.span.end.offset, equals(6));
+    });
+
+    test('is a single character', () {
+      var token = _scan('f');
+      expect(token, _isIdentifierToken);
+      expect((token as IdentifierToken).name, equals('f'));
+    });
+
+    test('has a leading underscore', () {
+      var token = _scan('_foo');
+      expect(token, _isIdentifierToken);
+      expect((token as IdentifierToken).name, equals('_foo'));
+    });
+
+    test('has a leading dash', () {
+      var token = _scan('-foo');
+      expect(token, _isIdentifierToken);
+      expect((token as IdentifierToken).name, equals('-foo'));
+    });
+
+    test('contains an underscore', () {
+      var token = _scan('foo_bar');
+      expect(token, _isIdentifierToken);
+      expect((token as IdentifierToken).name, equals('foo_bar'));
+    });
+
+    test('contains a dash', () {
+      var token = _scan('foo-bar');
+      expect(token, _isIdentifierToken);
+      expect((token as IdentifierToken).name, equals('foo-bar'));
+    });
+
+    test('is capitalized', () {
+      var token = _scan('FOO');
+      expect(token, _isIdentifierToken);
+      expect((token as IdentifierToken).name, equals('FOO'));
+    });
+
+    test('contains numbers', () {
+      var token = _scan('foo123');
+      expect(token, _isIdentifierToken);
+      expect((token as IdentifierToken).name, equals('foo123'));
+    });
+  });
+
+  test('scans an empty selector', () {
+    expect(_scan('').type, equals(TokenType.endOfFile));
+  });
+
+  test('scans multiple tokens', () {
+    var scanner = Scanner('(foo && bar)');
+
+    var token = scanner.next();
+    expect(token.type, equals(TokenType.leftParen));
+    expect(token.span.start.offset, equals(0));
+    expect(token.span.end.offset, equals(1));
+
+    token = scanner.next();
+    expect(token.type, equals(TokenType.identifier));
+    expect((token as IdentifierToken).name, equals('foo'));
+    expect(token.span.start.offset, equals(1));
+    expect(token.span.end.offset, equals(4));
+
+    token = scanner.next();
+    expect(token.type, equals(TokenType.and));
+    expect(token.span.start.offset, equals(5));
+    expect(token.span.end.offset, equals(7));
+
+    token = scanner.next();
+    expect(token.type, equals(TokenType.identifier));
+    expect((token as IdentifierToken).name, equals('bar'));
+    expect(token.span.start.offset, equals(8));
+    expect(token.span.end.offset, equals(11));
+
+    token = scanner.next();
+    expect(token.type, equals(TokenType.rightParen));
+    expect(token.span.start.offset, equals(11));
+    expect(token.span.end.offset, equals(12));
+
+    token = scanner.next();
+    expect(token.type, equals(TokenType.endOfFile));
+    expect(token.span.start.offset, equals(12));
+    expect(token.span.end.offset, equals(12));
+  });
+
+  group('ignores', () {
+    test('a single-line comment', () {
+      var scanner = Scanner('( // &&\n// ||\n)');
+      expect(scanner.next().type, equals(TokenType.leftParen));
+      expect(scanner.next().type, equals(TokenType.rightParen));
+      expect(scanner.next().type, equals(TokenType.endOfFile));
+    });
+
+    test('a single-line comment without a trailing newline', () {
+      var scanner = Scanner('( // &&');
+      expect(scanner.next().type, equals(TokenType.leftParen));
+      expect(scanner.next().type, equals(TokenType.endOfFile));
+    });
+
+    test('a multi-line comment', () {
+      var scanner = Scanner('( /* && * /\n|| */\n)');
+      expect(scanner.next().type, equals(TokenType.leftParen));
+      expect(scanner.next().type, equals(TokenType.rightParen));
+      expect(scanner.next().type, equals(TokenType.endOfFile));
+    });
+
+    test('a multi-line nested comment', () {
+      var scanner = Scanner('(/* && /* ? /* || */ : */ ! */)');
+      expect(scanner.next().type, equals(TokenType.leftParen));
+      expect(scanner.next().type, equals(TokenType.rightParen));
+      expect(scanner.next().type, equals(TokenType.endOfFile));
+    });
+
+    test("Dart's notion of whitespace", () {
+      var scanner = Scanner('( \t \n)');
+      expect(scanner.next().type, equals(TokenType.leftParen));
+      expect(scanner.next().type, equals(TokenType.rightParen));
+      expect(scanner.next().type, equals(TokenType.endOfFile));
+    });
+  });
+
+  group('disallows', () {
+    test('a single |', () {
+      expect(() => _scan('|'), throwsFormatException);
+    });
+
+    test('"| |"', () {
+      expect(() => _scan('| |'), throwsFormatException);
+    });
+
+    test('a single &', () {
+      expect(() => _scan('&'), throwsFormatException);
+    });
+
+    test('"& &"', () {
+      expect(() => _scan('& &'), throwsFormatException);
+    });
+
+    test('an unknown operator', () {
+      expect(() => _scan('=='), throwsFormatException);
+    });
+
+    test('unicode', () {
+      expect(() => _scan('öh'), throwsFormatException);
+    });
+
+    test('an unclosed multi-line comment', () {
+      expect(() => _scan('/*'), throwsFormatException);
+    });
+
+    test('an unopened multi-line comment', () {
+      expect(() => _scan('*/'), throwsFormatException);
+    });
+  });
+}
+
+/// Asserts that the first token scanned from [selector] has type [type],
+/// and that that token's span is exactly [selector].
+void _expectSimpleScan(String selector, TokenType type) {
+  // Complicate the selector to test that the span covers it correctly.
+  var token = _scan('   $selector  ');
+  expect(token.type, equals(type));
+  expect(token.span.text, equals(selector));
+  expect(token.span.start.offset, equals(3));
+  expect(token.span.end.offset, equals(3 + selector.length));
+}
+
+/// Scans a single token from [selector].
+Token _scan(String selector) => Scanner(selector).next();
diff --git a/pkgs/boolean_selector/test/to_string_test.dart b/pkgs/boolean_selector/test/to_string_test.dart
new file mode 100644
index 0000000..971e5b9
--- /dev/null
+++ b/pkgs/boolean_selector/test/to_string_test.dart
@@ -0,0 +1,84 @@
+// Copyright (c) 2016, 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.
+
+import 'package:boolean_selector/boolean_selector.dart';
+import 'package:test/test.dart';
+
+void main() {
+  group('toString() for', () {
+    test('a variable is its name', () {
+      _expectToString('foo');
+      _expectToString('a-b');
+    });
+
+    group('not', () {
+      test("doesn't parenthesize a variable", () => _expectToString('!a'));
+      test("doesn't parenthesize a nested not", () => _expectToString('!!a'));
+      test('parenthesizes an or', () => _expectToString('!(a || b)'));
+      test('parenthesizes an and', () => _expectToString('!(a && b)'));
+      test('parenthesizes a condition', () => _expectToString('!(a ? b : c)'));
+    });
+
+    group('or', () {
+      test("doesn't parenthesize variables", () => _expectToString('a || b'));
+      test("doesn't parenthesize nots", () => _expectToString('!a || !b'));
+
+      test("doesn't parenthesize ors", () {
+        _expectToString('a || b || c || d');
+        _expectToString('((a || b) || c) || d', 'a || b || c || d');
+      });
+
+      test('parenthesizes ands',
+          () => _expectToString('a && b || c && d', '(a && b) || (c && d)'));
+
+      test('parenthesizes conditions',
+          () => _expectToString('(a ? b : c) || (e ? f : g)'));
+    });
+
+    group('and', () {
+      test("doesn't parenthesize variables", () => _expectToString('a && b'));
+      test("doesn't parenthesize nots", () => _expectToString('!a && !b'));
+
+      test(
+          'parenthesizes ors',
+          () =>
+              _expectToString('(a || b) && (c || d)', '(a || b) && (c || d)'));
+
+      test("doesn't parenthesize ands", () {
+        _expectToString('a && b && c && d');
+        _expectToString('((a && b) && c) && d', 'a && b && c && d');
+      });
+
+      test('parenthesizes conditions',
+          () => _expectToString('(a ? b : c) && (e ? f : g)'));
+    });
+
+    group('conditional', () {
+      test(
+          "doesn't parenthesize variables", () => _expectToString('a ? b : c'));
+
+      test("doesn't parenthesize nots", () => _expectToString('!a ? !b : !c'));
+
+      test("doesn't parenthesize ors",
+          () => _expectToString('a || b ? c || d : e || f'));
+
+      test("doesn't parenthesize ands",
+          () => _expectToString('a && b ? c && d : e && f'));
+
+      test('parenthesizes non-trailing conditions', () {
+        _expectToString('(a ? b : c) ? (e ? f : g) : h ? i : j');
+        _expectToString('(a ? b : c) ? (e ? f : g) : (h ? i : j)',
+            '(a ? b : c) ? (e ? f : g) : h ? i : j');
+      });
+    });
+  });
+}
+
+void _expectToString(String selector, [String? result]) {
+  result ??= selector;
+  expect(_toString(selector), equals(result),
+      reason: 'Expected toString of "$selector" to be "$result".');
+}
+
+String _toString(String selector) => BooleanSelector.parse(selector).toString();
diff --git a/pkgs/boolean_selector/test/validate_test.dart b/pkgs/boolean_selector/test/validate_test.dart
new file mode 100644
index 0000000..ec5b7eb
--- /dev/null
+++ b/pkgs/boolean_selector/test/validate_test.dart
@@ -0,0 +1,20 @@
+// Copyright (c) 2016, 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.
+
+import 'package:boolean_selector/boolean_selector.dart';
+import 'package:test/test.dart';
+
+var _selector = BooleanSelector.parse('foo && bar && baz');
+
+void main() {
+  test('throws if any variables are undefined', () {
+    expect(() => _selector.validate((variable) => variable == 'bar'),
+        throwsFormatException);
+  });
+
+  test("doesn't throw if all variables are defined", () {
+    // Should not throw.
+    _selector.validate((variable) => true);
+  });
+}
diff --git a/pkgs/boolean_selector/test/variables_test.dart b/pkgs/boolean_selector/test/variables_test.dart
new file mode 100644
index 0000000..5331409
--- /dev/null
+++ b/pkgs/boolean_selector/test/variables_test.dart
@@ -0,0 +1,43 @@
+// Copyright (c) 2016, 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.
+
+import 'package:boolean_selector/boolean_selector.dart';
+import 'package:test/test.dart';
+
+void main() {
+  test('a variable reports itself', () {
+    expect(BooleanSelector.parse('foo').variables, equals(['foo']));
+  });
+
+  test('a negation reports its contents', () {
+    expect(BooleanSelector.parse('!foo').variables, equals(['foo']));
+  });
+
+  test('a parenthesized expression reports its contents', () {
+    expect(BooleanSelector.parse('(foo)').variables, equals(['foo']));
+  });
+
+  test('an or reports its contents', () {
+    expect(
+        BooleanSelector.parse('foo || bar').variables, equals(['foo', 'bar']));
+  });
+
+  test('an and reports its contents', () {
+    expect(
+        BooleanSelector.parse('foo && bar').variables, equals(['foo', 'bar']));
+  });
+
+  test('a conditional reports its contents', () {
+    expect(BooleanSelector.parse('foo ? bar : baz').variables,
+        equals(['foo', 'bar', 'baz']));
+  });
+
+  test('BooleanSelector.all reports no variables', () {
+    expect(BooleanSelector.all.variables, isEmpty);
+  });
+
+  test('BooleanSelector.none reports no variables', () {
+    expect(BooleanSelector.none.variables, isEmpty);
+  });
+}
diff --git a/pkgs/cli_config/.gitignore b/pkgs/cli_config/.gitignore
new file mode 100644
index 0000000..58e48f3
--- /dev/null
+++ b/pkgs/cli_config/.gitignore
@@ -0,0 +1,9 @@
+# https://dart.dev/guides/libraries/private-files
+# Created by `dart pub`
+.dart_tool/
+
+# Avoid committing pubspec.lock for library packages; see
+# https://dart.dev/guides/libraries/private-files#pubspeclock.
+pubspec.lock
+
+coverage/
diff --git a/pkgs/cli_config/CHANGELOG.md b/pkgs/cli_config/CHANGELOG.md
new file mode 100644
index 0000000..55fcd2d
--- /dev/null
+++ b/pkgs/cli_config/CHANGELOG.md
@@ -0,0 +1,22 @@
+## 0.2.1-wip
+
+- Require Dart 3.4.
+
+## 0.2.0
+
+- **Breaking Change** Rename `Config.fromArgs` to `Config.fromArguments`.
+- Add `Config.fromArgumentsSync`.
+
+## 0.1.2
+
+- Add usage docs to the readme.
+- Require Dart 3.0.
+
+## 0.1.1
+
+- Support non-String map keys in YAML configuration files.
+- Support null values in YAML configuration files.
+
+## 0.1.0
+
+- Initial version.
diff --git a/pkgs/cli_config/LICENSE b/pkgs/cli_config/LICENSE
new file mode 100644
index 0000000..ac90031
--- /dev/null
+++ b/pkgs/cli_config/LICENSE
@@ -0,0 +1,27 @@
+Copyright 2023, the Dart project authors.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+    * Redistributions of source code must retain the above copyright
+      notice, this list of conditions and the following disclaimer.
+    * Redistributions in binary form must reproduce the above
+      copyright notice, this list of conditions and the following
+      disclaimer in the documentation and/or other materials provided
+      with the distribution.
+    * Neither the name of Google LLC nor the names of its
+      contributors may be used to endorse or promote products derived
+      from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
\ No newline at end of file
diff --git a/pkgs/cli_config/README.md b/pkgs/cli_config/README.md
new file mode 100644
index 0000000..54c08e4
--- /dev/null
+++ b/pkgs/cli_config/README.md
@@ -0,0 +1,71 @@
+[![package:cli_config](https://github.com/dart-lang/tools/actions/workflows/cli_config.yml/badge.svg)](https://github.com/dart-lang/tools/actions/workflows/cli_config.yml)
+[![Coverage Status](https://coveralls.io/repos/github/dart-lang/tools/badge.svg?branch=main)](https://coveralls.io/github/dart-lang/tools?branch=main)
+[![pub package](https://img.shields.io/pub/v/cli_config.svg)](https://pub.dev/packages/cli_config)
+[![package publisher](https://img.shields.io/pub/publisher/cli_config.svg)](https://pub.dev/packages/cli_config/publisher)
+
+A library to take config values from configuration files, CLI arguments, and
+environment variables.
+
+## Usage
+
+Configuration can be provided from commandline arguments, environment variables,
+and configuration files. This library makes these accessible via a uniform API.
+
+Configuration can be provided via the three sources as follows:
+1. commandline argument defines as `-Dsome_key=some_value`,
+2. environment variables as `SOME_KEY=some_value`, and
+3. config files as JSON or YAML as `{'some_key': 'some_value'}`.
+
+The default lookup behavior is that commandline argument defines take precedence
+over environment variables, which take precedence over the configuration file.
+
+If a single value is requested from this configuration, the first source that
+can provide the value will provide it. For example
+`config.string('some_key')` with `{'some_key': 'file_value'}` in the config file
+and `-Dsome_key=cli_value` as commandline argument returns
+`'cli_value'`. The implication is that you can not remove keys from the
+configuration file, only overwrite or append them.
+
+If a list value is requested from this configuration, the values provided by the
+various sources can be combined or not. For example
+`config.optionalStringList('some_key', combineAllConfigs: true)` returns
+`['cli_value', 'file_value']`.
+
+The config is hierarchical in nature, using `.` as the hierarchy separator for
+lookup and commandline defines. The hierarchy should be materialized in the JSON
+or YAML configuration file. For environment variables `__` is used as hierarchy
+separator.
+
+Hierarchical configuration can be provided via the three sources as follows:
+1. commandline argument defines as `-Dsome_key.some_nested_key=some_value`,
+2. environment variables as `SOME_KEY__SOME_NESTED_KEY=some_value`, and
+3. config files as JSON or YAML as
+   ```yaml
+   some_key:
+     some_nested_key:
+       some_value
+   ```
+
+The config is opinionated on the format of the keys in the sources.
+* Command-line argument keys should be lower-cased alphanumeric
+  characters or underscores, with `.` for hierarchy.
+* Environment variables keys should be upper-cased alphanumeric
+   characters or underscores, with `__` for hierarchy.
+* Config files keys should be lower-cased alphanumeric
+  characters or underscores.
+
+In the API they are made available lower-cased and with underscores, and
+`.` as hierarchy separator.
+
+## Example usage
+
+This example creates a configuration which first looks for command-line defines
+in the `arguments` list then looks in `Platform.environment`, then looks in any
+local configuration file.
+
+```dart
+final config = await Config.fromArguments(arguments: arguments);
+final pathValue =
+    config.optionalPath('my_path', resolveUri: true, mustExist: false);
+print(pathValue?.toFilePath());
+```
diff --git a/pkgs/cli_config/analysis_options.yaml b/pkgs/cli_config/analysis_options.yaml
new file mode 100644
index 0000000..dd3dcda
--- /dev/null
+++ b/pkgs/cli_config/analysis_options.yaml
@@ -0,0 +1,12 @@
+include: package:dart_flutter_team_lints/analysis_options.yaml
+
+analyzer:
+  language:
+    strict-raw-types: true
+
+linter:
+  rules:
+    - prefer_const_declarations
+    - prefer_expression_function_bodies
+    - prefer_final_in_for_each
+    - prefer_final_locals
diff --git a/pkgs/cli_config/example/bin/cli_config_example.dart b/pkgs/cli_config/example/bin/cli_config_example.dart
new file mode 100644
index 0000000..1256bd7
--- /dev/null
+++ b/pkgs/cli_config/example/bin/cli_config_example.dart
@@ -0,0 +1,12 @@
+// Copyright (c) 2023, 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.
+
+import 'package:cli_config/cli_config.dart';
+
+Future<void> main(List<String> args) async {
+  final config = await Config.fromArguments(arguments: args);
+  final myPath =
+      config.optionalPath('my_path', resolveUri: true, mustExist: false);
+  print(myPath?.toFilePath());
+}
diff --git a/pkgs/cli_config/example/pubspec.yaml b/pkgs/cli_config/example/pubspec.yaml
new file mode 100644
index 0000000..cec900a
--- /dev/null
+++ b/pkgs/cli_config/example/pubspec.yaml
@@ -0,0 +1,11 @@
+name: cli_config_example
+description: An example for cli_config.
+
+publish_to: none
+
+environment:
+  sdk: ">=2.19.3 <4.0.0"
+
+dependencies:
+  cli_config:
+    path: ../
diff --git a/pkgs/cli_config/lib/cli_config.dart b/pkgs/cli_config/lib/cli_config.dart
new file mode 100644
index 0000000..51df312
--- /dev/null
+++ b/pkgs/cli_config/lib/cli_config.dart
@@ -0,0 +1,9 @@
+// Copyright (c) 2023, 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.
+
+/// A library to take config values from configuration files, CLI arguments,
+/// and environment variables.
+library;
+
+export 'src/config.dart';
diff --git a/pkgs/cli_config/lib/src/cli_parser.dart b/pkgs/cli_config/lib/src/cli_parser.dart
new file mode 100644
index 0000000..9396a7a
--- /dev/null
+++ b/pkgs/cli_config/lib/src/cli_parser.dart
@@ -0,0 +1,53 @@
+// Copyright (c) 2023, 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.
+
+import 'package:args/args.dart';
+
+class CliParser {
+  final ArgParser parser = () {
+    final parser = ArgParser();
+    parser.addFlag(
+      'help',
+      abbr: 'h',
+      help: 'Show this help.',
+    );
+    parser.addMultiOption(
+      'define',
+      abbr: 'D',
+      help: '''Define or override a config property from command line.
+The same option can be passed multiple times.
+Keys should only contain lower-case alphanumeric characters, underscores,
+and '.'s''',
+    );
+    parser.addOption(
+      'config',
+      abbr: 'c',
+      help: '''Path to JSON or YAML config file.
+Keys should only contain lower-case alphanumeric characters, and underscores.
+Hierarchies should be maps.''',
+    );
+    return parser;
+  }();
+
+  ArgResults parse(List<String> args) => parser.parse(args);
+}
+
+class DefinesParser {
+  static final _defineRegex = RegExp('([a-z_.]+)=(.+)');
+
+  Map<String, List<String>> parse(List<String> args) {
+    final defines = <String, List<String>>{};
+    for (final arg in args) {
+      final match = _defineRegex.matchAsPrefix(arg);
+      if (match == null || match.group(0) != arg) {
+        throw FormatException("Define '$arg' does not match expected pattern "
+            "'${_defineRegex.pattern}'.");
+      }
+      final key = match.group(1)!;
+      final value = match.group(2)!;
+      defines[key] = (defines[key] ?? [])..add(value);
+    }
+    return defines;
+  }
+}
diff --git a/pkgs/cli_config/lib/src/cli_source.dart b/pkgs/cli_config/lib/src/cli_source.dart
new file mode 100644
index 0000000..20e662c
--- /dev/null
+++ b/pkgs/cli_config/lib/src/cli_source.dart
@@ -0,0 +1,95 @@
+// Copyright (c) 2023, 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.
+
+import 'config.dart';
+import 'source.dart';
+
+class CliSource extends Source {
+  /// Configuration options passed in via CLI arguments.
+  ///
+  /// Options can be passed multiple times, so the values here are a list.
+  ///
+  /// Stored as a flat non-hierarchical structure, keys contain `.`.
+  final Map<String, List<String>> _cli;
+
+  /// If provided, used to resolve paths within [_cli].
+  ///
+  /// Typically the current working directory at application start.
+  @override
+  final Uri? baseUri;
+
+  CliSource(this._cli, this.baseUri);
+
+  @override
+  String? optionalString(String key) {
+    final value = _cli[key];
+    if (value == null) {
+      return null;
+    }
+    if (value.length > 1) {
+      throw FormatException(
+          "More than one value was passed for '$key' in the CLI defines."
+          ' Values passed: $value');
+    }
+    return value.single;
+  }
+
+  @override
+  List<String>? optionalStringList(
+    String key, {
+    String? splitPattern,
+  }) {
+    final cliValue = _cli[key];
+    if (cliValue == null) {
+      return null;
+    }
+    if (splitPattern != null) {
+      return [for (final value in cliValue) ...value.split(splitPattern)];
+    }
+    return cliValue;
+  }
+
+  @override
+  bool? optionalBool(String key) {
+    final stringValue = optionalString(key);
+    if (stringValue != null) {
+      Source.throwIfUnexpectedValue(key, stringValue, Config.boolStrings.keys);
+      return Config.boolStrings[stringValue]!;
+    }
+    return null;
+  }
+
+  @override
+  int? optionalInt(String key) {
+    final stringValue = optionalString(key);
+    if (stringValue != null) {
+      try {
+        return int.parse(stringValue);
+      } on FormatException catch (e) {
+        throw FormatException(
+            "Unexpected value '$stringValue' for key '$key'. Expected an int."
+            ' ${e.message}');
+      }
+    }
+    return null;
+  }
+
+  @override
+  double? optionalDouble(String key) {
+    final stringValue = optionalString(key);
+    if (stringValue != null) {
+      try {
+        return double.parse(stringValue);
+      } on FormatException catch (e) {
+        throw FormatException(
+            "Unexpected value '$stringValue' for key '$key'. Expected a double."
+            ' ${e.message}');
+      }
+    }
+    return null;
+  }
+
+  @override
+  String toString() => 'CliSource($_cli)';
+}
diff --git a/pkgs/cli_config/lib/src/config.dart b/pkgs/cli_config/lib/src/config.dart
new file mode 100644
index 0000000..85e2c0c
--- /dev/null
+++ b/pkgs/cli_config/lib/src/config.dart
@@ -0,0 +1,650 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:core' as core show bool, double, int;
+import 'dart:core' hide bool, double, int;
+import 'dart:io';
+
+import 'cli_parser.dart';
+import 'cli_source.dart';
+import 'environment_parser.dart';
+import 'environment_source.dart';
+import 'file_parser.dart';
+import 'file_source.dart';
+import 'source.dart';
+
+/// A hierarchical configuration.
+///
+/// Configuration can be provided from three sources: commandline arguments,
+/// environment variables and configuration files. This configuration makes
+/// these accessible via a uniform API.
+///
+/// Configuration can be provided via the three sources as follows:
+/// 1. commandline argument defines as `-Dsome_key=some_value`,
+/// 2. environment variables as `SOME_KEY=some_value`, and
+/// 3. config files as JSON or YAML as `{'some_key': 'some_value'}`.
+///
+/// The default lookup behavior is that commandline argument defines take
+/// precedence over environment variables, which take precedence over the
+/// configuration file.
+///
+/// If a single value is requested from this configuration, the first source
+/// that can provide the value will provide it. For example
+/// `config.string('some_key')` with `{'some_key': 'file_value'}` in the
+/// config file and `-Dsome_key=cli_value` as commandline argument returns
+/// `'cli_value'`. The implication is that you can not remove keys from the
+/// configuration file, only overwrite or append them.
+///
+/// If a list value is requested from this configuration, the values provided
+/// by the various sources can be combined or not. For example
+/// `config.optionalStringList('some_key', combineAllConfigs: true)` returns
+/// `['cli_value', 'file_value']`.
+///
+/// The config is hierarchical in nature, using `.` as the hierarchy separator
+/// for lookup and commandline defines. The hierarchy should be materialized in
+/// the JSON or YAML configuration file. For environment variables `__` is used
+/// as hierarchy separator.
+///
+/// Hierarchical configuration can be provided via the three sources as follows:
+/// 1. commandline argument defines as `-Dsome_key.some_nested_key=some_value`,
+/// 2. environment variables as `SOME_KEY__SOME_NESTED_KEY=some_value`, and
+/// 3. config files as JSON or YAML as
+///    ```yaml
+///    some_key:
+///      some_nested_key:
+///        some_value
+///    ```
+///
+/// The config is opinionated on the format of the keys in the sources.
+/// * Command-line argument keys should be lower-cased alphanumeric
+///   characters or underscores, with `.` for hierarchy.
+/// * Environment variables keys should be upper-cased alphanumeric
+///    characters or underscores, with `__` for hierarchy.
+/// * Config files keys should be lower-cased alphanumeric
+///   characters or underscores.
+///
+/// In the API they are made available lower-cased and with underscores, and
+/// `.` as hierarchy separator.
+class Config {
+  final CliSource _cliSource;
+  final EnvironmentSource _environmentSource;
+  final FileSource _fileSource;
+
+  /// Config sources, ordered by precedence.
+  late final _sources = [_cliSource, _environmentSource, _fileSource];
+
+  Config._(
+    this._cliSource,
+    this._environmentSource,
+    this._fileSource,
+  );
+
+  /// Constructs a config by parsing the three sources.
+  ///
+  /// If provided, [commandLineDefines] must be a list of `<key>=<value>`.
+  ///
+  /// If provided, [workingDirectory] is used to resolves paths inside
+  /// [commandLineDefines].
+  ///
+  /// If provided, [environment] must be a map containing environment variables.
+  ///
+  /// If provided, [fileParsed] must be valid parsed YSON or YAML (maps, lists,
+  /// strings, integers, and booleans).
+  ///
+  /// If provided [fileSourceUri] is used to resolve paths inside
+  /// [fileParsed] and to provide better error messages on parsing the
+  /// configuration file.
+  factory Config({
+    List<String> commandLineDefines = const [],
+    Uri? workingDirectory,
+    Map<String, String> environment = const {},
+    Map<String, dynamic> fileParsed = const {},
+    Uri? fileSourceUri,
+  }) {
+    // Parse config file.
+    final fileConfig = FileParser().parseToplevelMap(fileParsed);
+
+    // Parse CLI argument defines.
+    final cliConfig = DefinesParser().parse(commandLineDefines);
+
+    // Parse environment.
+    final environmentConfig = EnvironmentParser().parse(environment);
+
+    return Config._(
+      CliSource(cliConfig, workingDirectory?.normalizePath()),
+      EnvironmentSource(environmentConfig),
+      FileSource(fileConfig, fileSourceUri?.normalizePath()),
+    );
+  }
+
+  /// Constructs a config by parsing the three sources.
+  ///
+  /// If provided, [commandLineDefines] must be a list of `<key>=<value>`.
+  ///
+  /// If provided, [workingDirectory] is used to resolves paths inside
+  /// [commandLineDefines].
+  ///
+  /// If provided, [environment] must be a map containing environment variables.
+  ///
+  /// If provided, [fileContents] must be valid JSON or YAML.
+  ///
+  /// If provided [fileSourceUri] is used to resolve paths inside
+  /// [fileContents] and to provide better error messages on parsing the
+  /// configuration file.
+  factory Config.fromConfigFileContents({
+    List<String> commandLineDefines = const [],
+    Uri? workingDirectory,
+    Map<String, String> environment = const {},
+    String? fileContents,
+    Uri? fileSourceUri,
+  }) {
+    // Parse config file.
+    final Map<String, dynamic> fileConfig;
+    if (fileContents != null) {
+      fileConfig = FileParser().parse(
+        fileContents,
+        sourceUrl: fileSourceUri,
+      );
+    } else {
+      fileConfig = {};
+    }
+
+    // Parse CLI argument defines.
+    final cliConfig = DefinesParser().parse(commandLineDefines);
+
+    // Parse environment.
+    final environmentConfig = EnvironmentParser().parse(environment);
+
+    return Config._(
+      CliSource(cliConfig, workingDirectory),
+      EnvironmentSource(environmentConfig),
+      FileSource(fileConfig, fileSourceUri),
+    );
+  }
+
+  /// Constructs a config by parsing CLI arguments and loading the config file.
+  ///
+  /// The [arguments] must be commandline arguments.
+  ///
+  /// If provided, [environment] must be a map containing environment variables.
+  /// If not provided, [environment] defaults to [Platform.environment].
+  ///
+  /// If provided, [workingDirectory] is used to resolves paths inside
+  /// [environment].
+  /// If not provided, [workingDirectory] defaults to [Directory.current].
+  ///
+  /// This async constructor is intended to be used directly in CLI files.
+  static Future<Config> fromArguments({
+    required List<String> arguments,
+    Map<String, String>? environment,
+    Uri? workingDirectory,
+  }) async {
+    final results = CliParser().parse(arguments);
+
+    // Load config file.
+    final configFile = results['config'] as String?;
+    String? fileContents;
+    Uri? fileSourceUri;
+    if (configFile != null) {
+      fileContents = await File(configFile).readAsString();
+      fileSourceUri = Uri.file(configFile);
+    }
+
+    return Config.fromConfigFileContents(
+      commandLineDefines: results['define'] as List<String>,
+      workingDirectory: workingDirectory ?? Directory.current.uri,
+      environment: environment ?? Platform.environment,
+      fileContents: fileContents,
+      fileSourceUri: fileSourceUri,
+    );
+  }
+
+  /// Constructs a config by parsing CLI arguments and loading the config file.
+  ///
+  /// The [arguments] must be commandline arguments.
+  ///
+  /// If provided, [environment] must be a map containing environment variables.
+  /// If not provided, [environment] defaults to [Platform.environment].
+  ///
+  /// If provided, [workingDirectory] is used to resolves paths inside
+  /// [environment].
+  /// If not provided, [workingDirectory] defaults to [Directory.current].
+  ///
+  /// This synchronous constructor is intended to be used directly in CLI files.
+  static Config fromArgumentsSync({
+    required List<String> arguments,
+    Map<String, String>? environment,
+    Uri? workingDirectory,
+  }) {
+    final results = CliParser().parse(arguments);
+
+    // Load config file.
+    final configFile = results['config'] as String?;
+    String? fileContents;
+    Uri? fileSourceUri;
+    if (configFile != null) {
+      fileContents = File(configFile).readAsStringSync();
+      fileSourceUri = Uri.file(configFile);
+    }
+
+    return Config.fromConfigFileContents(
+      commandLineDefines: results['define'] as List<String>,
+      workingDirectory: workingDirectory ?? Directory.current.uri,
+      environment: environment ?? Platform.environment,
+      fileContents: fileContents,
+      fileSourceUri: fileSourceUri,
+    );
+  }
+
+  /// Lookup a string value in this config.
+  ///
+  /// First tries CLI argument defines, then environment variables, and
+  /// finally the config file.
+  ///
+  /// Throws if one of the configs does not contain the expected value type.
+  ///
+  /// If [validValues] is provided, throws if an unxpected value is provided.
+  String string(String key, {Iterable<String>? validValues}) {
+    final value = optionalString(key, validValues: validValues);
+    _throwIfNull(key, value);
+    return value!;
+  }
+
+  /// Lookup an optional string value in this config.
+  ///
+  /// First tries CLI argument defines, then environment variables, and
+  /// finally the config file.
+  ///
+  /// If [validValues] is provided, throws if an unxpected value is provided.
+  String? optionalString(String key, {Iterable<String>? validValues}) {
+    String? value;
+    for (final source in _sources) {
+      value ??= source.optionalString(key);
+    }
+    if (value != null && validValues != null) {
+      Source.throwIfUnexpectedValue(key, value, validValues);
+    }
+    return value;
+  }
+
+  /// Lookup an optional string list in this config.
+  ///
+  /// If none of the sources provide a list, lookup will fail.
+  /// If an empty list is provided by one of the sources, lookup wil succeed.
+  ///
+  /// First tries CLI argument defines, then environment variables, and
+  /// finally the config file.
+  ///
+  /// If [combineAllConfigs] combines results from cli, environment, and
+  /// config file. Otherwise, precedence rules apply.
+  ///
+  /// If provided, [splitCliPattern] splits cli defines.
+  /// For example: `-Dfoo=bar;baz` can be split on `;`.
+  /// If not provided, a list can still be provided with multiple cli defines.
+  /// For example: `-Dfoo=bar -Dfoo=baz`.
+  ///
+  /// If provided, [splitEnvironmentPattern] splits environment values.
+  List<String> stringList(
+    String key, {
+    core.bool combineAllConfigs = true,
+    String? splitCliPattern,
+    String? splitEnvironmentPattern,
+  }) {
+    final value = optionalStringList(
+      key,
+      combineAllConfigs: combineAllConfigs,
+      splitCliPattern: splitCliPattern,
+      splitEnvironmentPattern: splitEnvironmentPattern,
+    );
+    _throwIfNull(key, value);
+    return value!;
+  }
+
+  /// Lookup an optional string list in this config.
+  ///
+  /// First tries CLI argument defines, then environment variables, and
+  /// finally the config file.
+  ///
+  /// If [combineAllConfigs] combines results from cli, environment, and
+  /// config file. Otherwise, precedence rules apply.
+  ///
+  /// If provided, [splitCliPattern] splits cli defines.
+  /// For example: `-Dfoo=bar;baz` can be split on `;`.
+  /// If not provided, a list can still be provided with multiple cli defines.
+  /// For example: `-Dfoo=bar -Dfoo=baz`.
+  ///
+  /// If provided, [splitEnvironmentPattern] splits environment values.
+  List<String>? optionalStringList(
+    String key, {
+    core.bool combineAllConfigs = true,
+    String? splitCliPattern,
+    String? splitEnvironmentPattern,
+  }) {
+    List<String>? result;
+    for (final entry in {
+      _cliSource: splitCliPattern,
+      _environmentSource: splitEnvironmentPattern,
+      _fileSource: null
+    }.entries) {
+      final source = entry.key;
+      final splitPattern = entry.value;
+      final value = source.optionalStringList(key, splitPattern: splitPattern);
+      if (value != null) {
+        if (combineAllConfigs) {
+          (result ??= []).addAll(value);
+        } else {
+          return value;
+        }
+      }
+    }
+    return result;
+  }
+
+  static const boolStrings = {
+    '0': false,
+    '1': true,
+    'false': false,
+    'FALSE': false,
+    'no': false,
+    'NO': false,
+    'true': true,
+    'TRUE': true,
+    'yes': true,
+    'YES': true,
+  };
+
+  /// Lookup a boolean value in this config.
+  ///
+  /// First tries CLI argument defines, then environment variables, and
+  /// finally the config file.
+  ///
+  /// For cli defines and environment variables, the value must be one of
+  /// [boolStrings].
+  /// For the config file, it must be a boolean.
+  ///
+  /// Throws if one of the configs does not contain the expected value type.
+  core.bool bool(String key) {
+    final value = optionalBool(key);
+    _throwIfNull(key, value);
+    return value!;
+  }
+
+  /// Lookup an optional boolean value in this config.
+  ///
+  /// First tries CLI argument defines, then environment variables, and
+  /// finally the config file.
+  ///
+  /// For cli defines and environment variables, the value must be one of
+  /// [boolStrings].
+  /// For the config file, it must be a boolean or null.
+  core.bool? optionalBool(String key) {
+    core.bool? value;
+    for (final source in _sources) {
+      value ??= source.optionalBool(key);
+    }
+    return value;
+  }
+
+  /// Lookup an integer value in this config.
+  ///
+  /// First tries CLI argument defines, then environment variables, and
+  /// finally the config file.
+  ///
+  /// For cli defines and environment variables, the value must be parseble
+  /// by [core.int.parse].
+  /// For the config file, it must be an integer.
+  core.int int(String key) {
+    final value = optionalInt(key);
+    _throwIfNull(key, value);
+    return value!;
+  }
+
+  /// Lookup an optional integer value in this config.
+  ///
+  /// First tries CLI argument defines, then environment variables, and
+  /// finally the config file.
+  ///
+  /// For cli defines and environment variables, the value must be parseble
+  /// by [core.int.parse].
+  /// For the config file, it must be an integer or null.
+  core.int? optionalInt(String key) {
+    core.int? value;
+    for (final source in _sources) {
+      value ??= source.optionalInt(key);
+    }
+    return value;
+  }
+
+  /// Lookup an double value in this config.
+  ///
+  /// First tries CLI argument defines, then environment variables, and
+  /// finally the config file.
+  ///
+  /// For cli defines and environment variables, the value must be parseble
+  /// by [core.double.parse].
+  /// For the config file, it must be an double.
+  core.double double(String key) {
+    final value = optionalDouble(key);
+    _throwIfNull(key, value);
+    return value!;
+  }
+
+  /// Lookup an optional double value in this config.
+  ///
+  /// First tries CLI argument defines, then environment variables, and
+  /// finally the config file.
+  ///
+  /// For cli defines and environment variables, the value must be parseble
+  /// by [core.double.parse].
+  /// For the config file, it must be an double or null.
+  core.double? optionalDouble(String key) {
+    core.double? value;
+    for (final source in _sources) {
+      value ??= source.optionalDouble(key);
+    }
+    return value;
+  }
+
+  /// Lookup a path in this config.
+  ///
+  /// First tries CLI argument defines, then environment variables, and
+  /// finally the config file.
+  ///
+  /// Throws if one of the configs does not contain the expected value type.
+  ///
+  /// If [resolveUri], resolves the paths in a source relative to the base
+  /// uri of that source. The base uri for the config file is the path of the
+  /// file. The base uri for environment values is the current working
+  /// directory.
+  ///
+  /// If [mustExist], throws if the path doesn't resolve to a file or directory
+  /// on the file system.
+  ///
+  /// Throws if one of the configs does not contain the expected value type.
+  Uri path(
+    String key, {
+    core.bool resolveUri = true,
+    core.bool mustExist = false,
+  }) {
+    final value =
+        optionalPath(key, resolveUri: resolveUri, mustExist: mustExist);
+    _throwIfNull(key, value);
+    return value!;
+  }
+
+  /// Lookup an optional path in this config.
+  ///
+  /// First tries CLI argument defines, then environment variables, and
+  /// finally the config file.
+  ///
+  /// Throws if one of the configs does not contain the expected value type.
+  ///
+  /// If [resolveUri], resolves the paths in a source relative to the base
+  /// uri of that source. The base uri for the config file is the path of the
+  /// file. The base uri for environment values is the current working
+  /// directory.
+  ///
+  /// If [mustExist], throws if the path doesn't resolve to a file or directory
+  /// on the file system.
+  Uri? optionalPath(
+    String key, {
+    core.bool resolveUri = true,
+    core.bool mustExist = false,
+  }) {
+    for (final source in _sources) {
+      final path = source.optionalString(key);
+      if (path != null) {
+        final value = _pathToUri(
+          path,
+          resolveUri: resolveUri,
+          baseUri: source.baseUri,
+        );
+        if (mustExist) {
+          _throwIfNotExists(key, value);
+        }
+        return value;
+      }
+    }
+    return null;
+  }
+
+  Uri _pathToUri(
+    String path, {
+    required core.bool resolveUri,
+    required Uri? baseUri,
+  }) {
+    final uri = Source.fileSystemPathToUri(path);
+    if (resolveUri && baseUri != null) {
+      return baseUri.resolveUri(uri);
+    }
+    return uri;
+  }
+
+  /// Lookup a list of paths in this config.
+  ///
+  /// If none of the sources provide a path, lookup will fail.
+  /// If an empty list is provided by one of the sources, lookup wil succeed.
+  ///
+  /// If [combineAllConfigs] combines results from cli, environment, and
+  /// config file. Otherwise, precedence rules apply.
+  ///
+  /// If provided, [splitCliPattern] splits cli defines.
+  ///
+  /// If provided, [splitEnvironmentPattern] splits environment values.
+  ///
+  /// If [resolveUri], resolves the paths in a source relative to the base
+  /// uri of that source. The base uri for the config file is the path of the
+  /// file. The base uri for environment values is the current working
+  /// directory.
+  List<Uri> pathList(
+    String key, {
+    core.bool combineAllConfigs = true,
+    String? splitCliPattern,
+    String? splitEnvironmentPattern,
+    core.bool resolveUri = true,
+  }) {
+    final value = optionalPathList(
+      key,
+      combineAllConfigs: combineAllConfigs,
+      splitCliPattern: splitCliPattern,
+      splitEnvironmentPattern: splitEnvironmentPattern,
+      resolveUri: resolveUri,
+    );
+    _throwIfNull(key, value);
+    return value!;
+  }
+
+  /// Lookup an optional list of paths in this config.
+  ///
+  /// If [combineAllConfigs] combines results from cli, environment, and
+  /// config file. Otherwise, precedence rules apply.
+  ///
+  /// If provided, [splitCliPattern] splits cli defines.
+  ///
+  /// If provided, [splitEnvironmentPattern] splits environment values.
+  ///
+  /// If [resolveUri], resolves the paths in a source relative to the base
+  /// uri of that source. The base uri for the config file is the path of the
+  /// file. The base uri for environment values is the current working
+  /// directory.
+  List<Uri>? optionalPathList(
+    String key, {
+    core.bool combineAllConfigs = true,
+    String? splitCliPattern,
+    String? splitEnvironmentPattern,
+    core.bool resolveUri = true,
+  }) {
+    List<Uri>? result;
+    for (final entry in {
+      _cliSource: splitCliPattern,
+      _environmentSource: splitEnvironmentPattern,
+      _fileSource: null
+    }.entries) {
+      final source = entry.key;
+      final splitPattern = entry.value;
+      final paths = source.optionalStringList(
+        key,
+        splitPattern: splitPattern,
+      );
+      if (paths != null) {
+        final value = [
+          for (final path in paths)
+            _pathToUri(
+              path,
+              resolveUri: resolveUri,
+              baseUri: source.baseUri,
+            )
+        ];
+        if (combineAllConfigs) {
+          (result ??= []).addAll(value);
+        } else {
+          return value;
+        }
+      }
+    }
+    return result;
+  }
+
+  /// Lookup a value of type [T] in this configuration.
+  ///
+  /// Does not support specialized options such as `splitPattern`. One must
+  /// use the specialized methods such as [optionalStringList] for that.
+  ///
+  /// If sources cannot lookup type [T], they return null.
+  T valueOf<T>(String key) {
+    T? value;
+    for (final source in _sources) {
+      value ??= source.optionalValueOf<T>(key);
+    }
+    if (null is! T) {
+      _throwIfNull(key, value);
+    }
+    return value as T;
+  }
+
+  void _throwIfNull(String key, Object? value) {
+    if (value == null) {
+      throw FormatException('No value was provided for required key: $key');
+    }
+  }
+
+  void _throwIfNotExists(String key, Uri value) {
+    final fileSystemEntity = value.fileSystemEntity;
+    if (!fileSystemEntity.existsSync()) {
+      throw FormatException("Path '$value' for key '$key' doesn't exist.");
+    }
+  }
+
+  @override
+  String toString() => 'Config($_sources)';
+}
+
+extension on Uri {
+  FileSystemEntity get fileSystemEntity {
+    if (path.endsWith(Platform.pathSeparator) || path.endsWith('/')) {
+      return Directory.fromUri(this);
+    }
+    return File.fromUri(this);
+  }
+}
diff --git a/pkgs/cli_config/lib/src/environment_parser.dart b/pkgs/cli_config/lib/src/environment_parser.dart
new file mode 100644
index 0000000..d91b8fa
--- /dev/null
+++ b/pkgs/cli_config/lib/src/environment_parser.dart
@@ -0,0 +1,19 @@
+// Copyright (c) 2023, 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.
+
+class EnvironmentParser {
+  /// Parses an environment key into an config key.
+  ///
+  /// Environment keys can only contain alphanumeric characters and underscores.
+  /// Treats `__` as hierarchy separator, and replaces it with `.`.
+  ///
+  /// Often, environment variables are uppercased.
+  /// Replaces all uppercase characters with lowercase characters.
+  String parseKey(String key) => key.replaceAll('__', '.').toLowerCase();
+
+  Map<String, String> parse(Map<String, String> environment) => {
+        for (final entry in environment.entries)
+          parseKey(entry.key): entry.value,
+      };
+}
diff --git a/pkgs/cli_config/lib/src/environment_source.dart b/pkgs/cli_config/lib/src/environment_source.dart
new file mode 100644
index 0000000..9cff18f
--- /dev/null
+++ b/pkgs/cli_config/lib/src/environment_source.dart
@@ -0,0 +1,86 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:io';
+
+import 'config.dart';
+import 'source.dart';
+
+class EnvironmentSource extends Source {
+  /// Configuration options passed in via the [Platform.environment].
+  ///
+  /// The keys have been transformed by `EnvironmentParser.parseKey`.
+  ///
+  /// Environment values are left intact.
+  ///
+  /// Stored as a flat non-hierarchical structure, keys contain `.`.
+  final Map<String, String> _environment;
+
+  EnvironmentSource(this._environment);
+
+  @override
+  String? optionalString(String key) => _environment[key];
+
+  @override
+  List<String>? optionalStringList(
+    String key, {
+    String? splitPattern,
+  }) {
+    final envValue = _environment[key];
+    if (envValue == null) {
+      return null;
+    }
+    if (splitPattern != null) {
+      return envValue.split(splitPattern);
+    }
+    return [envValue];
+  }
+
+  @override
+  bool? optionalBool(String key) {
+    final stringValue = optionalString(key);
+    if (stringValue != null) {
+      Source.throwIfUnexpectedValue(key, stringValue, Config.boolStrings.keys);
+      return Config.boolStrings[stringValue]!;
+    }
+    return null;
+  }
+
+  @override
+  int? optionalInt(String key) {
+    final stringValue = optionalString(key);
+    if (stringValue != null) {
+      try {
+        return int.parse(stringValue);
+      } on FormatException catch (e) {
+        throw FormatException(
+            "Unexpected value '$stringValue' for key '$key'. Expected an int."
+            ' ${e.message}');
+      }
+    }
+    return null;
+  }
+
+  @override
+  double? optionalDouble(String key) {
+    final stringValue = optionalString(key);
+    if (stringValue != null) {
+      try {
+        return double.parse(stringValue);
+      } on FormatException catch (e) {
+        throw FormatException(
+            "Unexpected value '$stringValue' for key '$key'. Expected a double."
+            ' ${e.message}');
+      }
+    }
+    return null;
+  }
+
+  @override
+  String toString() => 'EnvironmentSource($_environment)';
+
+  /// Environment path are not resolved.
+  @override
+  Uri? get baseUri => null;
+}
diff --git a/pkgs/cli_config/lib/src/file_parser.dart b/pkgs/cli_config/lib/src/file_parser.dart
new file mode 100644
index 0000000..2a647e5
--- /dev/null
+++ b/pkgs/cli_config/lib/src/file_parser.dart
@@ -0,0 +1,46 @@
+// Copyright (c) 2023, 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.
+
+import 'package:yaml/yaml.dart';
+
+class FileParser {
+  Map<String, Object?> parse(
+    String fileContents, {
+    Uri? sourceUrl,
+  }) {
+    final parsedYaml = loadYaml(
+      fileContents,
+      sourceUrl: sourceUrl,
+    );
+    if (parsedYaml is! Map) {
+      throw const FormatException(
+          'YAML config must be set of key value pairs.');
+    }
+    return parseToplevelMap(parsedYaml);
+  }
+
+  Map<String, Object?> parseToplevelMap(Map<dynamic, dynamic> input) {
+    final result = <String, Object?>{};
+    for (final entry in input.entries) {
+      final key = parseToplevelKey(entry.key);
+      final value = entry.value as Object?;
+      result[key] = value;
+    }
+    return result;
+  }
+
+  static final _keyRegex = RegExp('([a-z-_]+)');
+
+  String parseToplevelKey(Object? key) {
+    if (key is! String) {
+      throw FormatException("Key '$key' is not a String.");
+    }
+    final match = _keyRegex.matchAsPrefix(key);
+    if (match == null || match.group(0) != key) {
+      throw FormatException("Define '$key' does not match expected pattern "
+          "'${_keyRegex.pattern}'.");
+    }
+    return key.replaceAll('-', '_');
+  }
+}
diff --git a/pkgs/cli_config/lib/src/file_source.dart b/pkgs/cli_config/lib/src/file_source.dart
new file mode 100644
index 0000000..d0594c6
--- /dev/null
+++ b/pkgs/cli_config/lib/src/file_source.dart
@@ -0,0 +1,68 @@
+// Copyright (c) 2023, 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.
+
+import 'source.dart';
+
+class FileSource extends Source {
+  /// Configuration options passed in via a JSON or YAML configuration file.
+  ///
+  /// Stored as a partial hierarchical data structure. The values can be maps
+  /// in which subsequent parts of a key after a `.` can be resolved.
+  final Map<String, dynamic> _file;
+
+  /// If provided, used to resolve paths within [_file].
+  @override
+  final Uri? baseUri;
+
+  FileSource(this._file, this.baseUri);
+
+  @override
+  String? optionalString(String key) => optionalValueOf<String>(key);
+
+  @override
+  List<String>? optionalStringList(
+    String key, {
+    String? splitPattern,
+  }) {
+    assert(splitPattern == null);
+    return optionalValueOf<List<dynamic>>(key)?.cast<String>();
+  }
+
+  @override
+  bool? optionalBool(String key) => optionalValueOf<bool>(key);
+
+  @override
+  int? optionalInt(String key) => optionalValueOf<int>(key);
+
+  @override
+  double? optionalDouble(String key) => optionalValueOf<double>(key);
+
+  @override
+  T? optionalValueOf<T>(String key) {
+    Object? cursor = _file;
+    var current = '';
+    for (final keyPart in key.split('.')) {
+      if (cursor == null) {
+        return null;
+      }
+      if (cursor is! Map) {
+        throw FormatException(
+            "Unexpected value '$cursor' for key '$current' in config file. "
+            'Expected a Map.');
+      } else {
+        cursor = cursor[keyPart];
+      }
+      current += '.$keyPart';
+    }
+    if (cursor is! T?) {
+      throw FormatException(
+          "Unexpected value '$cursor' for key '$current' in config file. "
+          'Expected a $T.');
+    }
+    return cursor;
+  }
+
+  @override
+  String toString() => 'FileSource(file: $_file, fileUri: $baseUri)';
+}
diff --git a/pkgs/cli_config/lib/src/source.dart b/pkgs/cli_config/lib/src/source.dart
new file mode 100644
index 0000000..14c7965
--- /dev/null
+++ b/pkgs/cli_config/lib/src/source.dart
@@ -0,0 +1,65 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:io';
+
+abstract class Source {
+  /// If provided, the uri used for resolving paths.
+  Uri? get baseUri;
+
+  /// Lookup a nullable string value.
+  String? optionalString(String key);
+
+  /// Lookup a nullable string list.
+  ///
+  /// If provided, [splitPattern] splits config.
+  List<String>? optionalStringList(
+    String key, {
+    String? splitPattern,
+  });
+
+  /// Lookup an optional boolean value.
+  bool? optionalBool(String key);
+
+  /// Lookup an optional int value.
+  int? optionalInt(String key);
+
+  /// Lookup an optional int value.
+  double? optionalDouble(String key);
+
+  /// Lookup an optional value of type [T].
+  ///
+  /// Does not support specialized options such as `splitPattern`. One must
+  /// use the specialized methods such as [optionalStringList] for that.
+  ///
+  /// Returns `null` if the source cannot provide a value of type [T].
+  T? optionalValueOf<T>(String key) {
+    if (T == bool) {
+      return optionalBool(key) as T?;
+    }
+    if (T == String) {
+      return optionalString(key) as T?;
+    }
+    if (T == List<String>) {
+      return optionalStringList(key) as T?;
+    }
+    return null;
+  }
+
+  static void throwIfUnexpectedValue<T>(
+      String key, T value, Iterable<T> validValues) {
+    if (!validValues.contains(value)) {
+      throw FormatException(
+          "Unexpected value '$value' for key '$key'. Expected one of: "
+          "${validValues.map((e) => "'$e'").join(', ')}.");
+    }
+  }
+
+  static Uri fileSystemPathToUri(String path) {
+    if (path.endsWith(Platform.pathSeparator)) {
+      return Uri.directory(path);
+    }
+    return Uri.file(path);
+  }
+}
diff --git a/pkgs/cli_config/pubspec.yaml b/pkgs/cli_config/pubspec.yaml
new file mode 100644
index 0000000..e2b0721
--- /dev/null
+++ b/pkgs/cli_config/pubspec.yaml
@@ -0,0 +1,17 @@
+name: cli_config
+description: >-
+  A library to take config values from configuration files, CLI arguments, and
+  environment variables.
+version: 0.2.1-wip
+repository: https://github.com/dart-lang/tools/tree/main/pkgs/cli_config
+
+environment:
+  sdk: ^3.4.0
+
+dependencies:
+  args: ^2.4.0
+  yaml: ^3.1.1
+
+dev_dependencies:
+  dart_flutter_team_lints: ^3.0.0
+  test: ^1.21.0
diff --git a/pkgs/cli_config/test/cli_config_example_test.dart b/pkgs/cli_config/test/cli_config_example_test.dart
new file mode 100644
index 0000000..43ed7b9
--- /dev/null
+++ b/pkgs/cli_config/test/cli_config_example_test.dart
@@ -0,0 +1,106 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:io';
+
+import 'package:test/test.dart';
+
+import 'helpers.dart';
+
+void main() {
+  test('resolve command line paths relative to working directory', () async {
+    await inTempDir((tempUri) async {
+      final rootUri = Directory.current.uri.normalizePath();
+      final examplePackageUri =
+          rootUri.resolve('example${Platform.pathSeparator}');
+      final entryPoint = 'bin${Platform.pathSeparator}cli_config_example.dart';
+      const pubSpec = 'pubspec.yaml';
+      for (final filename in [entryPoint, pubSpec]) {
+        final targetUri = tempUri.resolve(filename);
+        await File.fromUri(targetUri).create(recursive: true);
+        await File.fromUri(examplePackageUri.resolve(filename))
+            .copy(targetUri.toFilePath());
+      }
+      final pubspecFile = File.fromUri(tempUri.resolve(pubSpec));
+      await pubspecFile.writeAsString(
+        (await pubspecFile.readAsString())
+            .replaceAll('path: ../', 'path: ${rootUri.toFilePath()}'),
+      );
+
+      final pubGetResult = await runProcess(
+        executable: Uri.file(Platform.resolvedExecutable),
+        arguments: ['pub', 'get'],
+        workingDirectory: tempUri,
+      );
+      expect(pubGetResult.exitCode, 0);
+
+      {
+        final commandLinePath = Uri.file(
+            'a${Platform.pathSeparator}b${Platform.pathSeparator}d.ext');
+        final result = await runProcess(
+          executable: Uri.file(Platform.resolvedExecutable),
+          arguments: [
+            tempUri.resolve(entryPoint).toFilePath(),
+            '-Dmy_path=${commandLinePath.toFilePath()}'
+          ],
+          workingDirectory: rootUri,
+        );
+        final stdout = (result.stdout as String).trim();
+        final resolvedPath = Uri.file(stdout);
+        expect(resolvedPath, rootUri.resolveUri(commandLinePath));
+      }
+
+      {
+        final commandLinePath = Uri.file(
+            'a${Platform.pathSeparator}b${Platform.pathSeparator}d.ext');
+        final result = await runProcess(
+          executable: Uri.file(Platform.resolvedExecutable),
+          arguments: [
+            tempUri.resolve(entryPoint).toFilePath(),
+            '-Dmy_path=${commandLinePath.toFilePath()}'
+          ],
+          workingDirectory: tempUri,
+        );
+        final stdout = (result.stdout as String).trim();
+        final resolvedPath = Uri.file(stdout);
+        expect(resolvedPath, tempUri.resolveUri(commandLinePath));
+      }
+
+      final pathInFile =
+          Uri.file('a${Platform.pathSeparator}b${Platform.pathSeparator}d.ext');
+      final configUri = tempUri.resolve('config.yaml');
+      await File.fromUri(configUri).writeAsString('''
+my_path: ${pathInFile.toFilePath()}
+''');
+
+      {
+        final result = await runProcess(
+          executable: Uri.file(Platform.resolvedExecutable),
+          arguments: [
+            tempUri.resolve(entryPoint).toFilePath(),
+            '--config=${configUri.toFilePath()}'
+          ],
+          workingDirectory: tempUri,
+        );
+        final stdout = (result.stdout as String).trim();
+        final resolvedPath = Uri.file(stdout);
+        expect(resolvedPath, tempUri.resolveUri(pathInFile));
+      }
+
+      {
+        final result = await runProcess(
+          executable: Uri.file(Platform.resolvedExecutable),
+          arguments: [
+            tempUri.resolve(entryPoint).toFilePath(),
+            '--config=${configUri.toFilePath()}'
+          ],
+          workingDirectory: rootUri,
+        );
+        final stdout = (result.stdout as String).trim();
+        final resolvedPath = Uri.file(stdout);
+        expect(resolvedPath, tempUri.resolveUri(pathInFile));
+      }
+    });
+  });
+}
diff --git a/pkgs/cli_config/test/cli_config_test.dart b/pkgs/cli_config/test/cli_config_test.dart
new file mode 100644
index 0000000..073002c
--- /dev/null
+++ b/pkgs/cli_config/test/cli_config_test.dart
@@ -0,0 +1,567 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:convert';
+import 'dart:io';
+
+import 'package:cli_config/cli_config.dart';
+import 'package:test/test.dart';
+
+import 'helpers.dart';
+
+void main() {
+  test('optionalStringList', () {
+    const path1 = 'path/in/cli_arguments/';
+    const path2 = 'path/in/cli_arguments_2/';
+    const path3 = 'path/in/environment/';
+    const path4 = 'path/in/environment_2/';
+    const path5 = 'path/in/config_file/';
+    const path6 = 'path/in/config_file_2/';
+    final config = Config.fromConfigFileContents(
+      commandLineDefines: [
+        'build.out_dir=$path1',
+        'build.out_dir=$path2',
+      ],
+      environment: {
+        'BUILD__OUT_DIR': '$path3:$path4',
+      },
+      fileContents: jsonEncode(
+        {
+          'build': {
+            'out_dir': [
+              path5,
+              path6,
+            ],
+          }
+        },
+      ),
+    );
+
+    {
+      final result = config.optionalStringList(
+        'build.out_dir',
+        combineAllConfigs: true,
+        splitEnvironmentPattern: ':',
+      );
+      expect(result, [path1, path2, path3, path4, path5, path6]);
+    }
+
+    {
+      final result = config.optionalStringList(
+        'build.out_dir',
+        combineAllConfigs: false,
+        splitEnvironmentPattern: ':',
+      );
+      expect(result, [path1, path2]);
+    }
+  });
+
+  test('optionalString cli precedence', () {
+    const path1 = 'path/in/cli_arguments/';
+    const path2 = 'path/in/environment/';
+    const path3 = 'path/in/config_file/';
+    final config = Config.fromConfigFileContents(
+      commandLineDefines: [
+        'build.out_dir=$path1',
+      ],
+      environment: {
+        'BUILD__OUT_DIR': path2,
+      },
+      fileContents: jsonEncode(
+        {
+          'build': {
+            'out_dir': path3,
+          }
+        },
+      ),
+    );
+
+    final result = config.optionalString(
+      'build.out_dir',
+    );
+    expect(result, path1);
+  });
+
+  test('optionalString environment precedence', () {
+    const path2 = 'path/in/environment/';
+    const path3 = 'path/in/config_file/';
+    final config = Config.fromConfigFileContents(
+      commandLineDefines: [],
+      environment: {
+        'BUILD__OUT_DIR': path2,
+      },
+      fileContents: jsonEncode(
+        {
+          'build': {
+            'out_dir': path3,
+          }
+        },
+      ),
+    );
+
+    final result = config.optionalString(
+      'build.out_dir',
+    );
+    expect(result, path2);
+  });
+
+  test('optionalString config file', () {
+    const path3 = 'path/in/config_file/';
+    final config = Config.fromConfigFileContents(
+      commandLineDefines: [],
+      environment: {},
+      fileContents: jsonEncode(
+        {
+          'build': {
+            'out_dir': path3,
+          }
+        },
+      ),
+    );
+
+    final result = config.optionalString(
+      'build.out_dir',
+    );
+    expect(result, path3);
+  });
+
+  test('optionalBool define', () {
+    final config = Config(
+      commandLineDefines: ['my_bool=true'],
+    );
+
+    expect(config.optionalBool('my_bool'), true);
+  });
+
+  test('optionalBool environment', () {
+    final config = Config(
+      environment: {
+        'MY_BOOL': 'true',
+      },
+    );
+
+    expect(config.optionalBool('my_bool'), true);
+  });
+
+  test('optionalBool  file', () {
+    final config = Config.fromConfigFileContents(
+      fileContents: jsonEncode(
+        {'my_bool': true},
+      ),
+    );
+
+    expect(config.optionalBool('my_bool'), true);
+  });
+
+  test('Read file and parse CLI args', () async {
+    final temp = await Directory.systemTemp.createTemp();
+    final configFile = File.fromUri(temp.uri.resolve('config.yaml'));
+    await configFile.writeAsString(jsonEncode(
+      {
+        'build': {
+          'out_dir': 'path/in/config_file/',
+        }
+      },
+    ));
+    final config = await Config.fromArguments(
+      arguments: [
+        '--config',
+        configFile.path,
+        '-Dbuild.out_dir=path/in/cli_arguments/',
+      ],
+      environment: {
+        'BUILD__OUT_DIR': 'path/in/environment',
+      },
+    );
+
+    final result = config.optionalString('build.out_dir');
+    expect(result, 'path/in/cli_arguments/');
+  });
+
+  test('Resolve config file path relative to config file', () async {
+    final temp = await Directory.systemTemp.createTemp();
+    final tempUri = temp.uri;
+    final configUri = tempUri.resolve('config.yaml');
+    final configFile = File.fromUri(configUri);
+    const relativePath = 'path/in/config_file/';
+    final resolvedPath = configUri.resolve(relativePath);
+
+    await configFile.writeAsString(jsonEncode(
+      {
+        'build': {
+          'out_dir': relativePath,
+        }
+      },
+    ));
+
+    final config = await Config.fromArguments(
+      arguments: [
+        '--config',
+        configFile.path,
+      ],
+    );
+    final result = config.optionalPath('build.out_dir');
+    expect(result!.path, resolvedPath.path);
+
+    final configSync = Config.fromArgumentsSync(
+      arguments: [
+        '--config',
+        configFile.path,
+      ],
+    );
+    final resultSync = configSync.optionalPath('build.out_dir');
+    expect(resultSync!.path, resolvedPath.path);
+  });
+
+  test('provide pre-parsed config', () {
+    const path3 = 'path/in/config_file/';
+    final config = Config(
+      commandLineDefines: [],
+      environment: {},
+      fileParsed: {
+        'build': {
+          'out_dir': path3,
+        }
+      },
+    );
+
+    final result = config.optionalString('build.out_dir');
+    expect(result, path3);
+  });
+
+  test('path exists', () async {
+    await inTempDir((tempUri) async {
+      final tempFileUri = tempUri.resolve('file.ext');
+      await File.fromUri(tempFileUri).create();
+      final nonExistUri = tempUri.resolve('foo.ext');
+      final config = Config(
+        commandLineDefines: [],
+        environment: {},
+        fileParsed: {
+          'build': {
+            'out_dir': tempUri.toFilePath(),
+            'file': tempFileUri.toFilePath(),
+            'non_exist': nonExistUri.toFilePath(),
+          }
+        },
+      );
+
+      final result = config.optionalPath('build.out_dir', mustExist: true);
+      expect(result, tempUri);
+      final result2 = config.optionalPath('build.file', mustExist: true);
+      expect(result2, tempFileUri);
+      expect(
+        () => config.optionalPath('build.non_exist', mustExist: true),
+        throwsFormatException,
+      );
+    });
+  });
+
+  test('wrong CLI key format', () {
+    expect(
+      () => Config(commandLineDefines: ['CAPITALIZED=value']),
+      throwsFormatException,
+    );
+  });
+
+  test('CLI two values when expecting one', () {
+    final config = Config(commandLineDefines: ['key=value', 'key=value2']);
+    expect(
+      () => config.string('key'),
+      throwsFormatException,
+    );
+  });
+
+  test('CLI split optionalStringList', () {
+    final config = Config(commandLineDefines: ['key=value;value2']);
+    final value = config.optionalStringList('key', splitCliPattern: ';');
+    expect(value, ['value', 'value2']);
+  });
+
+  test('CLI path', () {
+    final uri = Uri.file('some/path.ext');
+    final config = Config(commandLineDefines: ['key=${uri.path}']);
+    final value = config.optionalPath('key');
+    expect(value, uri);
+  });
+
+  test('CLI path list', () {
+    final uri = Uri.file('some/path.ext');
+    final uri2 = Uri.file('some/directory/');
+    final config = Config(commandLineDefines: ['key=${uri.path}:${uri2.path}']);
+    final value = config.optionalPathList('key', splitCliPattern: ':');
+    expect(value, [uri, uri2]);
+  });
+
+  test('toString', () {
+    final config = Config(
+      commandLineDefines: ['key=foo'],
+      environment: {'key': 'bar'},
+      fileParsed: {'key': 'baz'},
+    );
+    config.toString();
+  });
+
+  test('Missing nonullable throws FormatException', () {
+    final config = Config.fromConfigFileContents();
+    expect(() => config.bool('key'), throwsFormatException);
+    expect(() => config.string('key'), throwsFormatException);
+    expect(() => config.path('key'), throwsFormatException);
+  });
+
+  test('string not validValue throws FormatException', () {
+    final config = Config(environment: {'foo': 'bar'});
+    expect(
+      () => config.string('foo', validValues: ['not_bar']),
+      throwsFormatException,
+    );
+  });
+
+  test('optionalString validValues', () {
+    final config = Config();
+    expect(config.optionalString('foo', validValues: ['bar']), isNull);
+  });
+
+  test('valueOf file source', () {
+    final config = Config(fileParsed: {
+      'key': {'some': 'map'}
+    });
+    final value = config.valueOf<Map<dynamic, dynamic>>('key');
+    expect(value, {'some': 'map'});
+  });
+
+  test('valueOf command line source', () {
+    final config = Config(commandLineDefines: [
+      'string_key=value',
+      'bool_key=true',
+      'string_list_key=value1',
+      'string_list_key=value2',
+    ]);
+    expect(config.valueOf<String>('string_key'), 'value');
+    expect(config.valueOf<bool>('bool_key'), true);
+    expect(
+      config.valueOf<List<String>>('string_list_key'),
+      ['value1', 'value2'],
+    );
+  });
+
+  test('environment split optionalStringList', () {
+    final config = Config(environment: {'key': 'value;value2'});
+    final value =
+        config.optionalStringList('key', splitEnvironmentPattern: ';');
+    expect(value, ['value', 'value2']);
+  });
+
+  test('environment non split optionalStringList', () {
+    final config = Config(environment: {'key': 'value'});
+    final value = config.optionalStringList('key');
+    expect(value, ['value']);
+  });
+
+  test('environment path', () {
+    final uri = Uri.file('some/path.ext');
+    final config = Config(environment: {'key': uri.path});
+    final value = config.optionalPath('key');
+    expect(value, uri);
+  });
+
+  test('environment path list', () {
+    final uri = Uri.file('some/path.ext');
+    final uri2 = Uri.file('some/directory/');
+    final config = Config(environment: {'key': '${uri.path}:${uri2.path}'});
+    final value = config.optionalPathList('key', splitEnvironmentPattern: ':');
+    expect(value, [uri, uri2]);
+  });
+
+  test('Unexpected config file contents', () {
+    expect(() => Config.fromConfigFileContents(fileContents: 'asdf'),
+        throwsFormatException);
+    expect(() => Config.fromConfigFileContents(fileContents: "['asdf']"),
+        throwsFormatException);
+    expect(
+      () => Config.fromConfigFileContents(
+          fileContents: '''
+WRONGKEY:
+  1
+'''
+              .trim()),
+      throwsFormatException,
+    );
+    expect(
+      () => Config.fromConfigFileContents(
+          fileContents: '''
+1: 'asdf'
+'''
+              .trim()),
+      throwsFormatException,
+    );
+  });
+
+  test('file config try to access object as wrong type', () {
+    final config = Config.fromConfigFileContents(fileContents: '''foo:
+  bar:
+    true
+''');
+    expect(config.bool('foo.bar'), true);
+    expect(() => config.bool('foo.bar.baz'), throwsFormatException);
+    expect(() => config.string('foo.bar'), throwsFormatException);
+  });
+
+  test('file config path list unresolved', () {
+    final uri = Uri.file('some/path.ext');
+    final uri2 = Uri.file('some/directory/');
+    final config = Config(fileParsed: {
+      'key': [uri.path, uri2.path]
+    });
+    final value = config.optionalPathList('key', resolveUri: false);
+    expect(value, [uri, uri2]);
+  });
+
+  test('file config path list resolved', () {
+    final configUri = Uri.file('path/to/config.json');
+    final uri = Uri.file('some/path.ext');
+    final uri2 = Uri.file('some/directory/');
+    final config = Config(
+      fileSourceUri: configUri,
+      fileParsed: {
+        'key': [uri.path, uri2.path]
+      },
+    );
+    final value = config.optionalPathList('key', resolveUri: true);
+    expect(value, [configUri.resolveUri(uri), configUri.resolveUri(uri2)]);
+  });
+
+  test('resolveUri in working directory', () {
+    final systemTemp = Directory.systemTemp.uri;
+    final tempUri = systemTemp.resolve('x/y/z/');
+
+    final relativePath = Uri.file('a/b/c/d.ext');
+    final absolutePath = tempUri.resolveUri(relativePath);
+    final config = Config(
+      commandLineDefines: ['path=${relativePath.path}'],
+      workingDirectory: tempUri,
+    );
+
+    expect(config.optionalPath('path', mustExist: false, resolveUri: true),
+        absolutePath);
+  });
+
+  test('ints', () {
+    final config = Config(
+      commandLineDefines: ['cl=1', 'not_parsable=asdf'],
+      environment: {
+        'env': '2',
+        'not_parsable2': 'asfd',
+      },
+      fileParsed: {'file': 3},
+    );
+
+    expect(config.int('cl'), 1);
+    expect(config.optionalInt('env'), 2);
+    expect(config.optionalInt('file'), 3);
+    expect(config.optionalInt('nothing'), null);
+    expect(() => config.optionalInt('not_parsable'), throwsFormatException);
+    expect(() => config.optionalInt('not_parsable2'), throwsFormatException);
+  });
+
+  test('doubles', () {
+    final config = Config(
+      commandLineDefines: ['cl=1.1', 'not_parsable=asdf'],
+      environment: {
+        'env': '2.2',
+        'not_parsable2': 'asfd',
+      },
+      fileParsed: {'file': 3.3},
+    );
+
+    expect(config.double('cl'), 1.1);
+    expect(config.optionalDouble('env'), 2.2);
+    expect(config.optionalDouble('file'), 3.3);
+    expect(config.optionalDouble('nothing'), null);
+    expect(() => config.optionalDouble('not_parsable'), throwsFormatException);
+    expect(() => config.optionalDouble('not_parsable2'), throwsFormatException);
+  });
+
+  test('stringList and optionalStringList', () {
+    {
+      final config = Config(
+        fileParsed: {},
+      );
+
+      expect(config.optionalStringList('my_list'), null);
+      expect(() => config.stringList('my_list'), throwsFormatException);
+    }
+
+    {
+      final config = Config(
+        fileParsed: {'my_list': <String>[]},
+      );
+
+      expect(config.optionalStringList('my_list'), <String>[]);
+      expect(config.stringList('my_list'), <String>[]);
+    }
+  });
+
+  test('pathList and optionalPathList', () {
+    {
+      final config = Config(
+        fileParsed: {},
+      );
+
+      expect(config.optionalPathList('my_list'), null);
+      expect(() => config.pathList('my_list'), throwsFormatException);
+    }
+
+    {
+      final config = Config(
+        fileParsed: {'my_list': <String>[]},
+      );
+
+      expect(config.optionalPathList('my_list'), <String>[]);
+      expect(config.pathList('my_list'), <String>[]);
+    }
+  });
+
+  test('non-string key maps', () {
+    // This is valid in YAML (not in JSON).
+    //
+    // Such values cannot be accessed with our hierarchical keys, but they can
+    // be accessed with [Config.valueOf].
+    final config = Config(
+      fileParsed: {
+        'my_non_string_key_map': {
+          1: 'asdf',
+          2: 'foo',
+        },
+      },
+    );
+
+    expect(
+      config.valueOf<Map<Object, Object?>>('my_non_string_key_map'),
+      {
+        1: 'asdf',
+        2: 'foo',
+      },
+    );
+  });
+
+  test('null values in maps', () {
+    final config = Config(
+      fileParsed: {
+        'my_non_string_key_map': {
+          'x': null,
+          'y': 42,
+        },
+      },
+    );
+
+    expect(
+      config.valueOf<Map<Object, Object?>>('my_non_string_key_map'),
+      {
+        'x': null,
+        'y': 42,
+      },
+    );
+  });
+}
diff --git a/pkgs/cli_config/test/cli_config_windows_test.dart b/pkgs/cli_config/test/cli_config_windows_test.dart
new file mode 100644
index 0000000..2c401f2
--- /dev/null
+++ b/pkgs/cli_config/test/cli_config_windows_test.dart
@@ -0,0 +1,23 @@
+// Copyright (c) 2023, 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.
+
+@TestOn('windows')
+library;
+
+import 'package:cli_config/cli_config.dart';
+import 'package:test/test.dart';
+
+void main() {
+  test('path resolving windows', () {
+    const path = 'C:\\foo\\bar\\';
+    final workingDirectory = Uri.parse('file:///C:/baz/baf/');
+
+    final config = Config(
+      commandLineDefines: ['key=$path'],
+      workingDirectory: workingDirectory,
+    );
+    final value = config.path('key', resolveUri: true);
+    expect(value.toFilePath(), path);
+  });
+}
diff --git a/pkgs/cli_config/test/helpers.dart b/pkgs/cli_config/test/helpers.dart
new file mode 100644
index 0000000..d9fb40e
--- /dev/null
+++ b/pkgs/cli_config/test/helpers.dart
@@ -0,0 +1,43 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:io';
+
+const keepTempKey = 'KEEP_TEMPORARY_DIRECTORIES';
+
+Future<void> inTempDir(
+  Future<void> Function(Uri tempUri) fun, {
+  String? prefix,
+}) async {
+  final tempDir = await Directory.systemTemp.createTemp(prefix);
+  // Deal with Windows temp folder aliases.
+  final tempUri =
+      Directory(await tempDir.resolveSymbolicLinks()).uri.normalizePath();
+  try {
+    await fun(tempUri);
+  } finally {
+    if (!Platform.environment.containsKey(keepTempKey) ||
+        Platform.environment[keepTempKey]!.isEmpty) {
+      await tempDir.delete(recursive: true);
+    }
+  }
+}
+
+Future<ProcessResult> runProcess({
+  required Uri executable,
+  List<String> arguments = const [],
+  required Uri workingDirectory,
+}) async {
+  final result = await Process.run(
+    executable.toFilePath(),
+    arguments,
+    workingDirectory: workingDirectory.toFilePath(),
+  );
+  if (result.exitCode != 0) {
+    print(result.stdout);
+    print(result.stderr);
+    print(result.exitCode);
+  }
+  return result;
+}
diff --git a/pkgs/coverage/.gitignore b/pkgs/coverage/.gitignore
new file mode 100644
index 0000000..1a25097
--- /dev/null
+++ b/pkgs/coverage/.gitignore
@@ -0,0 +1,18 @@
+# Pub
+packages
+pubspec.lock
+build
+.dart_tool/
+.pub
+.packages
+
+# IDEs
+.project
+.settings
+.idea
+*.iml
+
+# Temp files
+*~
+coverage/
+var/
diff --git a/pkgs/coverage/AUTHORS b/pkgs/coverage/AUTHORS
new file mode 100644
index 0000000..7513829
--- /dev/null
+++ b/pkgs/coverage/AUTHORS
@@ -0,0 +1,12 @@
+# Below is a list of people and organizations that have contributed
+# to the coverage project. Names should be added to the list like so:
+#
+#   Name/Organization <email address>
+
+Google Inc.
+Achilleas Anagnostopoulos <achilleas.imap.mbox@gmail.com>
+Adam Singer <adammichaelsinger@gmail.com>
+Cédric Belin <cedxbelin@gmail.com>
+Evan Weible <ekweible@gmail.com>
+Günter Zöchbauer <guenter@gzoechbauer.com>
+Will Drach <will.drach@gmail.com>
diff --git a/pkgs/coverage/CHANGELOG.md b/pkgs/coverage/CHANGELOG.md
new file mode 100644
index 0000000..a58d0dc
--- /dev/null
+++ b/pkgs/coverage/CHANGELOG.md
@@ -0,0 +1,496 @@
+## 1.10.0
+
+- Fix bug where tests involving multiple isolates never finish (#520).
+
+## 1.9.2
+
+- Fix repository link in pubspec.
+
+## 1.9.1
+
+- Remove outdated VM service version checks.
+- Move to `dart-lang/tools`.
+
+## 1.9.0
+
+- Require Dart ^3.4
+- Fix bug where some ranges were able to bypass the `--scope-output` filters.
+- Add --ignore-files option allowing to exclude files from coverage reports using glob patterns
+
+## 1.8.0
+
+- Copy collect_coverage's `--scope-output` flag to test_with_coverage.
+
+## 1.7.2
+
+- Update `package:vm_service` constraints to '>=12.0.0 <15.0.0'.
+
+## 1.7.1
+
+- Update `package:vm_service` constraints to '>=12.0.0 <14.0.0'.
+
+## 1.7.0
+
+- Require Dart 3.0.0
+- Update `package:vm_service` constraints to '^12.0.0'.
+- Add `coverableLineCache` parameter to `collect`. This allows the set of
+  coverable lines to be cached between calls to `collect`, avoiding the need to
+  force compile the same libraries repeatedly. This is only useful when running
+  multiple coverage collections over the same libraries.
+
+## 1.6.4
+
+- allow omitting space between `//` and `coverage` in coverage ignore comments
+- allow text after coverage ignore comments
+- throw FormatException when encountering unbalanced ignore comments instead of silently erroring
+- Update `package:vm_service` constraints to '>= 9.4.0 <12.0.0'.
+
+## 1.6.3
+
+- Require Dart 2.18
+- Update `package:vm_service` constraints to '>=9.4.0 <12.0.0'.
+
+## 1.6.2
+
+- Update `package:vm_service` constraints to '>=9.4.0 <11.0.0'.
+
+## 1.6.1
+
+- Handle SentinelExceptions thrown by vm_service.
+
+## 1.6.0
+
+- Update to vm_service 9.4.0.
+- Use IsolateRef.isolateGroupId to speed up coverage collection.
+- Ignore uncoverable abstract methods.
+- Fix bug where 'ingore-line' comments etc are applied even if they're inside
+  string literals.
+- Change the LICENSE file to the standard Dart BSD license.
+
+## 1.5.0
+
+- Support passing extra arguments to `test_with_coverage` which are then passed
+  to `package:test`.
+
+  Example: `dart run coverage:test_with_coverage -- --preset CI`
+
+## 1.4.0
+
+- Added `HitMap.parseJsonSync` which takes a cache of ignored lines which can
+  speedup calls when `checkIgnoredLines` is true and the function is called
+  several times with overlapping files in the input json.
+- Bump the version of vm_service to 9.0.0.
+
+## 1.3.2
+
+- Fix test_with_coverage listening to an unsupported signal on windows.
+- Fix `--reportOn` on windows using incorrect path separators.
+
+## 1.3.1
+
+- Fix running `dart pub global run coverage:test_with_coverage` or
+  `dart run coverage:test_with_coverage`
+
+## 1.3.0
+
+- Bump the minimum Dart SDK version to 2.15.0
+- Add a `--package` flag, which takes the package's root directory, instead of
+  the .package file. Deprecate the `--packages` flag.
+- Deprecate the packagesPath parameter and add packagePath instead, in
+  `HitMap.parseJson`, `HitMap.parseFiles`, `createHitmap`, and `parseCoverage`.
+- Add a new executable to the package, `test_with_coverage`. This simplifies the
+  most common use case of coverage, running all the tests for a package, and
+  generating an lcov.info file.
+- Use the `libraryFilters` option in `getSourceReport` to speed up coverage runs
+  that use `scopedOutput`.
+
+## 1.2.0
+
+- Support branch level coverage information, when running tests in the Dart VM.
+  This is not supported for web tests yet.
+- Add flag `--branch-coverage` (abbr `-b`) to collect_coverage that collects
+  branch coverage information. The VM must also be run with the
+  `--branch-coverage` flag.
+- Add flag `--pretty-print-branch` to format_coverage that works similarly to
+  pretty print, but outputs branch level coverage, rather than line level.
+- Update `--lcov` (abbr `-l`) in format_coverage to output branch level
+  coverage, in addition to line level.
+- Add an optional bool flag to `collect` that controls whether branch coverage
+  is collected.
+- Add a `branchHits` field to `HitMap`.
+- Add support for scraping the service URI from the new Dart VM service message.
+- Correctly parse package_config files on Windows when the root URI is relative.
+
+## 1.1.0
+
+- Support function level coverage information, when running tests in the Dart
+  VM. This is not supported for web tests yet.
+- Add flag `--function-coverage` (abbr `-f`) to collect_coverage that collects
+  function coverage information.
+- Add flag `--pretty-print-func` (abbr `-f`) to format_coverage that works
+  similarly to pretty print, but outputs function level coverage, rather than
+  line level.
+- Update `--lcov` (abbr `-l`) in format_coverage to output function level
+  coverage, in addition to line level.
+- Add an optional bool flag to `collect` that controls whether function coverage
+  is collected.
+- Added `HitMap.parseJson`, `FileHitMaps.merge`, `HitMap.parseFiles`,
+  `HitMap.toJson`, `FileHitMapsFormatter.formatLcov`, and
+  `FileHitMapsFormatter.prettyPrint` that switch from using `Map<int, int>` to
+  represent line coverage to using `HitMap` (which contains both line and
+  function coverage). Document the old versions of these functions as
+  deprecated. We will delete the old functions when we update to coverage
+  version 2.0.0.
+- Ensure `createHitmap` returns a sorted hitmap. This fixes a potential issue
+  with ignore line annotations.
+- Use the `reportLines` flag in `vm_service`'s `getSourceReport` RPC. This
+  typically halves the number of RPCs that the coverage collector needs to run.
+- Require Dart `>=2.14.0`
+
+## 1.0.4
+
+- Updated dependency on `vm_service` package from `>=6.1.0 <8.0.0`to
+  `>=8.1.0 <9.0.0`.
+
+## 1.0.3
+
+- Updated dependency on `vm_service` package from `^6.1.0` to `>=6.1.0 <8.0.0`.
+
+## 1.0.2
+
+- Fix an issue where the `--packages` argument wasn't passed to
+  `format_coverage`.
+
+## 1.0.1
+
+- Allow the chrome `sourceUriProvider` to return `null`.
+
+## 1.0.0
+
+- Migrate to null safety.
+- Removed support for SDK `1.x.x`.
+
+## 0.15.2
+
+- Update `args`, `logging`, and `package_config` deps to allow the latest stable
+  releases.
+
+## 0.15.1
+
+- Updated dependency on `vm_service` package from `>=1.0.0 < 5.0.0` to
+  `>=1.0.0 <7.0.0`.
+
+## 0.15.0
+
+- BREAKING CHANGE: Eliminate the `--package-root` option from
+  `bin/run_and_collect.dart` and `bin/format_coverage.dart` as well as from
+  `runAndCollect` and the `Resolver` constructor.
+
+## 0.14.2
+
+- Fix an issue where `--wait-paused` with `collect` would attempt to collect
+  coverage if no isolates have started.
+
+## 0.14.1
+
+- Updated dependency on `vm_service` package from `>=1.0.0 < 5.0.0` to
+  `>=1.0.0 <6.0.0`.
+
+## 0.14.0
+
+- Add flag `--check-ignore` that is used to ignore lines from coverage depending
+  on the comments.
+
+  Use // coverage:ignore-line to ignore one line. Use // coverage:ignore-start
+  and // coverage:ignore-end to ignore range of lines inclusive. Use //
+  coverage:ignore-file to ignore the whole file.
+
+## 0.13.11
+
+- Revert breaking change in 13.10
+
+## 0.13.10
+
+- Add flag `--check-ignore` that is used to ignore lines from coverage depending
+  on the comments.
+
+  Use // coverage:ignore-line to ignore one line. Use // coverage:ignore-start
+  and // coverage:ignore-end to ignore range of lines inclusive. Use //
+  coverage:ignore-file to ignore the whole file.
+
+## 0.13.9
+
+- Don't crash on empty JSON input files.
+- Loosen the dependency on the `vm_service` package from `>=1.0.0 <4.0.0` to
+  `>=1.0.0 <5.0.0`.
+
+## 0.13.8
+
+- Update to package_config `1.9.0` which supports package_config.json files and
+  should be forwards compatible with `2.0.0`.
+- Deprecate the `packageRoot` argument on `Resolver`.
+
+## 0.13.7
+
+- Loosen the dependency on the `vm_service` package from `>=1.0.0 <3.0.0` to
+  `>=1.0.0 <4.0.0`.
+
+## 0.13.6
+
+- Now consider all `.json` files for the `format_coverage` command.
+
+## 0.13.5
+
+- Update `parseChromeCoverage` to merge coverage information for a given line.
+- Handle source map parse errors in `parseChromeCoverage`. Coverage will not be
+  considered for Dart files that have corresponding invalid source maps.
+
+## 0.13.4
+
+- Add `parseChromeCoverage` for creating a Dart based coverage report from a
+  Chrome coverage report.
+
+## 0.13.3+3 - 2019-12-03
+
+- Re-loosen the dependency on the `vm_service` package from `>=1.0.0 < 2.1.2` to
+  `>=1.0.0 <3.0.0` now that breakage introduced in version `2.1.2` has been
+  resolved. Fixed in:
+  https://github.com/dart-lang/sdk/commit/7a911ce3f1e945f2cbd1967c6109127e3acbab5a.
+
+## 0.13.3+2 - 2019-12-02
+
+- Tighten the dependency on the `vm_service` package from `>=1.0.0 <3.0.0` down
+  to `>=1.0.0 <2.1.2` in order to exclude version `2.1.2` which is broken on the
+  current stable Dart VM due to a missing SDK constraint in its pubspec.yaml.
+  The breakage was introduced in:
+  https://github.com/dart-lang/sdk/commit/9e636b5ab4de850fb19bc262e0686fdf14bfbfc0.
+
+## 0.13.3+1 - 2019-10-10
+
+- Loosen the dependency on the `vm_service` package from `^1.0.0` to
+  `>=1.0.0 <3.0.0`. Ensures dependency version range compatibility with the
+  latest versions of package `test`.
+
+## 0.13.3
+
+- Adds a new named argument to `collect` to filter coverage results by a set of
+  VM isolate IDs.
+- Migrates implementation of VM service protocol library from
+  `package:vm_service_lib`, which is no longer maintained, to
+  `package:vm_service`, which is.
+
+## 0.13.2
+
+- Add new multi-flag option `--scope-output` which restricts coverage output so
+  that only scripts that start with the provided path are considered.
+
+## 0.13.1
+
+- Handle scenario where the VM returns empty coverage information for a range.
+
+## 0.13.0
+
+- BREAKING CHANGE: Skips collecting coverage for `dart:` libraries by default,
+  which provides a significant performance boost. To restore the previous
+  behaviour and collect coverage for these libraries, use the `--include-dart`
+  flag.
+- Disables WebSocket compression for coverage collection. Since almost all
+  coverage collection runs happen over the loopback interface to localhost, this
+  improves performance and reduces CPU usage.
+- Migrates implementation of VM service protocol library from
+  `package:vm_service_client`, which is no longer maintained, to
+  `package:vm_service_lib`, which is.
+
+## 0.12.4
+
+- `collect()` now immediately throws `ArgumentError` if a null URI is passed in
+  the `serviceUri` parameter to avoid a less-easily debuggable null dereference
+  later. See dart-lang/coverage#240 for details.
+
+## 0.12.3
+
+- Fixed dart-lang/coverage#194. During collection, we now track each script by
+  its (unique) VMScriptRef. This ensures we look up the correct script when
+  computing the affected line for each hit token. The hitmap remains URI based,
+  since in the end, we want a single, unified set of line to hitCount mappings
+  per script.
+
+## 0.12.2
+
+- Dart SDK upper bound raised to <3.0.0.
+
+## 0.12.1
+
+- Minor type, dartfmt fixes.
+- Require package:args >= 1.4.0.
+
+## 0.12.0
+
+- BREAKING CHANGE: This version requires Dart SDK 2.0.0-dev.64.1 or later.
+- Strong mode fixes as of Dart SDK 2.0.0-dev.64.1.
+
+## 0.11.0
+
+- BREAKING CHANGE: This version requires Dart SDK 2.0.0-dev.30 or later.
+- Updated to Dart 2.0 constants from dart:convert.
+
+## 0.10.0
+
+- BREAKING CHANGE: `createHitmap` and `mergeHitmaps` now specify generic types
+  (`Map<String, Map<int, int>>`) on their hit map parameter/return value.
+- Updated package:args dependency to 1.0.0.
+
+## 0.9.3
+
+- Strong mode fixes as of Dart SDK 1.24.0.
+- Restrict the SDK lower version constraint to `>=1.21.0`. Required for method
+  generics.
+- Eliminate dependency on package:async.
+
+## 0.9.2
+
+- Strong mode fixes as of Dart SDK 1.22.0.
+
+## 0.9.1
+
+- Temporarily add back support for the `--host` and `--port` options to
+  `collect_coverage`. This is a temporary measure for backwards-compatibility
+  that may stop working on Dart SDKs >= 1.22. See the related
+  [breaking change note](https://groups.google.com/a/dartlang.org/forum/#!msg/announce/VxSw-V5tx8k/wPV0GfX7BwAJ)
+  for the Dart VM service protocol.
+
+## 0.9.0
+
+- BREAKING CHANGE: `collect` no longer supports the `host` and `port`
+  parameters. These are replaced with a `serviceUri` parameter. As of Dart SDK
+  1.22, the Dart VM will emit Observatory URIs that include an authentication
+  token for security reasons. Automated tools will need to scrape stdout for
+  this URI and pass it to `collect_coverage`.
+- BREAKING CHANGE: `collect_coverage`: the `--host` and `--port` options have
+  been replaced with a `--uri` option. See the above change for details.
+- BREAKING CHANGE: `runAndCollect` now defaults to running in checked mode.
+- Added `extractObservatoryUri`: scrapes an input string for an Observatory URI.
+  Potentially useful for automated tooling after Dart SDK 1.22.
+
+## 0.8.1
+
+- Added optional `checked` parameter to `runAndCollect` to run in checked mode.
+
+## 0.8.0+2
+
+- Strong mode fixes as of Dart SDK 1.20.1.
+
+## 0.8.0+1
+
+- Make strong mode clean.
+
+## 0.8.0
+
+- Moved `Formatter.format` parameters `reportOn` and `basePath` to constructor.
+  Eliminated `pathFilter` parameter.
+
+## 0.7.9
+
+- `format_coverage`: add `--base-directory` option. Source paths in
+  LCOV/pretty-print output are relative to this directory, or absolute if
+  unspecified.
+
+## 0.7.8
+
+- `format_coverage`: support `--packages` option for package specs.
+
+## 0.7.7
+
+- Add fallback URI resolution for Bazel http(s) URIs that don't contain a
+  `packages` path component.
+
+## 0.7.6
+
+- Add [Bazel](http://bazel.io) support to `format_coverage`.
+
+## 0.7.5
+
+- Bugfix in `collect_coverage`: prevent hang if initial VM service connection is
+  slow.
+- Workaround for VM behaviour in which `evaluate:source` ranges may appear in
+  the returned source report manifesting in a crash in `collect_coverage`. These
+  generally correspond to source evaluations in the debugger and add little
+  value to line coverage.
+- `format_coverage`: may be slower for large sets of coverage JSON input files.
+  Unlikely to be an issue due to elimination of `--coverage-dir` VM flag.
+
+## 0.7.4
+
+- Require at least Dart SDK 1.16.0.
+
+- Bugfix in format_coverage: if `--report-on` is not specified, emit all
+  coverage, rather than none.
+
+## 0.7.3
+
+- Added support for the latest Dart SDK.
+
+## 0.7.2
+
+- `Formatter.format` added two optional arguments: `reportOn` and `pathFilter`.
+  They can be used independently to limit the files which are included in the
+  output.
+
+- Added `runAndCollect` API to library.
+
+## 0.7.1
+
+- Added `collect` top-level method.
+
+- Updated support for latest `0.11.0` dev build.
+
+- Replaced `ServiceEvent.eventType` with `ServiceEvent.kind`.
+  - `ServiceEvent.eventType` is deprecated and will be removed in `0.8`.
+
+## 0.7.0
+
+- `format_coverage` no longer emits SDK coverage unless --sdk-root is set
+  explicitly.
+
+- Removed support for collecting coverage from old (<1.9.0) Dart SDKs.
+
+- Removed deprecated `Resolver.pkgRoot`.
+
+## 0.6.5
+
+- Fixed early collection bug when --wait-paused is set.
+
+## 0.6.4
+
+- Optimized formatters and fixed return value of `format` methods.
+
+- Added `Resolver.packageRoot` – deprecated `Resolver.pkgRoot`.
+
+## 0.6.3
+
+- Support the latest release of `args` package.
+
+- Support the latest release of `logging` package.
+
+- Fixed error when trying to access invalid paths.
+
+- Require at least Dart SDK v1.9.0.
+
+## 0.6.2
+
+- Support observatory protocol changes for VM >= 1.11.0.
+
+## 0.6.1
+
+- Support observatory protocol changes for VM >= 1.10.0.
+
+## 0.6.0+1
+
+- Add support for `pub global run`.
+
+## 0.6.0
+
+- Add support for SDK versions >= 1.9.0. For Dartium/content-shell versions past
+  1.9.0, coverage collection is no longer done over the remote debugging port,
+  but via the observatory port emitted on stdout. Backward compatibility with
+  SDKs back to 1.5.x is provided.
diff --git a/pkgs/coverage/LICENSE b/pkgs/coverage/LICENSE
new file mode 100644
index 0000000..000cd7b
--- /dev/null
+++ b/pkgs/coverage/LICENSE
@@ -0,0 +1,27 @@
+Copyright 2014, the Dart project authors. 
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+    * Redistributions of source code must retain the above copyright
+      notice, this list of conditions and the following disclaimer.
+    * Redistributions in binary form must reproduce the above
+      copyright notice, this list of conditions and the following
+      disclaimer in the documentation and/or other materials provided
+      with the distribution.
+    * Neither the name of Google LLC nor the names of its
+      contributors may be used to endorse or promote products derived
+      from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
diff --git a/pkgs/coverage/PATENTS b/pkgs/coverage/PATENTS
new file mode 100644
index 0000000..6954196
--- /dev/null
+++ b/pkgs/coverage/PATENTS
@@ -0,0 +1,23 @@
+Additional IP Rights Grant (Patents)
+
+"This implementation" means the copyrightable works distributed by
+Google as part of the Dart Project.
+
+Google hereby grants to you a perpetual, worldwide, non-exclusive,
+no-charge, royalty-free, irrevocable (except as stated in this
+section) patent license to make, have made, use, offer to sell, sell,
+import, transfer, and otherwise run, modify and propagate the contents
+of this implementation of Dart, where such license applies only to
+those patent claims, both currently owned by Google and acquired in
+the future, licensable by Google that are necessarily infringed by
+this implementation of Dart. This grant does not include claims that
+would be infringed only as a consequence of further modification of
+this implementation. If you or your agent or exclusive licensee
+institute or order or agree to the institution of patent litigation
+against any entity (including a cross-claim or counterclaim in a
+lawsuit) alleging that this implementation of Dart or any code
+incorporated within this implementation of Dart constitutes direct or
+contributory patent infringement, or inducement of patent
+infringement, then any patent rights granted to you under this License
+for this implementation of Dart shall terminate as of the date such
+litigation is filed.
diff --git a/pkgs/coverage/README.md b/pkgs/coverage/README.md
new file mode 100644
index 0000000..81736a4
--- /dev/null
+++ b/pkgs/coverage/README.md
@@ -0,0 +1,123 @@
+Coverage provides coverage data collection, manipulation, and formatting for
+Dart.
+
+[![Build Status](https://github.com/dart-lang/tools/actions/workflows/coverage.yml/badge.svg)](https://github.com/dart-lang/tools/actions/workflows/coverage.yml)
+[![Coverage Status](https://coveralls.io/repos/github/dart-lang/tools/badge.svg?branch=main)](https://coveralls.io/github/dart-lang/tools?branch=main)
+[![Pub](https://img.shields.io/pub/v/coverage.svg)](https://pub.dev/packages/coverage)
+
+## Tools
+
+`collect_coverage` collects coverage JSON from the Dart VM Service.
+`format_coverage` formats JSON coverage data into either
+[LCOV](https://github.com/linux-test-project/lcov) or pretty-printed format.
+
+#### Install coverage
+
+    dart pub global activate coverage
+
+Consider adding the `dart pub global run` executables directory to your path.
+See
+[Running a script from your PATH](https://dart.dev/tools/pub/cmd/pub-global#running-a-script-from-your-path)
+for more details.
+
+#### Running tests with coverage
+
+For the common use case where you just want to run all your tests, and generate
+an lcov.info file, you can use the test_with_coverage script:
+
+```
+dart pub global run coverage:test_with_coverage
+```
+
+By default, this script assumes it's being run from the root directory of a
+package, and outputs a coverage.json and lcov.info file to ./coverage/
+
+This script is essentially the same as running:
+
+```
+dart run --pause-isolates-on-exit --disable-service-auth-codes --enable-vm-service=8181 test &
+dart pub global run coverage:collect_coverage --wait-paused --uri=http://127.0.0.1:8181/ -o coverage/coverage.json --resume-isolates --scope-output=foo
+dart pub global run coverage:format_coverage --packages=.dart_tool/package_config.json --lcov -i coverage/coverage.json -o coverage/lcov.info
+```
+
+For more complicated use cases, where you want to control each of these stages,
+see the sections below.
+
+#### Collecting coverage from the VM
+
+```
+dart --pause-isolates-on-exit --disable-service-auth-codes --enable-vm-service=NNNN script.dart
+dart pub global run coverage:collect_coverage --uri=http://... -o coverage.json --resume-isolates
+```
+
+or if the `dart pub global run` executables are on your PATH,
+
+```
+collect_coverage --uri=http://... -o coverage.json --resume-isolates
+```
+
+where `--uri` specifies the Dart VM Service URI emitted by the VM.
+
+If `collect_coverage` is invoked before the script from which coverage is to be
+collected, it will wait until it detects a VM observatory to which it can
+connect. An optional `--connect-timeout` may be specified (in seconds). The
+`--wait-paused` flag may be enabled, causing `collect_coverage` to wait until
+all isolates are paused before collecting coverage.
+
+#### Formatting coverage data
+
+```
+dart pub global run coverage:format_coverage --package=app_package -i coverage.json
+```
+
+or if the `dart pub global run` exectuables are on your PATH,
+
+```
+format_coverage --package=app_package -i coverage.json
+```
+
+where `app_package` is the path to the package whose coverage is being collected
+(defaults to the current working directory). If `--sdk-root` is set, Dart SDK
+coverage will also be output.
+
+#### Ignore lines from coverage
+
+- `// coverage:ignore-line` to ignore one line.
+- `// coverage:ignore-start` and `// coverage:ignore-end` to ignore range of
+  lines inclusive.
+- `// coverage:ignore-file` to ignore the whole file.
+
+Then pass `--check-ignore` to `format_coverage`.
+
+#### Function and branch coverage
+
+To gather function level coverage information, pass `--function-coverage` to
+collect_coverage:
+
+```
+dart --pause-isolates-on-exit --disable-service-auth-codes --enable-vm-service=NNNN script.dart
+dart pub global run coverage:collect_coverage --uri=http://... -o coverage.json --resume-isolates --function-coverage
+```
+
+To gather branch level coverage information, pass `--branch-coverage` to _both_
+collect_coverage and the Dart command you're gathering coverage from:
+
+```
+dart --pause-isolates-on-exit --disable-service-auth-codes --enable-vm-service=NNNN --branch-coverage script.dart
+dart pub global run coverage:collect_coverage --uri=http://... -o coverage.json --resume-isolates --branch-coverage
+```
+
+Branch coverage requires Dart VM 2.17.0, with service API v3.56. Function,
+branch, and line coverage can all be gathered at the same time, by combining
+those flags:
+
+```
+dart --pause-isolates-on-exit --disable-service-auth-codes --enable-vm-service=NNNN --branch-coverage script.dart
+dart pub global run coverage:collect_coverage --uri=http://... -o coverage.json --resume-isolates --function-coverage --branch-coverage
+```
+
+These flags can also be passed to test_with_coverage:
+
+```
+pub global run coverage:test_with_coverage --branch-coverage --function-coverage
+```
diff --git a/pkgs/coverage/analysis_options.yaml b/pkgs/coverage/analysis_options.yaml
new file mode 100644
index 0000000..1d9542a
--- /dev/null
+++ b/pkgs/coverage/analysis_options.yaml
@@ -0,0 +1,23 @@
+include: package:dart_flutter_team_lints/analysis_options.yaml
+
+analyzer:
+  language:
+    strict-casts: true
+
+  exclude:
+    - var/**
+
+linter:
+  rules:
+    - always_declare_return_types
+    - avoid_slow_async_io
+    - cancel_subscriptions
+    - comment_references
+    - literal_only_boolean_expressions
+    - package_api_docs
+    - prefer_final_locals
+    - sort_constructors_first
+    - sort_unnamed_constructors_first
+    - test_types_in_equals
+    - throw_in_finally
+    - type_annotate_public_apis
diff --git a/pkgs/coverage/benchmark/.gitignore b/pkgs/coverage/benchmark/.gitignore
new file mode 100644
index 0000000..1269488
--- /dev/null
+++ b/pkgs/coverage/benchmark/.gitignore
@@ -0,0 +1 @@
+data
diff --git a/pkgs/coverage/benchmark/many_isolates.dart b/pkgs/coverage/benchmark/many_isolates.dart
new file mode 100644
index 0000000..185576a
--- /dev/null
+++ b/pkgs/coverage/benchmark/many_isolates.dart
@@ -0,0 +1,27 @@
+// Copyright (c) 2022, 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.
+
+import 'dart:isolate';
+import 'dart:math';
+
+Future<void> main(List<String> args, dynamic message) async {
+  if (message == null) {
+    // If there is no message, it means this instance was created by
+    // run_benchmarks.dart. In that case, this is the parent instance that
+    // spawns all the others.
+    var sum = 0;
+    for (var i = 0; i < 10; ++i) {
+      final port = ReceivePort();
+      final isolate =
+          Isolate.spawnUri(Uri.file('many_isolates.dart'), [], port.sendPort);
+      sum += await port.first as int;
+      await isolate;
+    }
+    print('sum = $sum');
+  } else {
+    // If there is a message, it means this instance is one of the child
+    // instances. The message is the port that this instance replies on.
+    (message as SendPort).send(Random().nextInt(1000));
+  }
+}
diff --git a/pkgs/coverage/benchmark/run_benchmarks.dart b/pkgs/coverage/benchmark/run_benchmarks.dart
new file mode 100644
index 0000000..1bd2990
--- /dev/null
+++ b/pkgs/coverage/benchmark/run_benchmarks.dart
@@ -0,0 +1,143 @@
+// Copyright (c) 2022, 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.
+
+import 'dart:async';
+import 'dart:io';
+
+import 'package:benchmark_harness/benchmark_harness.dart';
+
+import '../bin/collect_coverage.dart' as collect_coverage;
+import '../bin/format_coverage.dart' as format_coverage;
+
+// Runs a test script with various different coverage configurations.
+class CoverageBenchmark extends AsyncBenchmarkBase {
+  CoverageBenchmark(
+    ScoreEmitter emitter,
+    super.name,
+    this.script, {
+    this.gatherCoverage = false,
+    this.functionCoverage = false,
+    this.branchCoverage = false,
+  }) : super(emitter: emitter);
+
+  final String script;
+  final bool gatherCoverage;
+  final bool functionCoverage;
+  final bool branchCoverage;
+  int iteration = 0;
+
+  @override
+  Future<void> run() async {
+    print('Running $name...');
+    final covFile = 'data/$name $iteration coverage.json';
+    final lcovFile = 'data/$name $iteration lcov.info';
+    ++iteration;
+
+    await Process.start(
+      Platform.executable,
+      [
+        if (branchCoverage) '--branch-coverage',
+        'run',
+        if (gatherCoverage) ...[
+          '--pause-isolates-on-exit',
+          '--disable-service-auth-codes',
+          '--enable-vm-service=1234',
+        ],
+        script,
+      ],
+      mode: ProcessStartMode.detached,
+    );
+    if (gatherCoverage) {
+      await collect_coverage.main([
+        '--wait-paused',
+        '--resume-isolates',
+        '--uri=http://127.0.0.1:1234/',
+        if (branchCoverage) '--branch-coverage',
+        if (functionCoverage) '--function-coverage',
+        '-o',
+        covFile,
+      ]);
+
+      await format_coverage.main([
+        '--lcov',
+        '--check-ignore',
+        '-i',
+        covFile,
+        '-o',
+        lcovFile,
+      ]);
+    }
+  }
+}
+
+// Emitter that just captures the value.
+class CaptureEmitter implements ScoreEmitter {
+  late double capturedValue;
+
+  @override
+  void emit(String testName, double value) {
+    capturedValue = value;
+  }
+}
+
+// Prints a JSON representation of the benchmark results, in a format compatible
+// with the github benchmark action.
+class JsonEmitter implements ScoreEmitter {
+  JsonEmitter(this._baseline);
+
+  final double _baseline;
+  final _results = <String, double>{};
+
+  @override
+  void emit(String testName, double value) {
+    _results[testName] = value;
+  }
+
+  String write() => '[${_results.entries.map((entry) => """{
+  "name": "${entry.key}",
+  "unit": "times slower",
+  "value": ${(entry.value / _baseline).toStringAsFixed(2)}
+}""").join(',\n')}]';
+}
+
+Future<void> runBenchmark(CoverageBenchmark benchmark) async {
+  for (var i = 0; i < 3; ++i) {
+    try {
+      await benchmark.report().timeout(const Duration(minutes: 2));
+      return;
+    } on TimeoutException {
+      print('Timed out');
+    }
+  }
+  print('Timed out too many times. Giving up.');
+  exit(127);
+}
+
+Future<String> runBenchmarkSet(String name, String script) async {
+  final captureEmitter = CaptureEmitter();
+  await runBenchmark(
+      CoverageBenchmark(captureEmitter, '$name - no coverage', script));
+  final benchmarkBaseline = captureEmitter.capturedValue;
+
+  final emitter = JsonEmitter(benchmarkBaseline);
+  await runBenchmark(CoverageBenchmark(
+      emitter, '$name - basic coverage', script,
+      gatherCoverage: true));
+  await runBenchmark(CoverageBenchmark(
+      emitter, '$name - function coverage', script,
+      gatherCoverage: true, functionCoverage: true));
+  await runBenchmark(CoverageBenchmark(
+      emitter, '$name - branch coverage', script,
+      gatherCoverage: true, branchCoverage: true));
+  return emitter.write();
+}
+
+Future<void> main() async {
+  // Assume this script was started from the root coverage directory. Change to
+  // the benchmark directory.
+  Directory.current = 'benchmark';
+  final result = await runBenchmarkSet('Many isolates', 'many_isolates.dart');
+  await File('data/benchmark_result.json').writeAsString(result);
+  exit(0);
+}
diff --git a/pkgs/coverage/bin/collect_coverage.dart b/pkgs/coverage/bin/collect_coverage.dart
new file mode 100644
index 0000000..b02ac21
--- /dev/null
+++ b/pkgs/coverage/bin/collect_coverage.dart
@@ -0,0 +1,149 @@
+// 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.
+
+import 'dart:async';
+import 'dart:convert' show json;
+import 'dart:io';
+
+import 'package:args/args.dart';
+import 'package:coverage/src/collect.dart';
+import 'package:logging/logging.dart';
+import 'package:stack_trace/stack_trace.dart';
+
+Future<void> main(List<String> arguments) async {
+  Logger.root.level = Level.WARNING;
+  Logger.root.onRecord.listen((LogRecord rec) {
+    print('${rec.level.name}: ${rec.time}: ${rec.message}');
+  });
+
+  final options = _parseArgs(arguments);
+  await Chain.capture(() async {
+    final coverage = await collect(options.serviceUri, options.resume,
+        options.waitPaused, options.includeDart, options.scopedOutput,
+        timeout: options.timeout,
+        functionCoverage: options.functionCoverage,
+        branchCoverage: options.branchCoverage);
+    options.out.write(json.encode(coverage));
+    await options.out.close();
+  }, onError: (dynamic error, Chain chain) {
+    stderr.writeln(error);
+    stderr.writeln(chain.terse);
+    // See http://www.retro11.de/ouxr/211bsd/usr/include/sysexits.h.html
+    // EX_SOFTWARE
+    exit(70);
+  });
+}
+
+class Options {
+  Options(
+      this.serviceUri,
+      this.out,
+      this.timeout,
+      this.waitPaused,
+      this.resume,
+      this.includeDart,
+      this.functionCoverage,
+      this.branchCoverage,
+      this.scopedOutput);
+
+  final Uri serviceUri;
+  final IOSink out;
+  final Duration? timeout;
+  final bool waitPaused;
+  final bool resume;
+  final bool includeDart;
+  final bool functionCoverage;
+  final bool branchCoverage;
+  final Set<String> scopedOutput;
+}
+
+Options _parseArgs(List<String> arguments) {
+  final parser = ArgParser()
+    ..addOption('host',
+        abbr: 'H',
+        help: 'remote VM host. DEPRECATED: use --uri',
+        defaultsTo: '127.0.0.1')
+    ..addOption('port',
+        abbr: 'p',
+        help: 'remote VM port. DEPRECATED: use --uri',
+        defaultsTo: '8181')
+    ..addOption('uri', abbr: 'u', help: 'VM observatory service URI')
+    ..addOption('out',
+        abbr: 'o', defaultsTo: 'stdout', help: 'output: may be file or stdout')
+    ..addOption('connect-timeout',
+        abbr: 't', help: 'connect timeout in seconds')
+    ..addMultiOption('scope-output',
+        help: 'restrict coverage results so that only scripts that start with '
+            'the provided package path are considered')
+    ..addFlag('wait-paused',
+        abbr: 'w',
+        defaultsTo: false,
+        help: 'wait for all isolates to be paused before collecting coverage')
+    ..addFlag('resume-isolates',
+        abbr: 'r', defaultsTo: false, help: 'resume all isolates on exit')
+    ..addFlag('include-dart',
+        abbr: 'd', defaultsTo: false, help: 'include "dart:" libraries')
+    ..addFlag('function-coverage',
+        abbr: 'f', defaultsTo: false, help: 'Collect function coverage info')
+    ..addFlag('branch-coverage',
+        abbr: 'b',
+        defaultsTo: false,
+        help: 'Collect branch coverage info (Dart VM must also be run with '
+            '--branch-coverage for this to work)')
+    ..addFlag('help', abbr: 'h', negatable: false, help: 'show this help');
+
+  final args = parser.parse(arguments);
+
+  void printUsage() {
+    print('Usage: dart collect_coverage.dart --uri=http://... [OPTION...]\n');
+    print(parser.usage);
+  }
+
+  Never fail(String message) {
+    print('Error: $message\n');
+    printUsage();
+    exit(1);
+  }
+
+  if (args['help'] as bool) {
+    printUsage();
+    exit(0);
+  }
+
+  Uri serviceUri;
+  if (args['uri'] == null) {
+    // TODO(cbracken) eliminate --host and --port support when VM defaults to
+    // requiring an auth token. Estimated for Dart SDK 1.22.
+    serviceUri = Uri.parse('http://${args['host']}:${args['port']}/');
+  } else {
+    try {
+      serviceUri = Uri.parse(args['uri'] as String);
+    } on FormatException {
+      fail('Invalid service URI specified: ${args['uri']}');
+    }
+  }
+
+  final scopedOutput = args['scope-output'] as List<String>;
+  IOSink out;
+  if (args['out'] == 'stdout') {
+    out = stdout;
+  } else {
+    final outfile = File(args['out'] as String)..createSync(recursive: true);
+    out = outfile.openWrite();
+  }
+  final timeout = (args['connect-timeout'] == null)
+      ? null
+      : Duration(seconds: int.parse(args['connect-timeout'] as String));
+  return Options(
+    serviceUri,
+    out,
+    timeout,
+    args['wait-paused'] as bool,
+    args['resume-isolates'] as bool,
+    args['include-dart'] as bool,
+    args['function-coverage'] as bool,
+    args['branch-coverage'] as bool,
+    scopedOutput.toSet(),
+  );
+}
diff --git a/pkgs/coverage/bin/format_coverage.dart b/pkgs/coverage/bin/format_coverage.dart
new file mode 100644
index 0000000..d24f60d
--- /dev/null
+++ b/pkgs/coverage/bin/format_coverage.dart
@@ -0,0 +1,310 @@
+// Copyright (c) 2013, 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.
+
+import 'dart:io';
+
+import 'package:args/args.dart';
+import 'package:coverage/coverage.dart';
+import 'package:glob/glob.dart';
+import 'package:path/path.dart' as p;
+
+/// [Environment] stores gathered arguments information.
+class Environment {
+  Environment({
+    required this.baseDirectory,
+    required this.bazel,
+    required this.bazelWorkspace,
+    required this.checkIgnore,
+    required this.input,
+    required this.lcov,
+    required this.output,
+    required this.packagesPath,
+    required this.packagePath,
+    required this.prettyPrint,
+    required this.prettyPrintFunc,
+    required this.prettyPrintBranch,
+    required this.reportOn,
+    required this.ignoreFiles,
+    required this.sdkRoot,
+    required this.verbose,
+    required this.workers,
+  });
+
+  String? baseDirectory;
+  bool bazel;
+  String bazelWorkspace;
+  bool checkIgnore;
+  String input;
+  bool lcov;
+  IOSink output;
+  String? packagesPath;
+  String packagePath;
+  bool prettyPrint;
+  bool prettyPrintFunc;
+  bool prettyPrintBranch;
+  List<String>? reportOn;
+  List<String>? ignoreFiles;
+  String? sdkRoot;
+  bool verbose;
+  int workers;
+}
+
+Future<void> main(List<String> arguments) async {
+  final env = parseArgs(arguments);
+
+  final files = filesToProcess(env.input);
+  if (env.verbose) {
+    print('Environment:');
+    print('  # files: ${files.length}');
+    print('  # workers: ${env.workers}');
+    print('  sdk-root: ${env.sdkRoot}');
+    print('  package-path: ${env.packagePath}');
+    print('  packages-path: ${env.packagesPath}');
+    print('  report-on: ${env.reportOn}');
+    print('  check-ignore: ${env.checkIgnore}');
+  }
+
+  final clock = Stopwatch()..start();
+  final hitmap = await HitMap.parseFiles(
+    files,
+    checkIgnoredLines: env.checkIgnore,
+    // ignore: deprecated_member_use_from_same_package
+    packagesPath: env.packagesPath,
+    packagePath: env.packagePath,
+  );
+
+  // All workers are done. Process the data.
+  if (env.verbose) {
+    print('Done creating global hitmap. Took ${clock.elapsedMilliseconds} ms.');
+  }
+
+  final ignoreGlobs = env.ignoreFiles?.map(Glob.new).toSet();
+
+  String output;
+  final resolver = env.bazel
+      ? BazelResolver(workspacePath: env.bazelWorkspace)
+      : await Resolver.create(
+          packagesPath: env.packagesPath,
+          packagePath: env.packagePath,
+          sdkRoot: env.sdkRoot,
+        );
+  final loader = Loader();
+  if (env.prettyPrint) {
+    output = await hitmap.prettyPrint(resolver, loader,
+        reportOn: env.reportOn,
+        ignoreGlobs: ignoreGlobs,
+        reportFuncs: env.prettyPrintFunc,
+        reportBranches: env.prettyPrintBranch);
+  } else {
+    assert(env.lcov);
+    output = hitmap.formatLcov(resolver,
+        reportOn: env.reportOn,
+        ignoreGlobs: ignoreGlobs,
+        basePath: env.baseDirectory);
+  }
+
+  env.output.write(output);
+  await env.output.flush();
+  if (env.verbose) {
+    print('Done flushing output. Took ${clock.elapsedMilliseconds} ms.');
+  }
+
+  if (env.verbose) {
+    if (resolver.failed.isNotEmpty) {
+      print('Failed to resolve:');
+      for (var error in resolver.failed.toSet()) {
+        print('  $error');
+      }
+    }
+    if (loader.failed.isNotEmpty) {
+      print('Failed to load:');
+      for (var error in loader.failed.toSet()) {
+        print('  $error');
+      }
+    }
+  }
+  await env.output.close();
+}
+
+/// Checks the validity of the provided arguments. Does not initialize actual
+/// processing.
+Environment parseArgs(List<String> arguments) {
+  final parser = ArgParser();
+
+  parser
+    ..addOption('sdk-root', abbr: 's', help: 'path to the SDK root')
+    ..addOption('packages', help: '[DEPRECATED] path to the package spec file')
+    ..addOption('package',
+        help: 'root directory of the package', defaultsTo: '.')
+    ..addOption('in', abbr: 'i', help: 'input(s): may be file or directory')
+    ..addOption('out',
+        abbr: 'o', defaultsTo: 'stdout', help: 'output: may be file or stdout')
+    ..addMultiOption('report-on',
+        help: 'which directories or files to report coverage on')
+    ..addOption('workers',
+        abbr: 'j', defaultsTo: '1', help: 'number of workers')
+    ..addOption('bazel-workspace',
+        defaultsTo: '', help: 'Bazel workspace directory')
+    ..addOption('base-directory',
+        abbr: 'b',
+        help: 'the base directory relative to which source paths are output')
+    ..addFlag('bazel',
+        defaultsTo: false, help: 'use Bazel-style path resolution')
+    ..addFlag('pretty-print',
+        abbr: 'r',
+        negatable: false,
+        help: 'convert line coverage data to pretty print format')
+    ..addFlag('pretty-print-func',
+        abbr: 'f',
+        negatable: false,
+        help: 'convert function coverage data to pretty print format')
+    ..addFlag('pretty-print-branch',
+        negatable: false,
+        help: 'convert branch coverage data to pretty print format')
+    ..addFlag('lcov',
+        abbr: 'l',
+        negatable: false,
+        help: 'convert coverage data to lcov format')
+    ..addFlag('verbose', abbr: 'v', negatable: false, help: 'verbose output')
+    ..addFlag(
+      'check-ignore',
+      abbr: 'c',
+      negatable: false,
+      help: 'check for coverage ignore comments.'
+          ' Not supported in web coverage.',
+    )
+    ..addMultiOption(
+      'ignore-files',
+      defaultsTo: [],
+      help: 'Ignore files by glob patterns',
+    )
+    ..addFlag('help', abbr: 'h', negatable: false, help: 'show this help');
+
+  final args = parser.parse(arguments);
+
+  void printUsage() {
+    print('Usage: dart format_coverage.dart [OPTION...]\n');
+    print(parser.usage);
+  }
+
+  Never fail(String msg) {
+    print('\n$msg\n');
+    printUsage();
+    exit(1);
+  }
+
+  if (args['help'] as bool) {
+    printUsage();
+    exit(0);
+  }
+
+  var sdkRoot = args['sdk-root'] as String?;
+  if (sdkRoot != null) {
+    sdkRoot = p.normalize(p.join(p.absolute(sdkRoot), 'lib'));
+    if (!FileSystemEntity.isDirectorySync(sdkRoot)) {
+      fail('Provided SDK root "${args["sdk-root"]}" is not a valid SDK '
+          'top-level directory');
+    }
+  }
+
+  final packagesPath = args['packages'] as String?;
+  if (packagesPath != null) {
+    if (!FileSystemEntity.isFileSync(packagesPath)) {
+      fail('Package spec "${args["packages"]}" not found, or not a file.');
+    }
+  }
+
+  final packagePath = args['package'] as String;
+  if (!FileSystemEntity.isDirectorySync(packagePath)) {
+    fail('Package spec "${args["package"]}" not found, or not a directory.');
+  }
+
+  if (args['in'] == null) fail('No input files given.');
+  final input = p.absolute(p.normalize(args['in'] as String));
+  if (!FileSystemEntity.isDirectorySync(input) &&
+      !FileSystemEntity.isFileSync(input)) {
+    fail('Provided input "${args["in"]}" is neither a directory nor a file.');
+  }
+
+  IOSink output;
+  if (args['out'] == 'stdout') {
+    output = stdout;
+  } else {
+    final outpath = p.absolute(p.normalize(args['out'] as String));
+    final outfile = File(outpath)..createSync(recursive: true);
+    output = outfile.openWrite();
+  }
+
+  final reportOnRaw = args['report-on'] as List<String>;
+  final reportOn = reportOnRaw.isNotEmpty ? reportOnRaw : null;
+
+  final bazel = args['bazel'] as bool;
+  final bazelWorkspace = args['bazel-workspace'] as String;
+  if (bazelWorkspace.isNotEmpty && !bazel) {
+    stderr.writeln('warning: ignoring --bazel-workspace: --bazel not set');
+  }
+
+  String? baseDirectory;
+  if (args['base-directory'] != null) {
+    baseDirectory = p.absolute(args['base-directory'] as String);
+  }
+
+  final lcov = args['lcov'] as bool;
+  var prettyPrint = args['pretty-print'] as bool;
+  final prettyPrintFunc = args['pretty-print-func'] as bool;
+  final prettyPrintBranch = args['pretty-print-branch'] as bool;
+  final numModesChosen = (prettyPrint ? 1 : 0) +
+      (prettyPrintFunc ? 1 : 0) +
+      (prettyPrintBranch ? 1 : 0) +
+      (lcov ? 1 : 0);
+  if (numModesChosen > 1) {
+    fail('Choose one of the pretty-print modes or lcov output');
+  }
+
+  // The pretty printer is used by all modes other than lcov.
+  if (!lcov) prettyPrint = true;
+
+  int workers;
+  try {
+    workers = int.parse('${args["workers"]}');
+  } catch (e) {
+    fail('Invalid worker count: $e');
+  }
+
+  final checkIgnore = args['check-ignore'] as bool;
+  final ignoredGlobs = args['ignore-files'] as List<String>;
+  final verbose = args['verbose'] as bool;
+  return Environment(
+      baseDirectory: baseDirectory,
+      bazel: bazel,
+      bazelWorkspace: bazelWorkspace,
+      checkIgnore: checkIgnore,
+      input: input,
+      lcov: lcov,
+      output: output,
+      packagesPath: packagesPath,
+      packagePath: packagePath,
+      prettyPrint: prettyPrint,
+      prettyPrintFunc: prettyPrintFunc,
+      prettyPrintBranch: prettyPrintBranch,
+      reportOn: reportOn,
+      ignoreFiles: ignoredGlobs,
+      sdkRoot: sdkRoot,
+      verbose: verbose,
+      workers: workers);
+}
+
+/// Given an absolute path absPath, this function returns a [List] of files
+/// are contained by it if it is a directory, or a [List] containing the file if
+/// it is a file.
+List<File> filesToProcess(String absPath) {
+  if (FileSystemEntity.isDirectorySync(absPath)) {
+    return Directory(absPath)
+        .listSync(recursive: true)
+        .whereType<File>()
+        .where((e) => e.path.endsWith('.json'))
+        .toList();
+  }
+  return <File>[File(absPath)];
+}
diff --git a/pkgs/coverage/bin/run_and_collect.dart b/pkgs/coverage/bin/run_and_collect.dart
new file mode 100644
index 0000000..c255d01
--- /dev/null
+++ b/pkgs/coverage/bin/run_and_collect.dart
@@ -0,0 +1,12 @@
+// Copyright (c) 2017, 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.
+
+import 'dart:async';
+
+import 'package:coverage/src/run_and_collect.dart';
+
+Future<void> main(List<String> args) async {
+  final Map results = await runAndCollect(args[0]);
+  print(results);
+}
diff --git a/pkgs/coverage/bin/test_with_coverage.dart b/pkgs/coverage/bin/test_with_coverage.dart
new file mode 100644
index 0000000..010e608
--- /dev/null
+++ b/pkgs/coverage/bin/test_with_coverage.dart
@@ -0,0 +1,229 @@
+// Copyright (c) 2022, 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.
+
+import 'dart:async';
+import 'dart:io';
+
+import 'package:args/args.dart';
+import 'package:coverage/src/util.dart'
+    show StandardOutExtension, extractVMServiceUri;
+import 'package:package_config/package_config.dart';
+import 'package:path/path.dart' as path;
+
+import 'collect_coverage.dart' as collect_coverage;
+import 'format_coverage.dart' as format_coverage;
+
+final _allProcesses = <Process>[];
+
+Future<void> _dartRun(List<String> args,
+    {void Function(String)? onStdout, String? workingDir}) async {
+  final process = await Process.start(
+    Platform.executable,
+    args,
+    workingDirectory: workingDir,
+  );
+  _allProcesses.add(process);
+  final broadStdout = process.stdout.asBroadcastStream();
+  broadStdout.listen(stdout.add);
+  if (onStdout != null) {
+    broadStdout.lines().listen(onStdout);
+  }
+  process.stderr.listen(stderr.add);
+  final result = await process.exitCode;
+  if (result != 0) {
+    throw ProcessException(Platform.executable, args, '', result);
+  }
+}
+
+Future<String?> _packageNameFromConfig(String packageDir) async {
+  final config = await findPackageConfig(Directory(packageDir));
+  return config?.packageOf(Uri.directory(packageDir))?.name;
+}
+
+void _watchExitSignal(ProcessSignal signal) {
+  signal.watch().listen((sig) {
+    for (final process in _allProcesses) {
+      process.kill(sig);
+    }
+    exit(1);
+  });
+}
+
+ArgParser _createArgParser() => ArgParser()
+  ..addOption(
+    'package',
+    help: 'Root directory of the package to test.',
+    defaultsTo: '.',
+  )
+  ..addOption(
+    'package-name',
+    help: 'Name of the package to test. '
+        'Deduced from --package if not provided.',
+  )
+  ..addOption('port', help: 'VM service port.', defaultsTo: '8181')
+  ..addOption(
+    'out',
+    abbr: 'o',
+    help: 'Output directory. Defaults to <package-dir>/coverage.',
+  )
+  ..addOption('test', help: 'Test script to run.', defaultsTo: 'test')
+  ..addFlag(
+    'function-coverage',
+    abbr: 'f',
+    defaultsTo: false,
+    help: 'Collect function coverage info.',
+  )
+  ..addFlag(
+    'branch-coverage',
+    abbr: 'b',
+    defaultsTo: false,
+    help: 'Collect branch coverage info.',
+  )
+  ..addMultiOption('scope-output',
+      help: 'restrict coverage results so that only scripts that start with '
+          'the provided package path are considered. Defaults to the name of '
+          'the package under test.')
+  ..addFlag('help', abbr: 'h', negatable: false, help: 'Show this help.');
+
+class Flags {
+  Flags(
+    this.packageDir,
+    this.packageName,
+    this.outDir,
+    this.port,
+    this.testScript,
+    this.functionCoverage,
+    this.branchCoverage,
+    this.scopeOutput, {
+    required this.rest,
+  });
+
+  final String packageDir;
+  final String packageName;
+  final String outDir;
+  final String port;
+  final String testScript;
+  final bool functionCoverage;
+  final bool branchCoverage;
+  final List<String> scopeOutput;
+  final List<String> rest;
+}
+
+Future<Flags> _parseArgs(List<String> arguments) async {
+  final parser = _createArgParser();
+  final args = parser.parse(arguments);
+
+  void printUsage() {
+    print('''
+Runs tests and collects coverage for a package.
+
+By default this  script assumes it's being run from the root directory of a
+package, and outputs a coverage.json and lcov.info to ./coverage/
+
+Usage: test_with_coverage [OPTIONS...] [-- <test script OPTIONS>]
+
+${parser.usage}
+''');
+  }
+
+  Never fail(String msg) {
+    print('\n$msg\n');
+    printUsage();
+    exit(1);
+  }
+
+  if (args['help'] as bool) {
+    printUsage();
+    exit(0);
+  }
+
+  final packageDir = path.canonicalize(args['package'] as String);
+  if (!FileSystemEntity.isDirectorySync(packageDir)) {
+    fail('--package is not a valid directory.');
+  }
+
+  final packageName = (args['package-name'] as String?) ??
+      await _packageNameFromConfig(packageDir);
+  if (packageName == null) {
+    fail(
+      "Couldn't figure out package name from --package. Make sure this is a "
+      'package directory, or try passing --package-name explicitly.',
+    );
+  }
+
+  return Flags(
+    packageDir,
+    packageName,
+    (args['out'] as String?) ?? path.join(packageDir, 'coverage'),
+    args['port'] as String,
+    args['test'] as String,
+    args['function-coverage'] as bool,
+    args['branch-coverage'] as bool,
+    args['scope-output'] as List<String>,
+    rest: args.rest,
+  );
+}
+
+Future<void> main(List<String> arguments) async {
+  final flags = await _parseArgs(arguments);
+  final outJson = path.join(flags.outDir, 'coverage.json');
+  final outLcov = path.join(flags.outDir, 'lcov.info');
+
+  if (!FileSystemEntity.isDirectorySync(flags.outDir)) {
+    await Directory(flags.outDir).create(recursive: true);
+  }
+
+  _watchExitSignal(ProcessSignal.sighup);
+  _watchExitSignal(ProcessSignal.sigint);
+  if (!Platform.isWindows) {
+    _watchExitSignal(ProcessSignal.sigterm);
+  }
+
+  final serviceUriCompleter = Completer<Uri>();
+  final testProcess = _dartRun(
+    [
+      if (flags.branchCoverage) '--branch-coverage',
+      'run',
+      '--pause-isolates-on-exit',
+      '--disable-service-auth-codes',
+      '--enable-vm-service=${flags.port}',
+      flags.testScript,
+      ...flags.rest,
+    ],
+    onStdout: (line) {
+      if (!serviceUriCompleter.isCompleted) {
+        final uri = extractVMServiceUri(line);
+        if (uri != null) {
+          serviceUriCompleter.complete(uri);
+        }
+      }
+    },
+  );
+  final serviceUri = await serviceUriCompleter.future;
+
+  final scopes =
+      flags.scopeOutput.isEmpty ? [flags.packageName] : flags.scopeOutput;
+  await collect_coverage.main([
+    '--wait-paused',
+    '--resume-isolates',
+    '--uri=$serviceUri',
+    for (final scope in scopes) '--scope-output=$scope',
+    if (flags.branchCoverage) '--branch-coverage',
+    if (flags.functionCoverage) '--function-coverage',
+    '-o',
+    outJson,
+  ]);
+  await testProcess;
+
+  await format_coverage.main([
+    '--lcov',
+    '--check-ignore',
+    '--package=${flags.packageDir}',
+    '-i',
+    outJson,
+    '-o',
+    outLcov,
+  ]);
+  exit(0);
+}
diff --git a/pkgs/coverage/lib/coverage.dart b/pkgs/coverage/lib/coverage.dart
new file mode 100644
index 0000000..9cc81ab
--- /dev/null
+++ b/pkgs/coverage/lib/coverage.dart
@@ -0,0 +1,10 @@
+// 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.
+
+export 'src/chrome.dart';
+export 'src/collect.dart';
+export 'src/formatter.dart';
+export 'src/hitmap.dart' hide hitmapToJson;
+export 'src/resolver.dart';
+export 'src/run_and_collect.dart';
diff --git a/pkgs/coverage/lib/src/chrome.dart b/pkgs/coverage/lib/src/chrome.dart
new file mode 100644
index 0000000..2a97696
--- /dev/null
+++ b/pkgs/coverage/lib/src/chrome.dart
@@ -0,0 +1,171 @@
+// Copyright (c) 2020, 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.
+
+import 'package:source_maps/parser.dart';
+
+import 'hitmap.dart';
+
+/// Returns a Dart based hit-map containing coverage report for the provided
+/// Chrome [preciseCoverage].
+///
+/// [sourceProvider] returns the source content for the Chrome scriptId, or null
+/// if not available.
+///
+/// [sourceMapProvider] returns the associated source map content for the Chrome
+/// scriptId, or null if not available.
+///
+/// [sourceUriProvider] returns the uri for the provided sourceUrl and
+/// associated scriptId, or null if not available.
+///
+/// Chrome coverage information for which the corresponding source map or source
+/// content is null will be ignored.
+Future<Map<String, dynamic>> parseChromeCoverage(
+  List<Map<String, dynamic>> preciseCoverage,
+  Future<String?> Function(String scriptId) sourceProvider,
+  Future<String?> Function(String scriptId) sourceMapProvider,
+  Future<Uri?> Function(String sourceUrl, String scriptId) sourceUriProvider,
+) async {
+  final coverageReport = <Uri, Map<int, bool>>{};
+  for (var entry in preciseCoverage) {
+    final scriptId = entry['scriptId'] as String;
+
+    final mapResponse = await sourceMapProvider(scriptId);
+    if (mapResponse == null) continue;
+
+    SingleMapping mapping;
+    try {
+      mapping = parse(mapResponse) as SingleMapping;
+    } on FormatException {
+      continue;
+      // ignore: avoid_catching_errors
+    } on ArgumentError {
+      continue;
+    }
+
+    final compiledSource = await sourceProvider(scriptId);
+    if (compiledSource == null) continue;
+
+    final coverageInfo = _coverageInfoFor(entry);
+    final offsetCoverage = _offsetCoverage(coverageInfo, compiledSource.length);
+    final coveredPositions = _coveredPositions(compiledSource, offsetCoverage);
+
+    for (var lineEntry in mapping.lines) {
+      for (var columnEntry in lineEntry.entries) {
+        final sourceUrlId = columnEntry.sourceUrlId;
+        if (sourceUrlId == null) continue;
+        final sourceUrl = mapping.urls[sourceUrlId];
+
+        // Ignore coverage information for the SDK.
+        if (sourceUrl.startsWith('org-dartlang-sdk:')) continue;
+
+        final uri = await sourceUriProvider(sourceUrl, scriptId);
+        if (uri == null) continue;
+        final coverage = coverageReport.putIfAbsent(uri, () => <int, bool>{});
+
+        final sourceLine = columnEntry.sourceLine!;
+        final current = coverage[sourceLine + 1] ?? false;
+        coverage[sourceLine + 1] = current ||
+            coveredPositions.contains(
+                _Position(lineEntry.line + 1, columnEntry.column + 1));
+      }
+    }
+  }
+
+  final coverageHitMaps = <Uri, HitMap>{};
+  coverageReport.forEach((uri, coverage) {
+    final hitMap = HitMap();
+    for (var line in coverage.keys.toList()..sort()) {
+      hitMap.lineHits[line] = coverage[line]! ? 1 : 0;
+    }
+    coverageHitMaps[uri] = hitMap;
+  });
+
+  final allCoverage = <Map<String, dynamic>>[];
+  coverageHitMaps.forEach((uri, hitMap) {
+    allCoverage.add(hitmapToJson(hitMap, uri));
+  });
+  return <String, dynamic>{'type': 'CodeCoverage', 'coverage': allCoverage};
+}
+
+/// Returns all covered positions in a provided source.
+Set<_Position> _coveredPositions(
+    String compiledSource, List<bool> offsetCoverage) {
+  final positions = <_Position>{};
+  // Line is 1 based.
+  var line = 1;
+  // Column is 1 based.
+  var column = 0;
+  for (var offset = 0; offset < compiledSource.length; offset++) {
+    if (compiledSource[offset] == '\n') {
+      line++;
+      column = 0;
+    } else {
+      column++;
+    }
+    if (offsetCoverage[offset]) positions.add(_Position(line, column));
+  }
+  return positions;
+}
+
+/// Returns coverage information for a Chrome entry.
+List<_CoverageInfo> _coverageInfoFor(Map<String, dynamic> entry) {
+  final result = <_CoverageInfo>[];
+  for (var functions
+      in (entry['functions'] as List).cast<Map<String, dynamic>>()) {
+    for (var range
+        in (functions['ranges'] as List).cast<Map<String, dynamic>>()) {
+      result.add(_CoverageInfo(
+        range['startOffset'] as int,
+        range['endOffset'] as int,
+        (range['count'] as int) > 0,
+      ));
+    }
+  }
+  return result;
+}
+
+/// Returns the coverage information for each offset.
+List<bool> _offsetCoverage(List<_CoverageInfo> coverageInfo, int sourceLength) {
+  final offsetCoverage = List.filled(sourceLength, false);
+
+  // Sort coverage information by their size.
+  // Coverage information takes granularity as precedence.
+  coverageInfo.sort((a, b) =>
+      (b.endOffset - b.startOffset).compareTo(a.endOffset - a.startOffset));
+
+  for (var range in coverageInfo) {
+    for (var i = range.startOffset; i < range.endOffset; i++) {
+      offsetCoverage[i] = range.isCovered;
+    }
+  }
+
+  return offsetCoverage;
+}
+
+class _CoverageInfo {
+  _CoverageInfo(this.startOffset, this.endOffset, this.isCovered);
+
+  /// 0 based byte offset.
+  final int startOffset;
+
+  /// 0 based byte offset.
+  final int endOffset;
+
+  final bool isCovered;
+}
+
+/// A covered position in a source file where [line] and [column] are 1 based.
+class _Position {
+  _Position(this.line, this.column);
+
+  final int line;
+  final int column;
+
+  @override
+  int get hashCode => Object.hash(line, column);
+
+  @override
+  bool operator ==(Object o) =>
+      o is _Position && o.line == line && o.column == column;
+}
diff --git a/pkgs/coverage/lib/src/collect.dart b/pkgs/coverage/lib/src/collect.dart
new file mode 100644
index 0000000..76227ba
--- /dev/null
+++ b/pkgs/coverage/lib/src/collect.dart
@@ -0,0 +1,447 @@
+// 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.
+
+import 'dart:async';
+import 'dart:io';
+
+import 'package:vm_service/vm_service.dart';
+
+import 'hitmap.dart';
+import 'isolate_paused_listener.dart';
+import 'util.dart';
+
+const _retryInterval = Duration(milliseconds: 200);
+const _debugTokenPositions = bool.fromEnvironment('DEBUG_COVERAGE');
+
+/// Collects coverage for all isolates in the running VM.
+///
+/// Collects a hit-map containing merged coverage for all isolates in the Dart
+/// VM associated with the specified [serviceUri]. Returns a map suitable for
+/// input to the coverage formatters that ship with this package.
+///
+/// [serviceUri] must specify the http/https URI of the service port of a
+/// running Dart VM and must not be null.
+///
+/// If [resume] is true, all isolates will be resumed once coverage collection
+/// is complete.
+///
+/// If [waitPaused] is true, collection will not begin for an isolate until it
+/// is in the paused state.
+///
+/// If [includeDart] is true, code coverage for core `dart:*` libraries will be
+/// collected.
+///
+/// If [functionCoverage] is true, function coverage information will be
+/// collected.
+///
+/// If [branchCoverage] is true, branch coverage information will be collected.
+/// This will only work correctly if the target VM was run with the
+/// --branch-coverage flag.
+///
+/// If [scopedOutput] is non-empty, coverage will be restricted so that only
+/// scripts that start with any of the provided paths are considered.
+///
+/// If [isolateIds] is set, the coverage gathering will be restricted to only
+/// those VM isolates.
+///
+/// If [coverableLineCache] is set, the collector will avoid recompiling
+/// libraries it has already seen (see VmService.getSourceReport's
+/// librariesAlreadyCompiled parameter). This is only useful when doing more
+/// than one [collect] call over the same libraries. Pass an empty map to the
+/// first call, and then pass the same map to all subsequent calls.
+///
+/// [serviceOverrideForTesting] is for internal testing only, and should not be
+/// set by users.
+Future<Map<String, dynamic>> collect(Uri serviceUri, bool resume,
+    bool waitPaused, bool includeDart, Set<String>? scopedOutput,
+    {Set<String>? isolateIds,
+    Duration? timeout,
+    bool functionCoverage = false,
+    bool branchCoverage = false,
+    Map<String, Set<int>>? coverableLineCache,
+    VmService? serviceOverrideForTesting}) async {
+  scopedOutput ??= <String>{};
+
+  late VmService service;
+  if (serviceOverrideForTesting != null) {
+    service = serviceOverrideForTesting;
+  } else {
+    // Create websocket URI. Handle any trailing slashes.
+    final pathSegments =
+        serviceUri.pathSegments.where((c) => c.isNotEmpty).toList()..add('ws');
+    final uri = serviceUri.replace(scheme: 'ws', pathSegments: pathSegments);
+
+    await retry(() async {
+      try {
+        final options = const CompressionOptions(enabled: false);
+        final socket = await WebSocket.connect('$uri', compression: options);
+        final controller = StreamController<String>();
+        socket.listen((data) => controller.add(data as String), onDone: () {
+          controller.close();
+          service.dispose();
+        });
+        service = VmService(controller.stream, socket.add,
+            log: StdoutLog(), disposeHandler: socket.close);
+        await service.getVM().timeout(_retryInterval);
+      } on TimeoutException {
+        // The signature changed in vm_service version 6.0.0.
+        // ignore: await_only_futures
+        await service.dispose();
+        rethrow;
+      }
+    }, _retryInterval, timeout: timeout);
+  }
+
+  try {
+    return await _getAllCoverage(
+        service,
+        includeDart,
+        functionCoverage,
+        branchCoverage,
+        scopedOutput,
+        isolateIds,
+        coverableLineCache,
+        waitPaused);
+  } finally {
+    if (resume && !waitPaused) {
+      await _resumeIsolates(service);
+    }
+    // The signature changed in vm_service version 6.0.0.
+    // ignore: await_only_futures
+    await service.dispose();
+  }
+}
+
+Future<Map<String, dynamic>> _getAllCoverage(
+    VmService service,
+    bool includeDart,
+    bool functionCoverage,
+    bool branchCoverage,
+    Set<String> scopedOutput,
+    Set<String>? isolateIds,
+    Map<String, Set<int>>? coverableLineCache,
+    bool waitPaused) async {
+  final allCoverage = <Map<String, dynamic>>[];
+
+  final sourceReportKinds = [
+    SourceReportKind.kCoverage,
+    if (branchCoverage) SourceReportKind.kBranchCoverage,
+  ];
+
+  final librariesAlreadyCompiled = coverableLineCache?.keys.toList();
+
+  // Program counters are shared between isolates in the same group. So we need
+  // to make sure we're only gathering coverage data for one isolate in each
+  // group, otherwise we'll double count the hits.
+  final coveredIsolateGroups = <String>{};
+
+  Future<void> collectIsolate(IsolateRef isolateRef) async {
+    if (!(isolateIds?.contains(isolateRef.id) ?? true)) return;
+
+    // coveredIsolateGroups is only relevant for the !waitPaused flow. The
+    // waitPaused flow achieves the same once-per-group behavior using the
+    // isLastIsolateInGroup flag.
+    final isolateGroupId = isolateRef.isolateGroupId;
+    if (isolateGroupId != null) {
+      if (coveredIsolateGroups.contains(isolateGroupId)) return;
+      coveredIsolateGroups.add(isolateGroupId);
+    }
+
+    late final SourceReport isolateReport;
+    try {
+      isolateReport = await service.getSourceReport(
+        isolateRef.id!,
+        sourceReportKinds,
+        forceCompile: true,
+        reportLines: true,
+        libraryFilters: scopedOutput.isNotEmpty
+            ? List.from(scopedOutput.map((filter) => 'package:$filter/'))
+            : null,
+        librariesAlreadyCompiled: librariesAlreadyCompiled,
+      );
+    } on SentinelException {
+      return;
+    }
+
+    final coverage = await _processSourceReport(
+        service,
+        isolateRef,
+        isolateReport,
+        includeDart,
+        functionCoverage,
+        coverableLineCache,
+        scopedOutput);
+    allCoverage.addAll(coverage);
+  }
+
+  if (waitPaused) {
+    await IsolatePausedListener(service,
+            (IsolateRef isolateRef, bool isLastIsolateInGroup) async {
+      if (isLastIsolateInGroup) {
+        await collectIsolate(isolateRef);
+      }
+    }, stderr.writeln)
+        .waitUntilAllExited();
+  } else {
+    for (final isolateRef in await getAllIsolates(service)) {
+      await collectIsolate(isolateRef);
+    }
+  }
+
+  return <String, dynamic>{'type': 'CodeCoverage', 'coverage': allCoverage};
+}
+
+Future _resumeIsolates(VmService service) async {
+  final vm = await service.getVM();
+  final futures = <Future>[];
+  for (var isolateRef in vm.isolates!) {
+    // Guard against sync as well as async errors: sync - when we are writing
+    // message to the socket, the socket might be closed; async - when we are
+    // waiting for the response, the socket again closes.
+    futures.add(Future.sync(() async {
+      final isolate = await service.getIsolate(isolateRef.id!);
+      if (isolate.pauseEvent!.kind != EventKind.kResume) {
+        await service.resume(isolateRef.id!);
+      }
+    }));
+  }
+  try {
+    await Future.wait(futures);
+  } catch (_) {
+    // Ignore resume isolate failures
+  }
+}
+
+/// Returns the line number to which the specified token position maps.
+///
+/// Performs a binary search within the script's token position table to locate
+/// the line in question.
+int? _getLineFromTokenPos(Script script, int tokenPos) {
+  // TODO(cbracken): investigate whether caching this lookup results in
+  // significant performance gains.
+  var min = 0;
+  var max = script.tokenPosTable!.length;
+  while (min < max) {
+    final mid = min + ((max - min) >> 1);
+    final row = script.tokenPosTable![mid];
+    if (row[1] > tokenPos) {
+      max = mid;
+    } else {
+      for (var i = 1; i < row.length; i += 2) {
+        if (row[i] == tokenPos) return row.first;
+      }
+      min = mid + 1;
+    }
+  }
+  return null;
+}
+
+/// Returns a JSON coverage list backward-compatible with pre-1.16.0 SDKs.
+Future<List<Map<String, dynamic>>> _processSourceReport(
+    VmService service,
+    IsolateRef isolateRef,
+    SourceReport report,
+    bool includeDart,
+    bool functionCoverage,
+    Map<String, Set<int>>? coverableLineCache,
+    Set<String> scopedOutput) async {
+  final hitMaps = <Uri, HitMap>{};
+  final scripts = <ScriptRef, Script>{};
+  final libraries = <LibraryRef>{};
+  final needScripts = functionCoverage;
+
+  Future<Script?> getScript(ScriptRef? scriptRef) async {
+    if (scriptRef == null) {
+      return null;
+    }
+    if (!scripts.containsKey(scriptRef)) {
+      scripts[scriptRef] =
+          await service.getObject(isolateRef.id!, scriptRef.id!) as Script;
+    }
+    return scripts[scriptRef];
+  }
+
+  HitMap getHitMap(Uri scriptUri) => hitMaps.putIfAbsent(scriptUri, HitMap.new);
+
+  Future<void> processFunction(FuncRef funcRef) async {
+    final func = await service.getObject(isolateRef.id!, funcRef.id!) as Func;
+    if ((func.implicit ?? false) || (func.isAbstract ?? false)) {
+      return;
+    }
+    final location = func.location;
+    if (location == null) {
+      return;
+    }
+    final script = await getScript(location.script);
+    if (script == null) {
+      return;
+    }
+    final funcName = await _getFuncName(service, isolateRef, func);
+    // TODO(liama): Is this still necessary, or is location.line valid?
+    final tokenPos = location.tokenPos!;
+    final line = _getLineFromTokenPos(script, tokenPos);
+    if (line == null) {
+      if (_debugTokenPositions) {
+        stderr.writeln(
+            'tokenPos $tokenPos in function ${funcRef.name} has no line '
+            'mapping for script ${script.uri!}');
+      }
+      return;
+    }
+    final hits = getHitMap(Uri.parse(script.uri!));
+    hits.funcHits ??= <int, int>{};
+    (hits.funcNames ??= <int, String>{})[line] = funcName;
+  }
+
+  for (var range in report.ranges!) {
+    final scriptRef = report.scripts![range.scriptIndex!];
+    final scriptUriString = scriptRef.uri;
+    if (!scopedOutput.includesScript(scriptUriString)) {
+      // Sometimes a range's script can be different to the function's script
+      // (eg mixins), so we have to re-check the scope filter.
+      // See https://github.com/dart-lang/tools/issues/530
+      continue;
+    }
+    final scriptUri = Uri.parse(scriptUriString!);
+
+    // If we have a coverableLineCache, use it in the same way we use
+    // SourceReportCoverage.misses: to add zeros to the coverage result for all
+    // the lines that don't have a hit. Afterwards, add all the lines that were
+    // hit or missed to the cache, so that the next coverage collection won't
+    // need to compile this library.
+    final coverableLines =
+        coverableLineCache?.putIfAbsent(scriptUriString, () => <int>{});
+
+    // Not returned in scripts section of source report.
+    if (scriptUri.scheme == 'evaluate') continue;
+
+    // Skip scripts from dart:.
+    if (!includeDart && scriptUri.scheme == 'dart') continue;
+
+    // Look up the hit maps for this script (shared across isolates).
+    final hits = getHitMap(scriptUri);
+
+    Script? script;
+    if (needScripts) {
+      script = await getScript(scriptRef);
+      if (script == null) continue;
+    }
+
+    // If the script's library isn't loaded, load it then look up all its funcs.
+    final libRef = script?.library;
+    if (functionCoverage && libRef != null && !libraries.contains(libRef)) {
+      libraries.add(libRef);
+      final library =
+          await service.getObject(isolateRef.id!, libRef.id!) as Library;
+      if (library.functions != null) {
+        for (var funcRef in library.functions!) {
+          await processFunction(funcRef);
+        }
+      }
+      if (library.classes != null) {
+        for (var classRef in library.classes!) {
+          final clazz =
+              await service.getObject(isolateRef.id!, classRef.id!) as Class;
+          if (clazz.functions != null) {
+            for (var funcRef in clazz.functions!) {
+              await processFunction(funcRef);
+            }
+          }
+        }
+      }
+    }
+
+    // Collect hits and misses.
+    final coverage = range.coverage;
+
+    if (coverage == null) continue;
+
+    void forEachLine(List<int>? tokenPositions, void Function(int line) body) {
+      if (tokenPositions == null) return;
+      for (final line in tokenPositions) {
+        body(line);
+      }
+    }
+
+    if (coverableLines != null) {
+      for (final line in coverableLines) {
+        hits.lineHits.putIfAbsent(line, () => 0);
+      }
+    }
+
+    forEachLine(coverage.hits, (line) {
+      hits.lineHits.increment(line);
+      coverableLines?.add(line);
+      if (hits.funcNames != null && hits.funcNames!.containsKey(line)) {
+        hits.funcHits!.increment(line);
+      }
+    });
+    forEachLine(coverage.misses, (line) {
+      hits.lineHits.putIfAbsent(line, () => 0);
+      coverableLines?.add(line);
+    });
+    hits.funcNames?.forEach((line, funcName) {
+      hits.funcHits?.putIfAbsent(line, () => 0);
+    });
+
+    final branchCoverage = range.branchCoverage;
+    if (branchCoverage != null) {
+      hits.branchHits ??= <int, int>{};
+      forEachLine(branchCoverage.hits, (line) {
+        hits.branchHits!.increment(line);
+      });
+      forEachLine(branchCoverage.misses, (line) {
+        hits.branchHits!.putIfAbsent(line, () => 0);
+      });
+    }
+  }
+
+  // Output JSON
+  final coverage = <Map<String, dynamic>>[];
+  hitMaps.forEach((uri, hits) {
+    coverage.add(hitmapToJson(hits, uri));
+  });
+  return coverage;
+}
+
+extension _MapExtension<T> on Map<T, int> {
+  void increment(T key) => this[key] = (this[key] ?? 0) + 1;
+}
+
+Future<String> _getFuncName(
+    VmService service, IsolateRef isolateRef, Func func) async {
+  if (func.name == null) {
+    return '${func.type}:${func.location!.tokenPos}';
+  }
+  final owner = func.owner;
+  if (owner is ClassRef) {
+    final cls = await service.getObject(isolateRef.id!, owner.id!) as Class;
+    if (cls.name != null) return '${cls.name}.${func.name}';
+  }
+  return func.name!;
+}
+
+class StdoutLog extends Log {
+  @override
+  void warning(String message) => print(message);
+
+  @override
+  void severe(String message) => print(message);
+}
+
+extension _ScopedOutput on Set<String> {
+  bool includesScript(String? scriptUriString) {
+    if (scriptUriString == null) return false;
+
+    // If the set is empty, it means the user didn't specify a --scope-output
+    // flag, so allow everything.
+    if (isEmpty) return true;
+
+    final scriptUri = Uri.parse(scriptUriString);
+    if (scriptUri.scheme != 'package') return false;
+
+    final scope = scriptUri.pathSegments.first;
+    return contains(scope);
+  }
+}
diff --git a/pkgs/coverage/lib/src/formatter.dart b/pkgs/coverage/lib/src/formatter.dart
new file mode 100644
index 0000000..a37df73
--- /dev/null
+++ b/pkgs/coverage/lib/src/formatter.dart
@@ -0,0 +1,223 @@
+// 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.
+
+import 'package:glob/glob.dart';
+import 'package:path/path.dart' as p;
+
+import 'hitmap.dart';
+import 'resolver.dart';
+
+@Deprecated('Migrate to FileHitMapsFormatter')
+abstract class Formatter {
+  /// Returns the formatted coverage data.
+  Future<String> format(Map<String, Map<int, int>> hitmap);
+}
+
+/// Converts the given hitmap to lcov format and appends the result to
+/// env.output.
+///
+/// Returns a [Future] that completes as soon as all map entries have been
+/// emitted.
+@Deprecated('Migrate to FileHitMapsFormatter.formatLcov')
+class LcovFormatter implements Formatter {
+  /// Creates a LCOV formatter.
+  ///
+  /// If [reportOn] is provided, coverage report output is limited to files
+  /// prefixed with one of the paths included. If [basePath] is provided, paths
+  /// are reported relative to that path.
+  LcovFormatter(this.resolver, {this.reportOn, this.basePath});
+
+  final Resolver resolver;
+  final String? basePath;
+  final List<String>? reportOn;
+
+  @override
+  Future<String> format(Map<String, Map<int, int>> hitmap) {
+    return Future.value(hitmap
+        .map((key, value) => MapEntry(key, HitMap(value)))
+        .formatLcov(resolver, basePath: basePath, reportOn: reportOn));
+  }
+}
+
+/// Converts the given hitmap to a pretty-print format and appends the result
+/// to env.output.
+///
+/// Returns a [Future] that completes as soon as all map entries have been
+/// emitted.
+@Deprecated('Migrate to FileHitMapsFormatter.prettyPrint')
+class PrettyPrintFormatter implements Formatter {
+  /// Creates a pretty-print formatter.
+  ///
+  /// If [reportOn] is provided, coverage report output is limited to files
+  /// prefixed with one of the paths included.
+  PrettyPrintFormatter(this.resolver, this.loader,
+      {this.reportOn, this.reportFuncs = false});
+
+  final Resolver resolver;
+  final Loader loader;
+  final List<String>? reportOn;
+  final bool reportFuncs;
+
+  @override
+  Future<String> format(Map<String, Map<int, int>> hitmap) {
+    return hitmap.map((key, value) => MapEntry(key, HitMap(value))).prettyPrint(
+        resolver, loader,
+        reportOn: reportOn, reportFuncs: reportFuncs);
+  }
+}
+
+extension FileHitMapsFormatter on Map<String, HitMap> {
+  /// Converts the given hitmap to lcov format.
+  ///
+  /// If [reportOn] is provided, coverage report output is limited to files
+  /// prefixed with one of the paths included. If [basePath] is provided, paths
+  /// are reported relative to that path.
+  String formatLcov(
+    Resolver resolver, {
+    String? basePath,
+    List<String>? reportOn,
+    Set<Glob>? ignoreGlobs,
+  }) {
+    final pathFilter = _getPathFilter(
+      reportOn: reportOn,
+      ignoreGlobs: ignoreGlobs,
+    );
+    final buf = StringBuffer();
+    for (final entry in entries) {
+      final v = entry.value;
+      final lineHits = v.lineHits;
+      final funcHits = v.funcHits;
+      final funcNames = v.funcNames;
+      final branchHits = v.branchHits;
+      var source = resolver.resolve(entry.key);
+      if (source == null) {
+        continue;
+      }
+
+      if (!pathFilter(source)) {
+        continue;
+      }
+
+      if (basePath != null) {
+        source = p.relative(source, from: basePath);
+      }
+
+      buf.write('SF:$source\n');
+      if (funcHits != null && funcNames != null) {
+        for (final k in funcNames.keys.toList()..sort()) {
+          buf.write('FN:$k,${funcNames[k]}\n');
+        }
+        for (final k in funcHits.keys.toList()..sort()) {
+          if (funcHits[k]! != 0) {
+            buf.write('FNDA:${funcHits[k]},${funcNames[k]}\n');
+          }
+        }
+        buf.write('FNF:${funcNames.length}\n');
+        buf.write('FNH:${funcHits.values.where((v) => v > 0).length}\n');
+      }
+      for (final k in lineHits.keys.toList()..sort()) {
+        buf.write('DA:$k,${lineHits[k]}\n');
+      }
+      buf.write('LF:${lineHits.length}\n');
+      buf.write('LH:${lineHits.values.where((v) => v > 0).length}\n');
+      if (branchHits != null) {
+        for (final k in branchHits.keys.toList()..sort()) {
+          buf.write('BRDA:$k,0,0,${branchHits[k]}\n');
+        }
+      }
+      buf.write('end_of_record\n');
+    }
+
+    return buf.toString();
+  }
+
+  /// Converts the given hitmap to a pretty-print format.
+  ///
+  /// If [reportOn] is provided, coverage report output is limited to files
+  /// prefixed with one of the paths included. If [reportFuncs] is provided,
+  /// only function coverage information will be shown.
+  Future<String> prettyPrint(
+    Resolver resolver,
+    Loader loader, {
+    List<String>? reportOn,
+    Set<Glob>? ignoreGlobs,
+    bool reportFuncs = false,
+    bool reportBranches = false,
+  }) async {
+    final pathFilter = _getPathFilter(
+      reportOn: reportOn,
+      ignoreGlobs: ignoreGlobs,
+    );
+    final buf = StringBuffer();
+    for (final entry in entries) {
+      final v = entry.value;
+      if (reportFuncs && v.funcHits == null) {
+        throw StateError(
+          'Function coverage formatting was requested, but the hit map is '
+          'missing function coverage information. Did you run '
+          'collect_coverage with the --function-coverage flag?',
+        );
+      }
+      if (reportBranches && v.branchHits == null) {
+        throw StateError(
+            'Branch coverage formatting was requested, but the hit map is '
+            'missing branch coverage information. Did you run '
+            'collect_coverage with the --branch-coverage flag?');
+      }
+      final hits = reportFuncs
+          ? v.funcHits!
+          : reportBranches
+              ? v.branchHits!
+              : v.lineHits;
+      final source = resolver.resolve(entry.key);
+      if (source == null) {
+        continue;
+      }
+
+      if (!pathFilter(source)) {
+        continue;
+      }
+
+      final lines = await loader.load(source);
+      if (lines == null) {
+        continue;
+      }
+      buf.writeln(source);
+      for (var line = 1; line <= lines.length; line++) {
+        var prefix = _prefix;
+        if (hits.containsKey(line)) {
+          prefix = hits[line].toString().padLeft(_prefix.length);
+        }
+        buf.writeln('$prefix|${lines[line - 1]}');
+      }
+    }
+
+    return buf.toString();
+  }
+}
+
+const _prefix = '       ';
+
+typedef _PathFilter = bool Function(String path);
+
+_PathFilter _getPathFilter({List<String>? reportOn, Set<Glob>? ignoreGlobs}) {
+  if (reportOn == null && ignoreGlobs == null) return (String path) => true;
+
+  final absolutePaths = reportOn?.map(p.canonicalize).toList();
+
+  return (String path) {
+    final canonicalizedPath = p.canonicalize(path);
+
+    if (absolutePaths != null &&
+        !absolutePaths.any(canonicalizedPath.startsWith)) {
+      return false;
+    }
+    if (ignoreGlobs != null &&
+        ignoreGlobs.any((glob) => glob.matches(canonicalizedPath))) {
+      return false;
+    }
+
+    return true;
+  };
+}
diff --git a/pkgs/coverage/lib/src/hitmap.dart b/pkgs/coverage/lib/src/hitmap.dart
new file mode 100644
index 0000000..4c3b468
--- /dev/null
+++ b/pkgs/coverage/lib/src/hitmap.dart
@@ -0,0 +1,386 @@
+// 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.
+
+import 'dart:convert' show json;
+import 'dart:io';
+
+import 'resolver.dart';
+import 'util.dart';
+
+/// Contains line and function hit information for a single script.
+class HitMap {
+  /// Constructs a HitMap.
+  HitMap([
+    Map<int, int>? lineHits,
+    this.funcHits,
+    this.funcNames,
+    this.branchHits,
+  ]) : lineHits = lineHits ?? {};
+
+  /// Map from line to hit count for that line.
+  final Map<int, int> lineHits;
+
+  /// Map from the first line of each function, to the hit count for that
+  /// function. Null if function coverage info was not gathered.
+  Map<int, int>? funcHits;
+
+  /// Map from the first line of each function, to the function name. Null if
+  /// function coverage info was not gathered.
+  Map<int, String>? funcNames;
+
+  /// Map from branch line, to the hit count for that branch. Null if branch
+  /// coverage info was not gathered.
+  Map<int, int>? branchHits;
+
+  /// Creates a single hitmap from a raw json object.
+  ///
+  /// Note that when [checkIgnoredLines] is `true` all files will be
+  /// read to get ignore comments. This will add some overhead.
+  /// To combat this when calling this function multiple times from the
+  /// same source (e.g. test runs of different files) a cache is taken
+  /// via [ignoredLinesInFilesCache]. If this cache contains the parsed
+  /// data for the specific file already, the file will not be read and
+  /// parsed again.
+  ///
+  /// Throws away all entries that are not resolvable.
+  static Map<String, HitMap> parseJsonSync(
+    List<Map<String, dynamic>> jsonResult, {
+    required bool checkIgnoredLines,
+    required Map<String, List<List<int>>?> ignoredLinesInFilesCache,
+    required Resolver resolver,
+  }) {
+    final loader = Loader();
+
+    // Map of source file to map of line to hit count for that line.
+    final globalHitMap = <String, HitMap>{};
+
+    for (var e in jsonResult) {
+      final source = e['source'] as String?;
+      if (source == null) {
+        // Couldn't resolve import, so skip this entry.
+        continue;
+      }
+
+      var ignoredLinesList = <List<int>>[];
+
+      if (checkIgnoredLines) {
+        if (ignoredLinesInFilesCache.containsKey(source)) {
+          final cacheHit = ignoredLinesInFilesCache[source];
+          if (cacheHit == null) {
+            // Null-entry indicates that the whole file was ignored.
+            continue;
+          }
+          ignoredLinesList = cacheHit;
+        } else {
+          final path = resolver.resolve(source);
+          if (path != null) {
+            final lines = loader.loadSync(path) ?? [];
+            ignoredLinesList = getIgnoredLines(path, lines);
+
+            // Ignore the whole file.
+            if (ignoredLinesList.length == 1 &&
+                ignoredLinesList[0][0] == 0 &&
+                ignoredLinesList[0][1] == lines.length) {
+              // Null-entry indicates that the whole file was ignored.
+              ignoredLinesInFilesCache[source] = null;
+              continue;
+            }
+            ignoredLinesInFilesCache[source] = ignoredLinesList;
+          } else {
+            // Couldn't resolve source. Allow cache to answer next time
+            // anyway.
+            ignoredLinesInFilesCache[source] = ignoredLinesList;
+          }
+        }
+      }
+
+      // Move to the first ignore range.
+      final ignoredLines = ignoredLinesList.iterator;
+      var hasCurrent = ignoredLines.moveNext();
+
+      bool shouldIgnoreLine(Iterator<List<int>> ignoredRanges, int line) {
+        if (!hasCurrent || ignoredRanges.current.isEmpty) {
+          return false;
+        }
+
+        if (line < ignoredRanges.current[0]) return false;
+
+        while (hasCurrent &&
+            ignoredRanges.current.isNotEmpty &&
+            ignoredRanges.current[1] < line) {
+          hasCurrent = ignoredRanges.moveNext();
+        }
+
+        if (hasCurrent &&
+            ignoredRanges.current.isNotEmpty &&
+            ignoredRanges.current[0] <= line &&
+            line <= ignoredRanges.current[1]) {
+          return true;
+        }
+
+        return false;
+      }
+
+      void addToMap(Map<int, int> map, int line, int count) {
+        final oldCount = map.putIfAbsent(line, () => 0);
+        map[line] = count + oldCount;
+      }
+
+      void fillHitMap(List hits, Map<int, int> hitMap) {
+        // Ignore line annotations require hits to be sorted.
+        hits = _sortHits(hits);
+        // hits is a flat array of the following format:
+        // [ <line|linerange>, <hitcount>,...]
+        // line: number.
+        // linerange: '<line>-<line>'.
+        for (var i = 0; i < hits.length; i += 2) {
+          final k = hits[i];
+          if (k is int) {
+            // Single line.
+            if (shouldIgnoreLine(ignoredLines, k)) continue;
+
+            addToMap(hitMap, k, hits[i + 1] as int);
+          } else if (k is String) {
+            // Linerange. We expand line ranges to actual lines at this point.
+            final splitPos = k.indexOf('-');
+            final start = int.parse(k.substring(0, splitPos));
+            final end = int.parse(k.substring(splitPos + 1));
+            for (var j = start; j <= end; j++) {
+              if (shouldIgnoreLine(ignoredLines, j)) continue;
+
+              addToMap(hitMap, j, hits[i + 1] as int);
+            }
+          } else {
+            throw StateError('Expected value of type int or String');
+          }
+        }
+      }
+
+      final sourceHitMap = globalHitMap.putIfAbsent(source, HitMap.new);
+      fillHitMap(e['hits'] as List, sourceHitMap.lineHits);
+      if (e.containsKey('funcHits')) {
+        sourceHitMap.funcHits ??= <int, int>{};
+        fillHitMap(e['funcHits'] as List, sourceHitMap.funcHits!);
+      }
+      if (e.containsKey('funcNames')) {
+        sourceHitMap.funcNames ??= <int, String>{};
+        final funcNames = e['funcNames'] as List;
+        for (var i = 0; i < funcNames.length; i += 2) {
+          sourceHitMap.funcNames![funcNames[i] as int] =
+              funcNames[i + 1] as String;
+        }
+      }
+      if (e.containsKey('branchHits')) {
+        sourceHitMap.branchHits ??= <int, int>{};
+        fillHitMap(e['branchHits'] as List, sourceHitMap.branchHits!);
+      }
+    }
+    return globalHitMap;
+  }
+
+  /// Creates a single hitmap from a raw json object.
+  ///
+  /// Throws away all entries that are not resolvable.
+  static Future<Map<String, HitMap>> parseJson(
+    List<Map<String, dynamic>> jsonResult, {
+    bool checkIgnoredLines = false,
+    @Deprecated('Use packagePath') String? packagesPath,
+    String? packagePath,
+  }) async {
+    final resolver = await Resolver.create(
+        packagesPath: packagesPath, packagePath: packagePath);
+    return parseJsonSync(jsonResult,
+        checkIgnoredLines: checkIgnoredLines,
+        ignoredLinesInFilesCache: {},
+        resolver: resolver);
+  }
+
+  /// Generates a merged hitmap from a set of coverage JSON files.
+  static Future<Map<String, HitMap>> parseFiles(
+    Iterable<File> files, {
+    bool checkIgnoredLines = false,
+    @Deprecated('Use packagePath') String? packagesPath,
+    String? packagePath,
+  }) async {
+    final globalHitmap = <String, HitMap>{};
+    for (var file in files) {
+      final contents = file.readAsStringSync();
+      final jsonMap = json.decode(contents) as Map<String, dynamic>;
+      if (jsonMap.containsKey('coverage')) {
+        final jsonResult = jsonMap['coverage'] as List;
+        globalHitmap.merge(await HitMap.parseJson(
+          jsonResult.cast<Map<String, dynamic>>(),
+          checkIgnoredLines: checkIgnoredLines,
+          // ignore: deprecated_member_use_from_same_package
+          packagesPath: packagesPath,
+          packagePath: packagePath,
+        ));
+      }
+    }
+    return globalHitmap;
+  }
+}
+
+extension FileHitMaps on Map<String, HitMap> {
+  /// Merges [newMap] into this one.
+  void merge(Map<String, HitMap> newMap) {
+    newMap.forEach((file, v) {
+      final fileResult = this[file];
+      if (fileResult != null) {
+        _mergeHitCounts(v.lineHits, fileResult.lineHits);
+        if (v.funcHits != null) {
+          fileResult.funcHits ??= <int, int>{};
+          _mergeHitCounts(v.funcHits!, fileResult.funcHits!);
+        }
+        if (v.funcNames != null) {
+          fileResult.funcNames ??= <int, String>{};
+          v.funcNames?.forEach((line, name) {
+            fileResult.funcNames![line] = name;
+          });
+        }
+        if (v.branchHits != null) {
+          fileResult.branchHits ??= <int, int>{};
+          _mergeHitCounts(v.branchHits!, fileResult.branchHits!);
+        }
+      } else {
+        this[file] = v;
+      }
+    });
+  }
+
+  static void _mergeHitCounts(Map<int, int> src, Map<int, int> dest) {
+    src.forEach((line, count) {
+      final lineFileResult = dest[line];
+      if (lineFileResult == null) {
+        dest[line] = count;
+      } else {
+        dest[line] = lineFileResult + count;
+      }
+    });
+  }
+}
+
+/// Class containing information about a coverage hit.
+class _HitInfo {
+  _HitInfo(this.firstLine, this.hitRange, this.hitCount);
+
+  /// The line number of the first line of this hit range.
+  final int firstLine;
+
+  /// A hit range is either a number (1 line) or a String of the form
+  /// "start-end" (multi-line range).
+  final dynamic hitRange;
+
+  /// How many times this hit range was executed.
+  final int hitCount;
+}
+
+/// Creates a single hitmap from a raw json object.
+///
+/// Throws away all entries that are not resolvable.
+@Deprecated('Migrate to HitMap.parseJson')
+Future<Map<String, Map<int, int>>> createHitmap(
+  List<Map<String, dynamic>> jsonResult, {
+  bool checkIgnoredLines = false,
+  @Deprecated('Use packagePath') String? packagesPath,
+  String? packagePath,
+}) async {
+  final result = await HitMap.parseJson(
+    jsonResult,
+    checkIgnoredLines: checkIgnoredLines,
+    packagesPath: packagesPath,
+    packagePath: packagePath,
+  );
+  return result.map((key, value) => MapEntry(key, value.lineHits));
+}
+
+/// Merges [newMap] into [result].
+@Deprecated('Migrate to FileHitMaps.merge')
+void mergeHitmaps(
+    Map<String, Map<int, int>> newMap, Map<String, Map<int, int>> result) {
+  newMap.forEach((file, v) {
+    final fileResult = result[file];
+    if (fileResult != null) {
+      v.forEach((line, count) {
+        final lineFileResult = fileResult[line];
+        if (lineFileResult == null) {
+          fileResult[line] = count;
+        } else {
+          fileResult[line] = lineFileResult + count;
+        }
+      });
+    } else {
+      result[file] = v;
+    }
+  });
+}
+
+/// Generates a merged hitmap from a set of coverage JSON files.
+@Deprecated('Migrate to HitMap.parseFiles')
+Future<Map<String, Map<int, int>>> parseCoverage(
+  Iterable<File> files,
+  int _, {
+  bool checkIgnoredLines = false,
+  @Deprecated('Use packagePath') String? packagesPath,
+  String? packagePath,
+}) async {
+  final result = await HitMap.parseFiles(files,
+      checkIgnoredLines: checkIgnoredLines,
+      packagesPath: packagesPath,
+      packagePath: packagePath);
+  return result.map((key, value) => MapEntry(key, value.lineHits));
+}
+
+/// Returns a JSON hit map backward-compatible with pre-1.16.0 SDKs.
+@Deprecated('Will be removed in 2.0.0')
+Map<String, dynamic> toScriptCoverageJson(Uri scriptUri, Map<int, int> hitMap) {
+  return hitmapToJson(HitMap(hitMap), scriptUri);
+}
+
+List<T> _flattenMap<T>(Map map) {
+  final kvs = <T>[];
+  map.forEach((k, v) {
+    kvs.add(k as T);
+    kvs.add(v as T);
+  });
+  return kvs;
+}
+
+/// Returns a JSON hit map backward-compatible with pre-1.16.0 SDKs.
+Map<String, dynamic> hitmapToJson(HitMap hitmap, Uri scriptUri) =>
+    <String, dynamic>{
+      'source': '$scriptUri',
+      'script': {
+        'type': '@Script',
+        'fixedId': true,
+        'id':
+            'libraries/1/scripts/${Uri.encodeComponent(scriptUri.toString())}',
+        'uri': '$scriptUri',
+        '_kind': 'library',
+      },
+      'hits': _flattenMap<int>(hitmap.lineHits),
+      if (hitmap.funcHits != null)
+        'funcHits': _flattenMap<int>(hitmap.funcHits!),
+      if (hitmap.funcNames != null)
+        'funcNames': _flattenMap<dynamic>(hitmap.funcNames!),
+      if (hitmap.branchHits != null)
+        'branchHits': _flattenMap<int>(hitmap.branchHits!),
+    };
+
+/// Sorts the hits array based on the line numbers.
+List _sortHits(List hits) {
+  final structuredHits = <_HitInfo>[];
+  for (var i = 0; i < hits.length - 1; i += 2) {
+    final lineOrLineRange = hits[i];
+    final firstLineInRange = lineOrLineRange is int
+        ? lineOrLineRange
+        : int.parse((lineOrLineRange as String).split('-')[0]);
+    structuredHits.add(_HitInfo(firstLineInRange, hits[i], hits[i + 1] as int));
+  }
+  structuredHits.sort((a, b) => a.firstLine.compareTo(b.firstLine));
+  return structuredHits
+      .map((item) => [item.hitRange, item.hitCount])
+      .expand((item) => item)
+      .toList();
+}
diff --git a/pkgs/coverage/lib/src/isolate_paused_listener.dart b/pkgs/coverage/lib/src/isolate_paused_listener.dart
new file mode 100644
index 0000000..a89a88b
--- /dev/null
+++ b/pkgs/coverage/lib/src/isolate_paused_listener.dart
@@ -0,0 +1,275 @@
+// Copyright (c) 2024, 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.
+
+import 'dart:async';
+import 'dart:collection';
+
+import 'package:meta/meta.dart';
+import 'package:vm_service/vm_service.dart';
+
+import 'util.dart';
+
+typedef SyncIsolateCallback = void Function(IsolateRef isolate);
+typedef AsyncIsolateCallback = Future<void> Function(IsolateRef isolate);
+typedef AsyncIsolatePausedCallback = Future<void> Function(
+    IsolateRef isolate, bool isLastIsolateInGroup);
+typedef AsyncVmServiceEventCallback = Future<void> Function(Event event);
+typedef SyncErrorLogger = void Function(String message);
+
+/// Calls onIsolatePaused whenever an isolate reaches the pause-on-exit state,
+/// and passes a flag stating whether that isolate is the last one in the group.
+class IsolatePausedListener {
+  IsolatePausedListener(this._service, this._onIsolatePaused, this._log);
+
+  final VmService _service;
+  final AsyncIsolatePausedCallback _onIsolatePaused;
+  final SyncErrorLogger _log;
+
+  final _isolateGroups = <String, IsolateGroupState>{};
+
+  int _numNonMainIsolates = 0;
+  final _allNonMainIsolatesExited = Completer<void>();
+  bool _finished = false;
+
+  IsolateRef? _mainIsolate;
+  final _mainIsolatePaused = Completer<bool>();
+
+  /// Starts listening and returns a future that completes when all isolates
+  /// have exited.
+  Future<void> waitUntilAllExited() async {
+    await listenToIsolateLifecycleEvents(_service, _onStart, _onPause, _onExit);
+
+    await _allNonMainIsolatesExited.future;
+
+    // Resume the main isolate.
+    try {
+      if (_mainIsolate != null) {
+        if (await _mainIsolatePaused.future) {
+          await _runCallbackAndResume(_mainIsolate!, true);
+        }
+      }
+    } finally {
+      _finished = true;
+    }
+  }
+
+  IsolateGroupState _getGroup(IsolateRef isolateRef) =>
+      _isolateGroups[isolateRef.isolateGroupId!] ??= IsolateGroupState();
+
+  void _onStart(IsolateRef isolateRef) {
+    if (_finished) return;
+    final group = _getGroup(isolateRef);
+    group.start(isolateRef.id!);
+    if (_mainIsolate == null && _isMainIsolate(isolateRef)) {
+      _mainIsolate = isolateRef;
+    } else {
+      ++_numNonMainIsolates;
+    }
+  }
+
+  Future<void> _onPause(IsolateRef isolateRef) async {
+    if (_finished) return;
+    final group = _getGroup(isolateRef);
+    group.pause(isolateRef.id!);
+    if (isolateRef.id! == _mainIsolate?.id) {
+      _mainIsolatePaused.complete(true);
+
+      // If the main isolate is the only isolate, then _allNonMainIsolatesExited
+      // will never be completed. So check that case here.
+      _checkCompleted();
+    } else {
+      await _runCallbackAndResume(isolateRef, group.noRunningIsolates);
+    }
+  }
+
+  Future<void> _runCallbackAndResume(
+      IsolateRef isolateRef, bool isLastIsolateInGroup) async {
+    if (isLastIsolateInGroup) {
+      _getGroup(isolateRef).collected = true;
+    }
+    try {
+      await _onIsolatePaused(isolateRef, isLastIsolateInGroup);
+    } finally {
+      await _service.resume(isolateRef.id!);
+    }
+  }
+
+  void _onExit(IsolateRef isolateRef) {
+    if (_finished) return;
+    final group = _getGroup(isolateRef);
+    group.exit(isolateRef.id!);
+    if (group.noLiveIsolates && !group.collected) {
+      _log('ERROR: An isolate exited without pausing, causing '
+          'coverage data to be lost for group ${isolateRef.isolateGroupId!}.');
+    }
+    if (isolateRef.id! == _mainIsolate?.id) {
+      if (!_mainIsolatePaused.isCompleted) {
+        // Main isolate exited without pausing.
+        _mainIsolatePaused.complete(false);
+      }
+    } else {
+      --_numNonMainIsolates;
+      _checkCompleted();
+    }
+  }
+
+  void _checkCompleted() {
+    if (_numNonMainIsolates == 0 && !_allNonMainIsolatesExited.isCompleted) {
+      _allNonMainIsolatesExited.complete();
+    }
+  }
+
+  static bool _isMainIsolate(IsolateRef isolateRef) {
+    // HACK: This should pretty reliably detect the main isolate, but it's not
+    // foolproof and relies on unstable features. The Dart standalone embedder
+    // and Flutter both call the main isolate "main", and they both also list
+    // this isolate first when querying isolates from the VM service. So
+    // selecting the first isolate named "main" combines these conditions and
+    // should be reliable enough for now, while we wait for a better test.
+    // TODO(https://github.com/dart-lang/sdk/issues/56732): Switch to more
+    // reliable test when it's available.
+    return isolateRef.name == 'main';
+  }
+}
+
+/// Listens to isolate start and pause events, and backfills events for isolates
+/// that existed before listening started.
+///
+/// Ensures that:
+///  - Every [onIsolatePaused] and [onIsolateExited] call will be preceeded by
+///    an [onIsolateStarted] call for the same isolate.
+///  - Not every [onIsolateExited] call will be preceeded by a [onIsolatePaused]
+///    call, but a [onIsolatePaused] will never follow a [onIsolateExited].
+///  - [onIsolateExited] will always run after [onIsolatePaused] completes, even
+///    if an exit event arrives while [onIsolatePaused] is being awaited.
+///  - Each callback will only be called once per isolate.
+Future<void> listenToIsolateLifecycleEvents(
+    VmService service,
+    SyncIsolateCallback onIsolateStarted,
+    AsyncIsolateCallback onIsolatePaused,
+    SyncIsolateCallback onIsolateExited) async {
+  final started = <String>{};
+  void onStart(IsolateRef isolateRef) {
+    if (started.add(isolateRef.id!)) onIsolateStarted(isolateRef);
+  }
+
+  final paused = <String, Future<void>>{};
+  Future<void> onPause(IsolateRef isolateRef) async {
+    try {
+      onStart(isolateRef);
+    } finally {
+      await (paused[isolateRef.id!] ??= onIsolatePaused(isolateRef));
+    }
+  }
+
+  final exited = <String>{};
+  Future<void> onExit(IsolateRef isolateRef) async {
+    onStart(isolateRef);
+    if (exited.add(isolateRef.id!)) {
+      try {
+        // Wait for in-progress pause callbacks, and prevent future pause
+        // callbacks from running.
+        await (paused[isolateRef.id!] ??= Future<void>.value());
+      } finally {
+        onIsolateExited(isolateRef);
+      }
+    }
+  }
+
+  final eventBuffer = IsolateEventBuffer((Event event) async {
+    switch (event.kind) {
+      case EventKind.kIsolateStart:
+        return onStart(event.isolate!);
+      case EventKind.kPauseExit:
+        return await onPause(event.isolate!);
+      case EventKind.kIsolateExit:
+        return await onExit(event.isolate!);
+    }
+  });
+
+  // Listen for isolate start/exit events.
+  service.onIsolateEvent.listen(eventBuffer.add);
+  await service.streamListen(EventStreams.kIsolate);
+
+  // Listen for isolate paused events.
+  service.onDebugEvent.listen(eventBuffer.add);
+  await service.streamListen(EventStreams.kDebug);
+
+  // Backfill. Add/pause isolates that existed before we subscribed.
+  for (final isolateRef in await getAllIsolates(service)) {
+    onStart(isolateRef);
+    final isolate = await service.getIsolate(isolateRef.id!);
+    if (isolate.pauseEvent?.kind == EventKind.kPauseExit) {
+      await onPause(isolateRef);
+    }
+  }
+
+  // Flush the buffered stream events, and the start processing them as they
+  // arrive.
+  await eventBuffer.flush();
+}
+
+/// Keeps track of isolates in an isolate group.
+class IsolateGroupState {
+  // IDs of the isolates running in this group.
+  @visibleForTesting
+  final running = <String>{};
+
+  // IDs of the isolates paused just before exiting in this group.
+  @visibleForTesting
+  final paused = <String>{};
+
+  bool collected = false;
+
+  bool get noRunningIsolates => running.isEmpty;
+  bool get noLiveIsolates => running.isEmpty && paused.isEmpty;
+
+  void start(String id) {
+    paused.remove(id);
+    running.add(id);
+  }
+
+  void pause(String id) {
+    running.remove(id);
+    paused.add(id);
+  }
+
+  void exit(String id) {
+    running.remove(id);
+    paused.remove(id);
+  }
+
+  @override
+  String toString() => '{running: $running, paused: $paused}';
+}
+
+/// Buffers VM service isolate [Event]s until [flush] is called.
+///
+/// [flush] passes each buffered event to the handler function. After that, any
+/// further events are immediately passed to the handler. [flush] returns a
+/// future that completes when all the events in the queue have been handled (as
+/// well as any events that arrive while flush is in progress).
+class IsolateEventBuffer {
+  IsolateEventBuffer(this._handler);
+
+  final AsyncVmServiceEventCallback _handler;
+  final _buffer = Queue<Event>();
+  var _flushed = false;
+
+  Future<void> add(Event event) async {
+    if (_flushed) {
+      await _handler(event);
+    } else {
+      _buffer.add(event);
+    }
+  }
+
+  Future<void> flush() async {
+    while (_buffer.isNotEmpty) {
+      final event = _buffer.removeFirst();
+      await _handler(event);
+    }
+    _flushed = true;
+  }
+}
diff --git a/pkgs/coverage/lib/src/resolver.dart b/pkgs/coverage/lib/src/resolver.dart
new file mode 100644
index 0000000..cb5b728
--- /dev/null
+++ b/pkgs/coverage/lib/src/resolver.dart
@@ -0,0 +1,216 @@
+// 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.
+
+import 'dart:io';
+
+import 'package:package_config/package_config.dart';
+import 'package:path/path.dart' as p;
+
+/// [Resolver] resolves imports with respect to a given environment.
+class Resolver {
+  @Deprecated('Use Resolver.create')
+  Resolver({this.packagesPath, this.sdkRoot})
+      : _packages = packagesPath != null ? _parsePackages(packagesPath) : null,
+        packagePath = null;
+
+  Resolver._(
+      {this.packagesPath,
+      this.packagePath,
+      this.sdkRoot,
+      Map<String, Uri>? packages})
+      : _packages = packages;
+
+  static Future<Resolver> create({
+    String? packagesPath,
+    String? packagePath,
+    String? sdkRoot,
+  }) async {
+    return Resolver._(
+      packagesPath: packagesPath,
+      packagePath: packagePath,
+      sdkRoot: sdkRoot,
+      packages: packagesPath != null
+          ? _parsePackages(packagesPath)
+          : (packagePath != null ? await _parsePackage(packagePath) : null),
+    );
+  }
+
+  final String? packagesPath;
+  final String? packagePath;
+  final String? sdkRoot;
+  final List<String> failed = [];
+  final Map<String, Uri>? _packages;
+
+  /// Returns the absolute path wrt. to the given environment or null, if the
+  /// import could not be resolved.
+  String? resolve(String scriptUri) {
+    final uri = Uri.parse(scriptUri);
+    if (uri.scheme == 'dart') {
+      final sdkRoot = this.sdkRoot;
+      if (sdkRoot == null) {
+        // No sdk-root given, do not resolve dart: URIs.
+        return null;
+      }
+      String filePath;
+      if (uri.pathSegments.length > 1) {
+        var path = uri.pathSegments[0];
+        // Drop patch files, since we don't have their source in the compiled
+        // SDK.
+        if (path.endsWith('-patch')) {
+          failed.add('$uri');
+          return null;
+        }
+        // Canonicalize path. For instance: _collection-dev => _collection_dev.
+        path = path.replaceAll('-', '_');
+        final pathSegments = [
+          sdkRoot,
+          path,
+          ...uri.pathSegments.sublist(1),
+        ];
+        filePath = p.joinAll(pathSegments);
+      } else {
+        // Resolve 'dart:something' to be something/something.dart in the SDK.
+        final lib = uri.path;
+        filePath = p.join(sdkRoot, lib, '$lib.dart');
+      }
+      return resolveSymbolicLinks(filePath);
+    }
+    if (uri.scheme == 'package') {
+      final packages = _packages;
+      if (packages == null) {
+        return null;
+      }
+
+      final packageName = uri.pathSegments[0];
+      final packageUri = packages[packageName];
+      if (packageUri == null) {
+        failed.add('$uri');
+        return null;
+      }
+      final packagePath = p.fromUri(packageUri);
+      final pathInPackage = p.joinAll(uri.pathSegments.sublist(1));
+      return resolveSymbolicLinks(p.join(packagePath, pathInPackage));
+    }
+    if (uri.scheme == 'file') {
+      return resolveSymbolicLinks(p.fromUri(uri));
+    }
+    // We cannot deal with anything else.
+    failed.add('$uri');
+    return null;
+  }
+
+  /// Returns a canonicalized path, or `null` if the path cannot be resolved.
+  String? resolveSymbolicLinks(String path) {
+    final normalizedPath = p.normalize(path);
+    final type = FileSystemEntity.typeSync(normalizedPath, followLinks: true);
+    if (type == FileSystemEntityType.notFound) return null;
+    return File(normalizedPath).resolveSymbolicLinksSync();
+  }
+
+  static Map<String, Uri> _parsePackages(String packagesPath) {
+    final content = File(packagesPath).readAsStringSync();
+    final packagesUri = p.toUri(packagesPath);
+    final parsed =
+        PackageConfig.parseString(content, Uri.base.resolveUri(packagesUri));
+    return {
+      for (var package in parsed.packages) package.name: package.packageUriRoot
+    };
+  }
+
+  static Future<Map<String, Uri>?> _parsePackage(String packagePath) async {
+    final parsed = await findPackageConfig(Directory(packagePath));
+    if (parsed == null) return null;
+    return {
+      for (var package in parsed.packages) package.name: package.packageUriRoot
+    };
+  }
+}
+
+/// Bazel URI resolver.
+class BazelResolver extends Resolver {
+  /// Creates a Bazel resolver with the specified workspace path, if any.
+  BazelResolver({this.workspacePath = ''});
+
+  final String workspacePath;
+
+  /// Returns the absolute path wrt. to the given environment or null, if the
+  /// import could not be resolved.
+  @override
+  String? resolve(String scriptUri) {
+    final uri = Uri.parse(scriptUri);
+    if (uri.scheme == 'dart') {
+      // Ignore the SDK
+      return null;
+    }
+    if (uri.scheme == 'package') {
+      // TODO(cbracken) belongs in a Bazel package
+      return _resolveBazelPackage(uri.pathSegments);
+    }
+    if (uri.scheme == 'file') {
+      final runfilesPathSegment =
+          '.runfiles/$workspacePath'.replaceAll(RegExp(r'/*$'), '/');
+      final runfilesPos = uri.path.indexOf(runfilesPathSegment);
+      if (runfilesPos >= 0) {
+        final pathStart = runfilesPos + runfilesPathSegment.length;
+        return uri.path.substring(pathStart);
+      }
+      return null;
+    }
+    if (uri.scheme == 'https' || uri.scheme == 'http') {
+      return _extractHttpPath(uri);
+    }
+    // We cannot deal with anything else.
+    failed.add('$uri');
+    return null;
+  }
+
+  String _extractHttpPath(Uri uri) {
+    final packagesPos = uri.pathSegments.indexOf('packages');
+    if (packagesPos >= 0) {
+      final workspacePath = uri.pathSegments.sublist(packagesPos + 1);
+      return _resolveBazelPackage(workspacePath);
+    }
+    return uri.pathSegments.join('/');
+  }
+
+  String _resolveBazelPackage(List<String> pathSegments) {
+    // TODO(cbracken) belongs in a Bazel package
+    final packageName = pathSegments[0];
+    final pathInPackage = pathSegments.sublist(1).join('/');
+    final packagePath = packageName.contains('.')
+        ? packageName.replaceAll('.', '/')
+        : 'third_party/dart/$packageName';
+    return '$packagePath/lib/$pathInPackage';
+  }
+}
+
+/// Loads the lines of imported resources.
+class Loader {
+  final List<String> failed = [];
+
+  /// Loads an imported resource and returns a [Future] with a [List] of lines.
+  /// Returns `null` if the resource could not be loaded.
+  Future<List<String>?> load(String path) async {
+    try {
+      // Ensure `readAsLines` runs within the try block so errors are caught.
+      return await File(path).readAsLines();
+    } catch (_) {
+      failed.add(path);
+      return null;
+    }
+  }
+
+  /// Loads an imported resource and returns a [List] of lines.
+  /// Returns `null` if the resource could not be loaded.
+  List<String>? loadSync(String path) {
+    try {
+      // Ensure `readAsLinesSync` runs within the try block so errors are
+      // caught.
+      return File(path).readAsLinesSync();
+    } catch (_) {
+      failed.add(path);
+      return null;
+    }
+  }
+}
diff --git a/pkgs/coverage/lib/src/run_and_collect.dart b/pkgs/coverage/lib/src/run_and_collect.dart
new file mode 100644
index 0000000..f2a9cbc
--- /dev/null
+++ b/pkgs/coverage/lib/src/run_and_collect.dart
@@ -0,0 +1,50 @@
+// Copyright (c) 2015, 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.
+
+import 'dart:async';
+import 'dart:io';
+
+import 'collect.dart';
+import 'util.dart';
+
+Future<Map<String, dynamic>> runAndCollect(String scriptPath,
+    {List<String>? scriptArgs,
+    bool checked = false,
+    bool includeDart = false,
+    Duration? timeout}) async {
+  final dartArgs = [
+    '--enable-vm-service',
+    '--pause_isolates_on_exit',
+    if (checked) '--checked',
+    scriptPath,
+    ...?scriptArgs,
+  ];
+
+  final process = await Process.start(Platform.executable, dartArgs);
+
+  final serviceUri = await serviceUriFromProcess(process.stdout.lines());
+  Map<String, dynamic> coverage;
+  try {
+    coverage = await collect(
+      serviceUri,
+      true,
+      true,
+      includeDart,
+      <String>{},
+      timeout: timeout,
+    );
+  } finally {
+    await process.stderr.drain<void>();
+  }
+  final exitStatus = await process.exitCode;
+  if (exitStatus != 0) {
+    throw ProcessException(
+      Platform.executable,
+      dartArgs,
+      'Process failed.',
+      exitStatus,
+    );
+  }
+  return coverage;
+}
diff --git a/pkgs/coverage/lib/src/util.dart b/pkgs/coverage/lib/src/util.dart
new file mode 100644
index 0000000..cc7f584
--- /dev/null
+++ b/pkgs/coverage/lib/src/util.dart
@@ -0,0 +1,186 @@
+// 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.
+
+import 'dart:async';
+import 'dart:convert';
+import 'dart:io';
+
+import 'package:vm_service/vm_service.dart';
+
+// TODO(cbracken) make generic
+/// Retries the specified function with the specified interval and returns
+/// the result on successful completion.
+Future<dynamic> retry(Future Function() f, Duration interval,
+    {Duration? timeout}) async {
+  var keepGoing = true;
+
+  Future<dynamic> withTimeout(Future Function() f, {Duration? duration}) {
+    if (duration == null) {
+      return f();
+    }
+
+    return f().timeout(duration, onTimeout: () {
+      keepGoing = false;
+      final msg = duration.inSeconds == 0
+          ? '${duration.inMilliseconds}ms'
+          : '${duration.inSeconds}s';
+      throw StateError('Failed to complete within $msg');
+    });
+  }
+
+  return withTimeout(() async {
+    while (keepGoing) {
+      try {
+        return await f();
+      } catch (_) {
+        if (keepGoing) {
+          await Future<dynamic>.delayed(interval);
+        }
+      }
+    }
+  }, duration: timeout);
+}
+
+/// Scrapes and returns the Dart VM service URI from a string, or null if not
+/// found.
+///
+/// Potentially useful as a means to extract it from log statements.
+Uri? extractVMServiceUri(String str) {
+  final listeningMessageRegExp = RegExp(
+    r'(?:Observatory|The Dart VM service is) listening on ((http|//)[a-zA-Z0-9:/=_\-\.\[\]]+)',
+  );
+  final match = listeningMessageRegExp.firstMatch(str);
+  if (match != null) {
+    return Uri.parse(match[1]!);
+  }
+  return null;
+}
+
+/// Returns an open port by creating a temporary Socket
+Future<int> getOpenPort() async {
+  ServerSocket socket;
+
+  try {
+    socket = await ServerSocket.bind(InternetAddress.loopbackIPv4, 0);
+  } catch (_) {
+    // try again v/ V6 only. Slight possibility that V4 is disabled
+    socket =
+        await ServerSocket.bind(InternetAddress.loopbackIPv6, 0, v6Only: true);
+  }
+
+  try {
+    return socket.port;
+  } finally {
+    await socket.close();
+  }
+}
+
+final muliLineIgnoreStart = RegExp(r'//\s*coverage:ignore-start[\w\d\s]*$');
+final muliLineIgnoreEnd = RegExp(r'//\s*coverage:ignore-end[\w\d\s]*$');
+final singleLineIgnore = RegExp(r'//\s*coverage:ignore-line[\w\d\s]*$');
+final ignoreFile = RegExp(r'//\s*coverage:ignore-file[\w\d\s]*$');
+
+/// Return list containing inclusive range of lines to be ignored by coverage.
+/// If there is a error in balancing the statements it will throw a
+/// [FormatException],
+/// unless `coverage:ignore-file` is found.
+/// Return [0, lines.length] if the whole file is ignored.
+///
+/// ```
+/// 1.  final str = ''; // coverage:ignore-line
+/// 2.  final str = '';
+/// 3.  final str = ''; // coverage:ignore-start
+/// 4.  final str = '';
+/// 5.  final str = ''; // coverage:ignore-end
+/// ```
+///
+/// Returns
+/// ```
+/// [
+///   [1,1],
+///   [3,5],
+/// ]
+/// ```
+///
+List<List<int>> getIgnoredLines(String filePath, List<String>? lines) {
+  final ignoredLines = <List<int>>[];
+  if (lines == null) return ignoredLines;
+
+  final allLines = [
+    [0, lines.length]
+  ];
+
+  FormatException? err;
+  var i = 0;
+  while (i < lines.length) {
+    if (lines[i].contains(ignoreFile)) return allLines;
+
+    if (lines[i].contains(muliLineIgnoreEnd)) {
+      err ??= FormatException(
+        'unmatched coverage:ignore-end found at $filePath:${i + 1}',
+      );
+    }
+
+    if (lines[i].contains(singleLineIgnore)) ignoredLines.add([i + 1, i + 1]);
+
+    if (lines[i].contains(muliLineIgnoreStart)) {
+      final start = i;
+      var isUnmatched = true;
+      ++i;
+      while (i < lines.length) {
+        if (lines[i].contains(ignoreFile)) return allLines;
+        if (lines[i].contains(muliLineIgnoreStart)) {
+          err ??= FormatException(
+            'coverage:ignore-start found at $filePath:${i + 1}'
+            ' before previous coverage:ignore-start ended',
+          );
+          break;
+        }
+
+        if (lines[i].contains(muliLineIgnoreEnd)) {
+          ignoredLines.add([start + 1, i + 1]);
+          isUnmatched = false;
+          break;
+        }
+        ++i;
+      }
+
+      if (isUnmatched) {
+        err ??= FormatException(
+          'coverage:ignore-start found at $filePath:${start + 1}'
+          ' has no matching coverage:ignore-end',
+        );
+      }
+    }
+    ++i;
+  }
+
+  if (err == null) {
+    return ignoredLines;
+  }
+
+  throw err;
+}
+
+extension StandardOutExtension on Stream<List<int>> {
+  Stream<String> lines() =>
+      transform(const SystemEncoding().decoder).transform(const LineSplitter());
+}
+
+Future<Uri> serviceUriFromProcess(Stream<String> procStdout) {
+  // Capture the VM service URI.
+  final serviceUriCompleter = Completer<Uri>();
+  procStdout.listen((line) {
+    if (!serviceUriCompleter.isCompleted) {
+      final serviceUri = extractVMServiceUri(line);
+      if (serviceUri != null) {
+        serviceUriCompleter.complete(serviceUri);
+      }
+    }
+  });
+  return serviceUriCompleter.future;
+}
+
+Future<List<IsolateRef>> getAllIsolates(VmService service) async =>
+    (await service.getVM()).isolates ?? [];
diff --git a/pkgs/coverage/pubspec.yaml b/pkgs/coverage/pubspec.yaml
new file mode 100644
index 0000000..87a96d0
--- /dev/null
+++ b/pkgs/coverage/pubspec.yaml
@@ -0,0 +1,32 @@
+name: coverage
+version: 1.10.0
+description: Coverage data manipulation and formatting
+repository: https://github.com/dart-lang/tools/tree/main/pkgs/coverage
+
+environment:
+  sdk: ^3.4.0
+
+dependencies:
+  args: ^2.0.0
+  glob: ^2.1.2
+  logging: ^1.0.0
+  meta: ^1.0.2
+  package_config: ^2.0.0
+  path: ^1.8.0
+  source_maps: ^0.10.10
+  stack_trace: ^1.10.0
+  vm_service: '>=12.0.0 <15.0.0'
+
+dev_dependencies:
+  benchmark_harness: ^2.2.0
+  build_runner: ^2.3.1
+  dart_flutter_team_lints: ^3.0.0
+  mockito: ^5.4.4
+  test: ^1.24.7
+  test_descriptor: ^2.0.0
+  test_process: ^2.0.0
+
+executables:
+  collect_coverage:
+  format_coverage:
+  test_with_coverage:
diff --git a/pkgs/coverage/test/README.md b/pkgs/coverage/test/README.md
new file mode 100644
index 0000000..8fa00df
--- /dev/null
+++ b/pkgs/coverage/test/README.md
@@ -0,0 +1,9 @@
+## Regenerating mocks
+
+Some of the tests use a mock VmService that is automatically generated by
+Mockito. If the VmService changes, run this command in the root directory of
+this repo to regenerate that mock:
+
+```bash
+dart run build_runner build
+```
diff --git a/pkgs/coverage/test/chrome_test.dart b/pkgs/coverage/test/chrome_test.dart
new file mode 100644
index 0000000..50e7600
--- /dev/null
+++ b/pkgs/coverage/test/chrome_test.dart
@@ -0,0 +1,78 @@
+// Copyright (c) 2020, 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.
+
+// TODO(https://github.com/dart-lang/tools/issues/494): Fix and re-enable this.
+@TestOn('!windows')
+library;
+
+import 'dart:convert';
+import 'dart:io';
+
+import 'package:coverage/coverage.dart';
+import 'package:test/test.dart';
+
+// The scriptId for the main_test.js in the sample report.
+const String mainScriptId = '31';
+
+Future<String> sourceMapProvider(String scriptId) async {
+  if (scriptId != mainScriptId) {
+    return 'something invalid!';
+  }
+  return File('test/test_files/main_test.js.map').readAsString();
+}
+
+Future<String?> sourceProvider(String scriptId) async {
+  if (scriptId != mainScriptId) return null;
+  return File('test/test_files/main_test.js').readAsString();
+}
+
+Future<Uri> sourceUriProvider(String sourceUrl, String scriptId) async =>
+    Uri.parse(sourceUrl);
+
+void main() {
+  test('reports correctly', () async {
+    final preciseCoverage = json.decode(
+        await File('test/test_files/chrome_precise_report.txt')
+            .readAsString()) as List;
+
+    final report = await parseChromeCoverage(
+      preciseCoverage.cast(),
+      sourceProvider,
+      sourceMapProvider,
+      sourceUriProvider,
+    );
+
+    final sourceReport =
+        (report['coverage'] as List<Map<String, dynamic>>).firstWhere(
+      (Map<String, dynamic> report) =>
+          report['source'].toString().contains('main_test.dart'),
+    );
+
+    final expectedHits = {
+      7: 1,
+      11: 1,
+      13: 1,
+      14: 1,
+      17: 0,
+      19: 0,
+      20: 0,
+      22: 1,
+      23: 1,
+      24: 1,
+      25: 1,
+      28: 1,
+      30: 0,
+      32: 1,
+      34: 1,
+      35: 1,
+      36: 1,
+    };
+
+    final hitMap = sourceReport['hits'] as List<int>;
+    expect(hitMap.length, equals(expectedHits.keys.length * 2));
+    for (var i = 0; i < hitMap.length; i += 2) {
+      expect(expectedHits[hitMap[i]], equals(hitMap[i + 1]));
+    }
+  });
+}
diff --git a/pkgs/coverage/test/collect_coverage_api_test.dart b/pkgs/coverage/test/collect_coverage_api_test.dart
new file mode 100644
index 0000000..fd3de43
--- /dev/null
+++ b/pkgs/coverage/test/collect_coverage_api_test.dart
@@ -0,0 +1,157 @@
+// Copyright (c) 2015, 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.
+
+import 'dart:async';
+
+import 'package:coverage/coverage.dart';
+import 'package:coverage/src/util.dart';
+import 'package:path/path.dart' as p;
+import 'package:test/test.dart';
+
+import 'test_util.dart';
+
+final _isolateLibPath = p.join('test', 'test_files', 'test_app_isolate.dart');
+
+final _sampleAppFileUri = p.toUri(p.absolute(testAppPath)).toString();
+final _isolateLibFileUri = p.toUri(p.absolute(_isolateLibPath)).toString();
+
+void main() {
+  test('collect_coverage_api', () async {
+    final coverage = coverageDataFromJson(await _collectCoverage());
+    expect(coverage, isNotEmpty);
+
+    final sources = coverage.sources();
+
+    for (var sampleCoverageData in sources[_sampleAppFileUri]!) {
+      expect(sampleCoverageData['hits'], isNotEmpty);
+    }
+
+    for (var sampleCoverageData in sources[_isolateLibFileUri]!) {
+      expect(sampleCoverageData['hits'], isNotEmpty);
+    }
+  });
+
+  test('collect_coverage_api with scoped output', () async {
+    final coverage = coverageDataFromJson(
+      await _collectCoverage(scopedOutput: <String>{}..add('coverage')),
+    );
+    expect(coverage, isNotEmpty);
+
+    final sources = coverage.sources();
+
+    for (var key in sources.keys) {
+      final uri = Uri.parse(key);
+      expect(uri.path.startsWith('coverage'), isTrue);
+    }
+  });
+
+  test('collect_coverage_api with isolateIds', () async {
+    final coverage =
+        coverageDataFromJson(await _collectCoverage(isolateIds: true));
+    expect(coverage, isEmpty);
+  });
+
+  test('collect_coverage_api with function coverage', () async {
+    final coverage =
+        coverageDataFromJson(await _collectCoverage(functionCoverage: true));
+    expect(coverage, isNotEmpty);
+
+    final sources = coverage.sources();
+
+    final functionInfo = functionInfoFromSources(sources);
+
+    expect(
+      functionInfo[_sampleAppFileUri]!,
+      {
+        'main': 1,
+        'usedMethod': 1,
+        'unusedMethod': 0,
+      },
+    );
+
+    expect(
+      functionInfo[_isolateLibFileUri]!,
+      {
+        'BarClass.BarClass': 1,
+        'fooAsync': 1,
+        'fooSync': 1,
+        'isolateTask': 1,
+        'BarClass.baz': 1
+      },
+    );
+  });
+
+  test('collect_coverage_api with branch coverage', () async {
+    final coverage =
+        coverageDataFromJson(await _collectCoverage(branchCoverage: true));
+    expect(coverage, isNotEmpty);
+
+    final sources = coverage.sources();
+
+    // Dart VM versions before 2.17 don't support branch coverage.
+    expect(sources[_sampleAppFileUri],
+        everyElement(containsPair('branchHits', isNotEmpty)));
+    expect(sources[_isolateLibFileUri],
+        everyElement(containsPair('branchHits', isNotEmpty)));
+  });
+
+  test('collect_coverage_api with coverableLineCache', () async {
+    final coverableLineCache = <String, Set<int>>{};
+    final coverage =
+        await _collectCoverage(coverableLineCache: coverableLineCache);
+    final result = await HitMap.parseJson(
+        coverage['coverage'] as List<Map<String, dynamic>>);
+
+    expect(coverableLineCache, contains(_sampleAppFileUri));
+    expect(coverableLineCache, contains(_isolateLibFileUri));
+
+    // Expect that we have some missed lines.
+    expect(result[_sampleAppFileUri]!.lineHits.containsValue(0), isTrue);
+    expect(result[_isolateLibFileUri]!.lineHits.containsValue(0), isTrue);
+
+    // Clear _sampleAppFileUri's cache entry, then gather coverage again. We're
+    // doing this to verify that force compilation is disabled for these
+    // libraries. The result should be that _isolateLibFileUri should be the
+    // same, but _sampleAppFileUri should be missing all its missed lines.
+    coverableLineCache[_sampleAppFileUri] = {};
+    final coverage2 =
+        await _collectCoverage(coverableLineCache: coverableLineCache);
+    final result2 = await HitMap.parseJson(
+        coverage2['coverage'] as List<Map<String, dynamic>>);
+
+    // _isolateLibFileUri still has missed lines, but _sampleAppFileUri doesn't.
+    expect(result2[_sampleAppFileUri]!.lineHits.containsValue(0), isFalse);
+    expect(result2[_isolateLibFileUri]!.lineHits.containsValue(0), isTrue);
+
+    // _isolateLibFileUri is the same. _sampleAppFileUri is the same, but
+    // without all its missed lines.
+    expect(result2[_isolateLibFileUri]!.lineHits,
+        result[_isolateLibFileUri]!.lineHits);
+    result[_sampleAppFileUri]!.lineHits.removeWhere((line, hits) => hits == 0);
+    expect(result2[_sampleAppFileUri]!.lineHits,
+        result[_sampleAppFileUri]!.lineHits);
+  }, skip: !platformVersionCheck(3, 2));
+}
+
+Future<Map<String, dynamic>> _collectCoverage(
+    {Set<String> scopedOutput = const {},
+    bool isolateIds = false,
+    bool functionCoverage = false,
+    bool branchCoverage = false,
+    Map<String, Set<int>>? coverableLineCache}) async {
+  final openPort = await getOpenPort();
+
+  // run the sample app, with the right flags
+  final sampleProcess = await runTestApp(openPort);
+
+  final serviceUri = await serviceUriFromProcess(sampleProcess.stdoutStream());
+  final isolateIdSet = isolateIds ? <String>{} : null;
+
+  return collect(serviceUri, true, true, false, scopedOutput,
+      timeout: timeout,
+      isolateIds: isolateIdSet,
+      functionCoverage: functionCoverage,
+      branchCoverage: branchCoverage,
+      coverableLineCache: coverableLineCache);
+}
diff --git a/pkgs/coverage/test/collect_coverage_mock_test.dart b/pkgs/coverage/test/collect_coverage_mock_test.dart
new file mode 100644
index 0000000..372bd48
--- /dev/null
+++ b/pkgs/coverage/test/collect_coverage_mock_test.dart
@@ -0,0 +1,416 @@
+// Copyright (c) 2022, 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.
+
+import 'package:coverage/coverage.dart';
+import 'package:mockito/annotations.dart';
+import 'package:mockito/mockito.dart';
+import 'package:test/test.dart';
+import 'package:vm_service/vm_service.dart';
+
+import 'collect_coverage_mock_test.mocks.dart';
+
+@GenerateMocks([VmService])
+SourceReportRange _range(int scriptIndex, SourceReportCoverage coverage) =>
+    SourceReportRange(scriptIndex: scriptIndex, coverage: coverage);
+
+IsolateRef _isoRef(String id, String isoGroupId) =>
+    IsolateRef(id: id, isolateGroupId: isoGroupId);
+
+IsolateGroupRef _isoGroupRef(String id) => IsolateGroupRef(id: id);
+
+IsolateGroup _isoGroup(String id, List<IsolateRef> isolates) =>
+    IsolateGroup(id: id, isolates: isolates);
+
+class FakeSentinelException implements SentinelException {
+  @override
+  dynamic noSuchMethod(Invocation invocation) {}
+}
+
+MockVmService _mockService(
+  int majorVersion,
+  int minorVersion, {
+  Map<String, List<String>> isolateGroups = const {
+    'isolateGroup': ['isolate'],
+  },
+}) {
+  final service = MockVmService();
+  final isoRefs = <IsolateRef>[];
+  final isoGroupRefs = <IsolateGroupRef>[];
+  final isoGroups = <IsolateGroup>[];
+  for (final group in isolateGroups.entries) {
+    isoGroupRefs.add(_isoGroupRef(group.key));
+    final isosOfGroup = <IsolateRef>[];
+    for (final isoId in group.value) {
+      isosOfGroup.add(_isoRef(isoId, group.key));
+    }
+    isoGroups.add(_isoGroup(group.key, isosOfGroup));
+    isoRefs.addAll(isosOfGroup);
+  }
+  when(service.getVM()).thenAnswer(
+      (_) async => VM(isolates: isoRefs, isolateGroups: isoGroupRefs));
+  for (final group in isoGroups) {
+    when(service.getIsolateGroup(group.id)).thenAnswer((_) async => group);
+  }
+  when(service.getVersion()).thenAnswer(
+      (_) async => Version(major: majorVersion, minor: minorVersion));
+  return service;
+}
+
+void main() {
+  group('Mock VM Service', () {
+    test('Collect coverage', () async {
+      final service = _mockService(4, 13);
+      when(service.getSourceReport(
+        'isolate',
+        ['Coverage'],
+        forceCompile: true,
+        reportLines: true,
+      )).thenAnswer((_) async => SourceReport(
+            ranges: [
+              _range(
+                0,
+                SourceReportCoverage(
+                  hits: [12],
+                  misses: [47],
+                ),
+              ),
+              _range(
+                1,
+                SourceReportCoverage(
+                  hits: [95],
+                  misses: [52],
+                ),
+              ),
+            ],
+            scripts: [
+              ScriptRef(
+                uri: 'package:foo/foo.dart',
+                id: 'foo',
+              ),
+              ScriptRef(
+                uri: 'package:bar/bar.dart',
+                id: 'bar',
+              ),
+            ],
+          ));
+
+      final jsonResult = await collect(Uri(), false, false, false, null,
+          serviceOverrideForTesting: service);
+      final result = await HitMap.parseJson(
+          jsonResult['coverage'] as List<Map<String, dynamic>>);
+
+      expect(result.length, 2);
+      expect(result['package:foo/foo.dart']?.lineHits, {12: 1, 47: 0});
+      expect(result['package:bar/bar.dart']?.lineHits, {95: 1, 52: 0});
+    });
+
+    test('Collect coverage, scoped output', () async {
+      final service = _mockService(4, 13);
+      when(service.getSourceReport(
+        'isolate',
+        ['Coverage'],
+        forceCompile: true,
+        reportLines: true,
+        libraryFilters: ['package:foo/'],
+      )).thenAnswer((_) async => SourceReport(
+            ranges: [
+              _range(
+                0,
+                SourceReportCoverage(
+                  hits: [12],
+                  misses: [47],
+                ),
+              ),
+            ],
+            scripts: [
+              ScriptRef(
+                uri: 'package:foo/foo.dart',
+                id: 'foo',
+              ),
+            ],
+          ));
+
+      final jsonResult = await collect(Uri(), false, false, false, {'foo'},
+          serviceOverrideForTesting: service);
+      final result = await HitMap.parseJson(
+          jsonResult['coverage'] as List<Map<String, dynamic>>);
+
+      expect(result.length, 1);
+      expect(result['package:foo/foo.dart']?.lineHits, {12: 1, 47: 0});
+    });
+
+    test('Collect coverage, fast isolate group deduping', () async {
+      final service = _mockService(4, 13, isolateGroups: {
+        'isolateGroupA': ['isolate1', 'isolate2'],
+        'isolateGroupB': ['isolate3'],
+      });
+      when(service.getSourceReport(
+        'isolate1',
+        ['Coverage'],
+        forceCompile: true,
+        reportLines: true,
+      )).thenAnswer((_) async => SourceReport(
+            ranges: [
+              _range(
+                0,
+                SourceReportCoverage(
+                  hits: [12],
+                  misses: [47],
+                ),
+              ),
+              _range(
+                1,
+                SourceReportCoverage(
+                  hits: [95],
+                  misses: [52],
+                ),
+              ),
+            ],
+            scripts: [
+              ScriptRef(
+                uri: 'package:foo/foo.dart',
+                id: 'foo',
+              ),
+              ScriptRef(
+                uri: 'package:bar/bar.dart',
+                id: 'bar',
+              ),
+            ],
+          ));
+      when(service.getSourceReport(
+        'isolate3',
+        ['Coverage'],
+        forceCompile: true,
+        reportLines: true,
+      )).thenAnswer((_) async => SourceReport(
+            ranges: [
+              _range(
+                0,
+                SourceReportCoverage(
+                  hits: [34],
+                  misses: [61],
+                ),
+              ),
+            ],
+            scripts: [
+              ScriptRef(
+                uri: 'package:baz/baz.dart',
+                id: 'baz',
+              ),
+            ],
+          ));
+
+      final jsonResult = await collect(Uri(), false, false, false, null,
+          serviceOverrideForTesting: service);
+      final result = await HitMap.parseJson(
+          jsonResult['coverage'] as List<Map<String, dynamic>>);
+
+      expect(result.length, 3);
+      expect(result['package:foo/foo.dart']?.lineHits, {12: 1, 47: 0});
+      expect(result['package:bar/bar.dart']?.lineHits, {95: 1, 52: 0});
+      expect(result['package:baz/baz.dart']?.lineHits, {34: 1, 61: 0});
+      verifyNever(service.getSourceReport('isolate2', ['Coverage'],
+          forceCompile: true, reportLines: true));
+      verifyNever(service.getIsolateGroup('isolateGroupA'));
+      verifyNever(service.getIsolateGroup('isolateGroupB'));
+    });
+
+    test(
+        'Collect coverage, no scoped output, '
+        'handles SentinelException from getSourceReport', () async {
+      final service = _mockService(4, 13);
+      when(service.getSourceReport(
+        'isolate',
+        ['Coverage'],
+        forceCompile: true,
+        reportLines: true,
+      )).thenThrow(FakeSentinelException());
+
+      final jsonResult = await collect(Uri(), false, false, false, null,
+          serviceOverrideForTesting: service);
+      final result = await HitMap.parseJson(
+          jsonResult['coverage'] as List<Map<String, dynamic>>);
+
+      expect(result.length, 0);
+    });
+
+    test('Collect coverage, coverableLineCache', () async {
+      // Expect that on the first getSourceReport call, librariesAlreadyCompiled
+      // is empty.
+      final service = _mockService(4, 13);
+      when(service.getSourceReport(
+        'isolate',
+        ['Coverage'],
+        forceCompile: true,
+        reportLines: true,
+        librariesAlreadyCompiled: [],
+      )).thenAnswer((_) async => SourceReport(
+            ranges: [
+              _range(
+                0,
+                SourceReportCoverage(
+                  hits: [12],
+                  misses: [47],
+                ),
+              ),
+              _range(
+                1,
+                SourceReportCoverage(
+                  hits: [95],
+                  misses: [52],
+                ),
+              ),
+            ],
+            scripts: [
+              ScriptRef(
+                uri: 'package:foo/foo.dart',
+                id: 'foo',
+              ),
+              ScriptRef(
+                uri: 'package:bar/bar.dart',
+                id: 'bar',
+              ),
+            ],
+          ));
+
+      final coverableLineCache = <String, Set<int>>{};
+      final jsonResult = await collect(Uri(), false, false, false, null,
+          coverableLineCache: coverableLineCache,
+          serviceOverrideForTesting: service);
+      final result = await HitMap.parseJson(
+          jsonResult['coverage'] as List<Map<String, dynamic>>);
+
+      expect(result.length, 2);
+      expect(result['package:foo/foo.dart']?.lineHits, {12: 1, 47: 0});
+      expect(result['package:bar/bar.dart']?.lineHits, {95: 1, 52: 0});
+
+      // The coverableLineCache should now be filled with all the lines that
+      // were hit or missed.
+      expect(coverableLineCache, {
+        'package:foo/foo.dart': {12, 47},
+        'package:bar/bar.dart': {95, 52},
+      });
+
+      // The second getSourceReport call should now list all the libraries we've
+      // seen. The response won't contain any misses for these libraries,
+      // because they won't be force compiled. We'll also return a 3rd library,
+      // which will contain misses, as it hasn't been compiled yet.
+      when(service.getSourceReport(
+        'isolate',
+        ['Coverage'],
+        forceCompile: true,
+        reportLines: true,
+        librariesAlreadyCompiled: [
+          'package:foo/foo.dart',
+          'package:bar/bar.dart'
+        ],
+      )).thenAnswer((_) async => SourceReport(
+            ranges: [
+              _range(
+                0,
+                SourceReportCoverage(
+                  hits: [47],
+                ),
+              ),
+              _range(
+                1,
+                SourceReportCoverage(
+                  hits: [95],
+                ),
+              ),
+              _range(
+                2,
+                SourceReportCoverage(
+                  hits: [36],
+                  misses: [81],
+                ),
+              ),
+            ],
+            scripts: [
+              ScriptRef(
+                uri: 'package:foo/foo.dart',
+                id: 'foo',
+              ),
+              ScriptRef(
+                uri: 'package:bar/bar.dart',
+                id: 'bar',
+              ),
+              ScriptRef(
+                uri: 'package:baz/baz.dart',
+                id: 'baz',
+              ),
+            ],
+          ));
+
+      final jsonResult2 = await collect(Uri(), false, false, false, null,
+          coverableLineCache: coverableLineCache,
+          serviceOverrideForTesting: service);
+      final result2 = await HitMap.parseJson(
+          jsonResult2['coverage'] as List<Map<String, dynamic>>);
+
+      // The missed lines still appear in foo and bar, even though they weren't
+      // returned in the response. They were read from the cache.
+      expect(result2.length, 3);
+      expect(result2['package:foo/foo.dart']?.lineHits, {12: 0, 47: 1});
+      expect(result2['package:bar/bar.dart']?.lineHits, {95: 1, 52: 0});
+      expect(result2['package:baz/baz.dart']?.lineHits, {36: 1, 81: 0});
+
+      // The coverableLineCache should now also contain the baz library.
+      expect(coverableLineCache, {
+        'package:foo/foo.dart': {12, 47},
+        'package:bar/bar.dart': {95, 52},
+        'package:baz/baz.dart': {36, 81},
+      });
+    });
+
+    test(
+        'Collect coverage, scoped output, '
+        'handles SourceReports that contain unfiltered ranges', () async {
+      // Regression test for https://github.com/dart-lang/tools/issues/530
+      final service = _mockService(4, 13);
+      when(service.getSourceReport(
+        'isolate',
+        ['Coverage'],
+        forceCompile: true,
+        reportLines: true,
+        libraryFilters: ['package:foo/'],
+      )).thenAnswer((_) async => SourceReport(
+            ranges: [
+              _range(
+                0,
+                SourceReportCoverage(
+                  hits: [12],
+                  misses: [47],
+                ),
+              ),
+              _range(
+                1,
+                SourceReportCoverage(
+                  hits: [86],
+                  misses: [91],
+                ),
+              ),
+            ],
+            scripts: [
+              ScriptRef(
+                uri: 'package:foo/foo.dart',
+                id: 'foo',
+              ),
+              ScriptRef(
+                uri: 'package:bar/bar.dart',
+                id: 'bar',
+              ),
+            ],
+          ));
+
+      final jsonResult = await collect(Uri(), false, false, false, {'foo'},
+          serviceOverrideForTesting: service);
+      final result = await HitMap.parseJson(
+          jsonResult['coverage'] as List<Map<String, dynamic>>);
+
+      expect(result.length, 1);
+      expect(result['package:foo/foo.dart']?.lineHits, {12: 1, 47: 0});
+    });
+  });
+}
diff --git a/pkgs/coverage/test/collect_coverage_mock_test.mocks.dart b/pkgs/coverage/test/collect_coverage_mock_test.mocks.dart
new file mode 100644
index 0000000..86f596a
--- /dev/null
+++ b/pkgs/coverage/test/collect_coverage_mock_test.mocks.dart
@@ -0,0 +1,2047 @@
+// Mocks generated by Mockito 5.4.4 from annotations
+// in coverage/test/collect_coverage_mock_test.dart.
+// Do not manually edit this file.
+
+// ignore_for_file: no_leading_underscores_for_library_prefixes
+import 'dart:async' as _i3;
+
+import 'package:mockito/mockito.dart' as _i1;
+import 'package:mockito/src/dummies.dart' as _i4;
+import 'package:vm_service/src/vm_service.dart' as _i2;
+
+// ignore_for_file: type=lint
+// ignore_for_file: avoid_redundant_argument_values
+// ignore_for_file: avoid_setters_without_getters
+// ignore_for_file: comment_references
+// ignore_for_file: deprecated_member_use
+// ignore_for_file: deprecated_member_use_from_same_package
+// ignore_for_file: implementation_imports
+// ignore_for_file: invalid_use_of_visible_for_testing_member
+// ignore_for_file: prefer_const_constructors
+// ignore_for_file: unnecessary_parenthesis
+// ignore_for_file: camel_case_types
+// ignore_for_file: subtype_of_sealed_class
+
+class _FakeBreakpoint_0 extends _i1.SmartFake implements _i2.Breakpoint {
+  _FakeBreakpoint_0(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeSuccess_1 extends _i1.SmartFake implements _i2.Success {
+  _FakeSuccess_1(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeIdZone_2 extends _i1.SmartFake implements _i2.IdZone {
+  _FakeIdZone_2(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeResponse_3 extends _i1.SmartFake implements _i2.Response {
+  _FakeResponse_3(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeAllocationProfile_4 extends _i1.SmartFake
+    implements _i2.AllocationProfile {
+  _FakeAllocationProfile_4(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeCpuSamples_5 extends _i1.SmartFake implements _i2.CpuSamples {
+  _FakeCpuSamples_5(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeClassList_6 extends _i1.SmartFake implements _i2.ClassList {
+  _FakeClassList_6(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeFlagList_7 extends _i1.SmartFake implements _i2.FlagList {
+  _FakeFlagList_7(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeInboundReferences_8 extends _i1.SmartFake
+    implements _i2.InboundReferences {
+  _FakeInboundReferences_8(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeInstanceSet_9 extends _i1.SmartFake implements _i2.InstanceSet {
+  _FakeInstanceSet_9(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeInstanceRef_10 extends _i1.SmartFake implements _i2.InstanceRef {
+  _FakeInstanceRef_10(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeIsolate_11 extends _i1.SmartFake implements _i2.Isolate {
+  _FakeIsolate_11(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeIsolateGroup_12 extends _i1.SmartFake implements _i2.IsolateGroup {
+  _FakeIsolateGroup_12(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeEvent_13 extends _i1.SmartFake implements _i2.Event {
+  _FakeEvent_13(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeMemoryUsage_14 extends _i1.SmartFake implements _i2.MemoryUsage {
+  _FakeMemoryUsage_14(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeScriptList_15 extends _i1.SmartFake implements _i2.ScriptList {
+  _FakeScriptList_15(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeObj_16 extends _i1.SmartFake implements _i2.Obj {
+  _FakeObj_16(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakePerfettoCpuSamples_17 extends _i1.SmartFake
+    implements _i2.PerfettoCpuSamples {
+  _FakePerfettoCpuSamples_17(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakePerfettoTimeline_18 extends _i1.SmartFake
+    implements _i2.PerfettoTimeline {
+  _FakePerfettoTimeline_18(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakePortList_19 extends _i1.SmartFake implements _i2.PortList {
+  _FakePortList_19(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeRetainingPath_20 extends _i1.SmartFake implements _i2.RetainingPath {
+  _FakeRetainingPath_20(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeProcessMemoryUsage_21 extends _i1.SmartFake
+    implements _i2.ProcessMemoryUsage {
+  _FakeProcessMemoryUsage_21(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeStack_22 extends _i1.SmartFake implements _i2.Stack {
+  _FakeStack_22(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeProtocolList_23 extends _i1.SmartFake implements _i2.ProtocolList {
+  _FakeProtocolList_23(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeSourceReport_24 extends _i1.SmartFake implements _i2.SourceReport {
+  _FakeSourceReport_24(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeVersion_25 extends _i1.SmartFake implements _i2.Version {
+  _FakeVersion_25(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeVM_26 extends _i1.SmartFake implements _i2.VM {
+  _FakeVM_26(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeTimeline_27 extends _i1.SmartFake implements _i2.Timeline {
+  _FakeTimeline_27(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeTimelineFlags_28 extends _i1.SmartFake implements _i2.TimelineFlags {
+  _FakeTimelineFlags_28(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeTimestamp_29 extends _i1.SmartFake implements _i2.Timestamp {
+  _FakeTimestamp_29(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeUriList_30 extends _i1.SmartFake implements _i2.UriList {
+  _FakeUriList_30(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeReloadReport_31 extends _i1.SmartFake implements _i2.ReloadReport {
+  _FakeReloadReport_31(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+class _FakeFuture_32<T1> extends _i1.SmartFake implements _i3.Future<T1> {
+  _FakeFuture_32(
+    Object parent,
+    Invocation parentInvocation,
+  ) : super(
+          parent,
+          parentInvocation,
+        );
+}
+
+/// A class which mocks [VmService].
+///
+/// See the documentation for Mockito's code generation for more information.
+class MockVmService extends _i1.Mock implements _i2.VmService {
+  MockVmService() {
+    _i1.throwOnMissingStub(this);
+  }
+
+  @override
+  _i3.Stream<String> get onSend => (super.noSuchMethod(
+        Invocation.getter(#onSend),
+        returnValue: _i3.Stream<String>.empty(),
+      ) as _i3.Stream<String>);
+
+  @override
+  _i3.Stream<String> get onReceive => (super.noSuchMethod(
+        Invocation.getter(#onReceive),
+        returnValue: _i3.Stream<String>.empty(),
+      ) as _i3.Stream<String>);
+
+  @override
+  _i3.Future<void> get onDone => (super.noSuchMethod(
+        Invocation.getter(#onDone),
+        returnValue: _i3.Future<void>.value(),
+      ) as _i3.Future<void>);
+
+  @override
+  _i3.Stream<_i2.Event> get onVMEvent => (super.noSuchMethod(
+        Invocation.getter(#onVMEvent),
+        returnValue: _i3.Stream<_i2.Event>.empty(),
+      ) as _i3.Stream<_i2.Event>);
+
+  @override
+  _i3.Stream<_i2.Event> get onIsolateEvent => (super.noSuchMethod(
+        Invocation.getter(#onIsolateEvent),
+        returnValue: _i3.Stream<_i2.Event>.empty(),
+      ) as _i3.Stream<_i2.Event>);
+
+  @override
+  _i3.Stream<_i2.Event> get onDebugEvent => (super.noSuchMethod(
+        Invocation.getter(#onDebugEvent),
+        returnValue: _i3.Stream<_i2.Event>.empty(),
+      ) as _i3.Stream<_i2.Event>);
+
+  @override
+  _i3.Stream<_i2.Event> get onProfilerEvent => (super.noSuchMethod(
+        Invocation.getter(#onProfilerEvent),
+        returnValue: _i3.Stream<_i2.Event>.empty(),
+      ) as _i3.Stream<_i2.Event>);
+
+  @override
+  _i3.Stream<_i2.Event> get onGCEvent => (super.noSuchMethod(
+        Invocation.getter(#onGCEvent),
+        returnValue: _i3.Stream<_i2.Event>.empty(),
+      ) as _i3.Stream<_i2.Event>);
+
+  @override
+  _i3.Stream<_i2.Event> get onExtensionEvent => (super.noSuchMethod(
+        Invocation.getter(#onExtensionEvent),
+        returnValue: _i3.Stream<_i2.Event>.empty(),
+      ) as _i3.Stream<_i2.Event>);
+
+  @override
+  _i3.Stream<_i2.Event> get onTimelineEvent => (super.noSuchMethod(
+        Invocation.getter(#onTimelineEvent),
+        returnValue: _i3.Stream<_i2.Event>.empty(),
+      ) as _i3.Stream<_i2.Event>);
+
+  @override
+  _i3.Stream<_i2.Event> get onLoggingEvent => (super.noSuchMethod(
+        Invocation.getter(#onLoggingEvent),
+        returnValue: _i3.Stream<_i2.Event>.empty(),
+      ) as _i3.Stream<_i2.Event>);
+
+  @override
+  _i3.Stream<_i2.Event> get onServiceEvent => (super.noSuchMethod(
+        Invocation.getter(#onServiceEvent),
+        returnValue: _i3.Stream<_i2.Event>.empty(),
+      ) as _i3.Stream<_i2.Event>);
+
+  @override
+  _i3.Stream<_i2.Event> get onHeapSnapshotEvent => (super.noSuchMethod(
+        Invocation.getter(#onHeapSnapshotEvent),
+        returnValue: _i3.Stream<_i2.Event>.empty(),
+      ) as _i3.Stream<_i2.Event>);
+
+  @override
+  _i3.Stream<_i2.Event> get onStdoutEvent => (super.noSuchMethod(
+        Invocation.getter(#onStdoutEvent),
+        returnValue: _i3.Stream<_i2.Event>.empty(),
+      ) as _i3.Stream<_i2.Event>);
+
+  @override
+  _i3.Stream<_i2.Event> get onStderrEvent => (super.noSuchMethod(
+        Invocation.getter(#onStderrEvent),
+        returnValue: _i3.Stream<_i2.Event>.empty(),
+      ) as _i3.Stream<_i2.Event>);
+
+  @override
+  _i3.Stream<_i2.Event> onEvent(String? streamId) => (super.noSuchMethod(
+        Invocation.method(
+          #onEvent,
+          [streamId],
+        ),
+        returnValue: _i3.Stream<_i2.Event>.empty(),
+      ) as _i3.Stream<_i2.Event>);
+
+  @override
+  _i3.Future<_i2.Breakpoint> addBreakpoint(
+    String? isolateId,
+    String? scriptId,
+    int? line, {
+    int? column,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #addBreakpoint,
+          [
+            isolateId,
+            scriptId,
+            line,
+          ],
+          {#column: column},
+        ),
+        returnValue: _i3.Future<_i2.Breakpoint>.value(_FakeBreakpoint_0(
+          this,
+          Invocation.method(
+            #addBreakpoint,
+            [
+              isolateId,
+              scriptId,
+              line,
+            ],
+            {#column: column},
+          ),
+        )),
+      ) as _i3.Future<_i2.Breakpoint>);
+
+  @override
+  _i3.Future<_i2.Breakpoint> addBreakpointWithScriptUri(
+    String? isolateId,
+    String? scriptUri,
+    int? line, {
+    int? column,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #addBreakpointWithScriptUri,
+          [
+            isolateId,
+            scriptUri,
+            line,
+          ],
+          {#column: column},
+        ),
+        returnValue: _i3.Future<_i2.Breakpoint>.value(_FakeBreakpoint_0(
+          this,
+          Invocation.method(
+            #addBreakpointWithScriptUri,
+            [
+              isolateId,
+              scriptUri,
+              line,
+            ],
+            {#column: column},
+          ),
+        )),
+      ) as _i3.Future<_i2.Breakpoint>);
+
+  @override
+  _i3.Future<_i2.Breakpoint> addBreakpointAtEntry(
+    String? isolateId,
+    String? functionId,
+  ) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #addBreakpointAtEntry,
+          [
+            isolateId,
+            functionId,
+          ],
+        ),
+        returnValue: _i3.Future<_i2.Breakpoint>.value(_FakeBreakpoint_0(
+          this,
+          Invocation.method(
+            #addBreakpointAtEntry,
+            [
+              isolateId,
+              functionId,
+            ],
+          ),
+        )),
+      ) as _i3.Future<_i2.Breakpoint>);
+
+  @override
+  _i3.Future<_i2.Success> clearCpuSamples(String? isolateId) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #clearCpuSamples,
+          [isolateId],
+        ),
+        returnValue: _i3.Future<_i2.Success>.value(_FakeSuccess_1(
+          this,
+          Invocation.method(
+            #clearCpuSamples,
+            [isolateId],
+          ),
+        )),
+      ) as _i3.Future<_i2.Success>);
+
+  @override
+  _i3.Future<_i2.Success> clearVMTimeline() => (super.noSuchMethod(
+        Invocation.method(
+          #clearVMTimeline,
+          [],
+        ),
+        returnValue: _i3.Future<_i2.Success>.value(_FakeSuccess_1(
+          this,
+          Invocation.method(
+            #clearVMTimeline,
+            [],
+          ),
+        )),
+      ) as _i3.Future<_i2.Success>);
+
+  @override
+  _i3.Future<_i2.IdZone> createIdZone(
+    String? isolateId,
+    String? backingBufferKind,
+    String? idAssignmentPolicy, {
+    int? capacity,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #createIdZone,
+          [
+            isolateId,
+            backingBufferKind,
+            idAssignmentPolicy,
+          ],
+          {#capacity: capacity},
+        ),
+        returnValue: _i3.Future<_i2.IdZone>.value(_FakeIdZone_2(
+          this,
+          Invocation.method(
+            #createIdZone,
+            [
+              isolateId,
+              backingBufferKind,
+              idAssignmentPolicy,
+            ],
+            {#capacity: capacity},
+          ),
+        )),
+      ) as _i3.Future<_i2.IdZone>);
+
+  @override
+  _i3.Future<_i2.Success> deleteIdZone(
+    String? isolateId,
+    String? idZoneId,
+  ) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #deleteIdZone,
+          [
+            isolateId,
+            idZoneId,
+          ],
+        ),
+        returnValue: _i3.Future<_i2.Success>.value(_FakeSuccess_1(
+          this,
+          Invocation.method(
+            #deleteIdZone,
+            [
+              isolateId,
+              idZoneId,
+            ],
+          ),
+        )),
+      ) as _i3.Future<_i2.Success>);
+
+  @override
+  _i3.Future<_i2.Success> invalidateIdZone(
+    String? isolateId,
+    String? idZoneId,
+  ) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #invalidateIdZone,
+          [
+            isolateId,
+            idZoneId,
+          ],
+        ),
+        returnValue: _i3.Future<_i2.Success>.value(_FakeSuccess_1(
+          this,
+          Invocation.method(
+            #invalidateIdZone,
+            [
+              isolateId,
+              idZoneId,
+            ],
+          ),
+        )),
+      ) as _i3.Future<_i2.Success>);
+
+  @override
+  _i3.Future<_i2.Response> invoke(
+    String? isolateId,
+    String? targetId,
+    String? selector,
+    List<String>? argumentIds, {
+    bool? disableBreakpoints,
+    String? idZoneId,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #invoke,
+          [
+            isolateId,
+            targetId,
+            selector,
+            argumentIds,
+          ],
+          {
+            #disableBreakpoints: disableBreakpoints,
+            #idZoneId: idZoneId,
+          },
+        ),
+        returnValue: _i3.Future<_i2.Response>.value(_FakeResponse_3(
+          this,
+          Invocation.method(
+            #invoke,
+            [
+              isolateId,
+              targetId,
+              selector,
+              argumentIds,
+            ],
+            {
+              #disableBreakpoints: disableBreakpoints,
+              #idZoneId: idZoneId,
+            },
+          ),
+        )),
+      ) as _i3.Future<_i2.Response>);
+
+  @override
+  _i3.Future<_i2.Response> evaluate(
+    String? isolateId,
+    String? targetId,
+    String? expression, {
+    Map<String, String>? scope,
+    bool? disableBreakpoints,
+    String? idZoneId,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #evaluate,
+          [
+            isolateId,
+            targetId,
+            expression,
+          ],
+          {
+            #scope: scope,
+            #disableBreakpoints: disableBreakpoints,
+            #idZoneId: idZoneId,
+          },
+        ),
+        returnValue: _i3.Future<_i2.Response>.value(_FakeResponse_3(
+          this,
+          Invocation.method(
+            #evaluate,
+            [
+              isolateId,
+              targetId,
+              expression,
+            ],
+            {
+              #scope: scope,
+              #disableBreakpoints: disableBreakpoints,
+              #idZoneId: idZoneId,
+            },
+          ),
+        )),
+      ) as _i3.Future<_i2.Response>);
+
+  @override
+  _i3.Future<_i2.Response> evaluateInFrame(
+    String? isolateId,
+    int? frameIndex,
+    String? expression, {
+    Map<String, String>? scope,
+    bool? disableBreakpoints,
+    String? idZoneId,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #evaluateInFrame,
+          [
+            isolateId,
+            frameIndex,
+            expression,
+          ],
+          {
+            #scope: scope,
+            #disableBreakpoints: disableBreakpoints,
+            #idZoneId: idZoneId,
+          },
+        ),
+        returnValue: _i3.Future<_i2.Response>.value(_FakeResponse_3(
+          this,
+          Invocation.method(
+            #evaluateInFrame,
+            [
+              isolateId,
+              frameIndex,
+              expression,
+            ],
+            {
+              #scope: scope,
+              #disableBreakpoints: disableBreakpoints,
+              #idZoneId: idZoneId,
+            },
+          ),
+        )),
+      ) as _i3.Future<_i2.Response>);
+
+  @override
+  _i3.Future<_i2.AllocationProfile> getAllocationProfile(
+    String? isolateId, {
+    bool? reset,
+    bool? gc,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #getAllocationProfile,
+          [isolateId],
+          {
+            #reset: reset,
+            #gc: gc,
+          },
+        ),
+        returnValue:
+            _i3.Future<_i2.AllocationProfile>.value(_FakeAllocationProfile_4(
+          this,
+          Invocation.method(
+            #getAllocationProfile,
+            [isolateId],
+            {
+              #reset: reset,
+              #gc: gc,
+            },
+          ),
+        )),
+      ) as _i3.Future<_i2.AllocationProfile>);
+
+  @override
+  _i3.Future<_i2.CpuSamples> getAllocationTraces(
+    String? isolateId, {
+    int? timeOriginMicros,
+    int? timeExtentMicros,
+    String? classId,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #getAllocationTraces,
+          [isolateId],
+          {
+            #timeOriginMicros: timeOriginMicros,
+            #timeExtentMicros: timeExtentMicros,
+            #classId: classId,
+          },
+        ),
+        returnValue: _i3.Future<_i2.CpuSamples>.value(_FakeCpuSamples_5(
+          this,
+          Invocation.method(
+            #getAllocationTraces,
+            [isolateId],
+            {
+              #timeOriginMicros: timeOriginMicros,
+              #timeExtentMicros: timeExtentMicros,
+              #classId: classId,
+            },
+          ),
+        )),
+      ) as _i3.Future<_i2.CpuSamples>);
+
+  @override
+  _i3.Future<_i2.ClassList> getClassList(String? isolateId) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #getClassList,
+          [isolateId],
+        ),
+        returnValue: _i3.Future<_i2.ClassList>.value(_FakeClassList_6(
+          this,
+          Invocation.method(
+            #getClassList,
+            [isolateId],
+          ),
+        )),
+      ) as _i3.Future<_i2.ClassList>);
+
+  @override
+  _i3.Future<_i2.CpuSamples> getCpuSamples(
+    String? isolateId,
+    int? timeOriginMicros,
+    int? timeExtentMicros,
+  ) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #getCpuSamples,
+          [
+            isolateId,
+            timeOriginMicros,
+            timeExtentMicros,
+          ],
+        ),
+        returnValue: _i3.Future<_i2.CpuSamples>.value(_FakeCpuSamples_5(
+          this,
+          Invocation.method(
+            #getCpuSamples,
+            [
+              isolateId,
+              timeOriginMicros,
+              timeExtentMicros,
+            ],
+          ),
+        )),
+      ) as _i3.Future<_i2.CpuSamples>);
+
+  @override
+  _i3.Future<_i2.FlagList> getFlagList() => (super.noSuchMethod(
+        Invocation.method(
+          #getFlagList,
+          [],
+        ),
+        returnValue: _i3.Future<_i2.FlagList>.value(_FakeFlagList_7(
+          this,
+          Invocation.method(
+            #getFlagList,
+            [],
+          ),
+        )),
+      ) as _i3.Future<_i2.FlagList>);
+
+  @override
+  _i3.Future<_i2.InboundReferences> getInboundReferences(
+    String? isolateId,
+    String? targetId,
+    int? limit, {
+    String? idZoneId,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #getInboundReferences,
+          [
+            isolateId,
+            targetId,
+            limit,
+          ],
+          {#idZoneId: idZoneId},
+        ),
+        returnValue:
+            _i3.Future<_i2.InboundReferences>.value(_FakeInboundReferences_8(
+          this,
+          Invocation.method(
+            #getInboundReferences,
+            [
+              isolateId,
+              targetId,
+              limit,
+            ],
+            {#idZoneId: idZoneId},
+          ),
+        )),
+      ) as _i3.Future<_i2.InboundReferences>);
+
+  @override
+  _i3.Future<_i2.InstanceSet> getInstances(
+    String? isolateId,
+    String? objectId,
+    int? limit, {
+    bool? includeSubclasses,
+    bool? includeImplementers,
+    String? idZoneId,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #getInstances,
+          [
+            isolateId,
+            objectId,
+            limit,
+          ],
+          {
+            #includeSubclasses: includeSubclasses,
+            #includeImplementers: includeImplementers,
+            #idZoneId: idZoneId,
+          },
+        ),
+        returnValue: _i3.Future<_i2.InstanceSet>.value(_FakeInstanceSet_9(
+          this,
+          Invocation.method(
+            #getInstances,
+            [
+              isolateId,
+              objectId,
+              limit,
+            ],
+            {
+              #includeSubclasses: includeSubclasses,
+              #includeImplementers: includeImplementers,
+              #idZoneId: idZoneId,
+            },
+          ),
+        )),
+      ) as _i3.Future<_i2.InstanceSet>);
+
+  @override
+  _i3.Future<_i2.InstanceRef> getInstancesAsList(
+    String? isolateId,
+    String? objectId, {
+    bool? includeSubclasses,
+    bool? includeImplementers,
+    String? idZoneId,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #getInstancesAsList,
+          [
+            isolateId,
+            objectId,
+          ],
+          {
+            #includeSubclasses: includeSubclasses,
+            #includeImplementers: includeImplementers,
+            #idZoneId: idZoneId,
+          },
+        ),
+        returnValue: _i3.Future<_i2.InstanceRef>.value(_FakeInstanceRef_10(
+          this,
+          Invocation.method(
+            #getInstancesAsList,
+            [
+              isolateId,
+              objectId,
+            ],
+            {
+              #includeSubclasses: includeSubclasses,
+              #includeImplementers: includeImplementers,
+              #idZoneId: idZoneId,
+            },
+          ),
+        )),
+      ) as _i3.Future<_i2.InstanceRef>);
+
+  @override
+  _i3.Future<_i2.Isolate> getIsolate(String? isolateId) => (super.noSuchMethod(
+        Invocation.method(
+          #getIsolate,
+          [isolateId],
+        ),
+        returnValue: _i3.Future<_i2.Isolate>.value(_FakeIsolate_11(
+          this,
+          Invocation.method(
+            #getIsolate,
+            [isolateId],
+          ),
+        )),
+      ) as _i3.Future<_i2.Isolate>);
+
+  @override
+  _i3.Future<_i2.IsolateGroup> getIsolateGroup(String? isolateGroupId) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #getIsolateGroup,
+          [isolateGroupId],
+        ),
+        returnValue: _i3.Future<_i2.IsolateGroup>.value(_FakeIsolateGroup_12(
+          this,
+          Invocation.method(
+            #getIsolateGroup,
+            [isolateGroupId],
+          ),
+        )),
+      ) as _i3.Future<_i2.IsolateGroup>);
+
+  @override
+  _i3.Future<_i2.Event> getIsolatePauseEvent(String? isolateId) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #getIsolatePauseEvent,
+          [isolateId],
+        ),
+        returnValue: _i3.Future<_i2.Event>.value(_FakeEvent_13(
+          this,
+          Invocation.method(
+            #getIsolatePauseEvent,
+            [isolateId],
+          ),
+        )),
+      ) as _i3.Future<_i2.Event>);
+
+  @override
+  _i3.Future<_i2.MemoryUsage> getMemoryUsage(String? isolateId) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #getMemoryUsage,
+          [isolateId],
+        ),
+        returnValue: _i3.Future<_i2.MemoryUsage>.value(_FakeMemoryUsage_14(
+          this,
+          Invocation.method(
+            #getMemoryUsage,
+            [isolateId],
+          ),
+        )),
+      ) as _i3.Future<_i2.MemoryUsage>);
+
+  @override
+  _i3.Future<_i2.MemoryUsage> getIsolateGroupMemoryUsage(
+          String? isolateGroupId) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #getIsolateGroupMemoryUsage,
+          [isolateGroupId],
+        ),
+        returnValue: _i3.Future<_i2.MemoryUsage>.value(_FakeMemoryUsage_14(
+          this,
+          Invocation.method(
+            #getIsolateGroupMemoryUsage,
+            [isolateGroupId],
+          ),
+        )),
+      ) as _i3.Future<_i2.MemoryUsage>);
+
+  @override
+  _i3.Future<_i2.ScriptList> getScripts(String? isolateId) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #getScripts,
+          [isolateId],
+        ),
+        returnValue: _i3.Future<_i2.ScriptList>.value(_FakeScriptList_15(
+          this,
+          Invocation.method(
+            #getScripts,
+            [isolateId],
+          ),
+        )),
+      ) as _i3.Future<_i2.ScriptList>);
+
+  @override
+  _i3.Future<_i2.Obj> getObject(
+    String? isolateId,
+    String? objectId, {
+    int? offset,
+    int? count,
+    String? idZoneId,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #getObject,
+          [
+            isolateId,
+            objectId,
+          ],
+          {
+            #offset: offset,
+            #count: count,
+            #idZoneId: idZoneId,
+          },
+        ),
+        returnValue: _i3.Future<_i2.Obj>.value(_FakeObj_16(
+          this,
+          Invocation.method(
+            #getObject,
+            [
+              isolateId,
+              objectId,
+            ],
+            {
+              #offset: offset,
+              #count: count,
+              #idZoneId: idZoneId,
+            },
+          ),
+        )),
+      ) as _i3.Future<_i2.Obj>);
+
+  @override
+  _i3.Future<_i2.PerfettoCpuSamples> getPerfettoCpuSamples(
+    String? isolateId, {
+    int? timeOriginMicros,
+    int? timeExtentMicros,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #getPerfettoCpuSamples,
+          [isolateId],
+          {
+            #timeOriginMicros: timeOriginMicros,
+            #timeExtentMicros: timeExtentMicros,
+          },
+        ),
+        returnValue:
+            _i3.Future<_i2.PerfettoCpuSamples>.value(_FakePerfettoCpuSamples_17(
+          this,
+          Invocation.method(
+            #getPerfettoCpuSamples,
+            [isolateId],
+            {
+              #timeOriginMicros: timeOriginMicros,
+              #timeExtentMicros: timeExtentMicros,
+            },
+          ),
+        )),
+      ) as _i3.Future<_i2.PerfettoCpuSamples>);
+
+  @override
+  _i3.Future<_i2.PerfettoTimeline> getPerfettoVMTimeline({
+    int? timeOriginMicros,
+    int? timeExtentMicros,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #getPerfettoVMTimeline,
+          [],
+          {
+            #timeOriginMicros: timeOriginMicros,
+            #timeExtentMicros: timeExtentMicros,
+          },
+        ),
+        returnValue:
+            _i3.Future<_i2.PerfettoTimeline>.value(_FakePerfettoTimeline_18(
+          this,
+          Invocation.method(
+            #getPerfettoVMTimeline,
+            [],
+            {
+              #timeOriginMicros: timeOriginMicros,
+              #timeExtentMicros: timeExtentMicros,
+            },
+          ),
+        )),
+      ) as _i3.Future<_i2.PerfettoTimeline>);
+
+  @override
+  _i3.Future<_i2.PortList> getPorts(String? isolateId) => (super.noSuchMethod(
+        Invocation.method(
+          #getPorts,
+          [isolateId],
+        ),
+        returnValue: _i3.Future<_i2.PortList>.value(_FakePortList_19(
+          this,
+          Invocation.method(
+            #getPorts,
+            [isolateId],
+          ),
+        )),
+      ) as _i3.Future<_i2.PortList>);
+
+  @override
+  _i3.Future<_i2.RetainingPath> getRetainingPath(
+    String? isolateId,
+    String? targetId,
+    int? limit, {
+    String? idZoneId,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #getRetainingPath,
+          [
+            isolateId,
+            targetId,
+            limit,
+          ],
+          {#idZoneId: idZoneId},
+        ),
+        returnValue: _i3.Future<_i2.RetainingPath>.value(_FakeRetainingPath_20(
+          this,
+          Invocation.method(
+            #getRetainingPath,
+            [
+              isolateId,
+              targetId,
+              limit,
+            ],
+            {#idZoneId: idZoneId},
+          ),
+        )),
+      ) as _i3.Future<_i2.RetainingPath>);
+
+  @override
+  _i3.Future<_i2.ProcessMemoryUsage> getProcessMemoryUsage() =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #getProcessMemoryUsage,
+          [],
+        ),
+        returnValue:
+            _i3.Future<_i2.ProcessMemoryUsage>.value(_FakeProcessMemoryUsage_21(
+          this,
+          Invocation.method(
+            #getProcessMemoryUsage,
+            [],
+          ),
+        )),
+      ) as _i3.Future<_i2.ProcessMemoryUsage>);
+
+  @override
+  _i3.Future<_i2.Stack> getStack(
+    String? isolateId, {
+    int? limit,
+    String? idZoneId,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #getStack,
+          [isolateId],
+          {
+            #limit: limit,
+            #idZoneId: idZoneId,
+          },
+        ),
+        returnValue: _i3.Future<_i2.Stack>.value(_FakeStack_22(
+          this,
+          Invocation.method(
+            #getStack,
+            [isolateId],
+            {
+              #limit: limit,
+              #idZoneId: idZoneId,
+            },
+          ),
+        )),
+      ) as _i3.Future<_i2.Stack>);
+
+  @override
+  _i3.Future<_i2.ProtocolList> getSupportedProtocols() => (super.noSuchMethod(
+        Invocation.method(
+          #getSupportedProtocols,
+          [],
+        ),
+        returnValue: _i3.Future<_i2.ProtocolList>.value(_FakeProtocolList_23(
+          this,
+          Invocation.method(
+            #getSupportedProtocols,
+            [],
+          ),
+        )),
+      ) as _i3.Future<_i2.ProtocolList>);
+
+  @override
+  _i3.Future<_i2.SourceReport> getSourceReport(
+    String? isolateId,
+    List<String>? reports, {
+    String? scriptId,
+    int? tokenPos,
+    int? endTokenPos,
+    bool? forceCompile,
+    bool? reportLines,
+    List<String>? libraryFilters,
+    List<String>? librariesAlreadyCompiled,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #getSourceReport,
+          [
+            isolateId,
+            reports,
+          ],
+          {
+            #scriptId: scriptId,
+            #tokenPos: tokenPos,
+            #endTokenPos: endTokenPos,
+            #forceCompile: forceCompile,
+            #reportLines: reportLines,
+            #libraryFilters: libraryFilters,
+            #librariesAlreadyCompiled: librariesAlreadyCompiled,
+          },
+        ),
+        returnValue: _i3.Future<_i2.SourceReport>.value(_FakeSourceReport_24(
+          this,
+          Invocation.method(
+            #getSourceReport,
+            [
+              isolateId,
+              reports,
+            ],
+            {
+              #scriptId: scriptId,
+              #tokenPos: tokenPos,
+              #endTokenPos: endTokenPos,
+              #forceCompile: forceCompile,
+              #reportLines: reportLines,
+              #libraryFilters: libraryFilters,
+              #librariesAlreadyCompiled: librariesAlreadyCompiled,
+            },
+          ),
+        )),
+      ) as _i3.Future<_i2.SourceReport>);
+
+  @override
+  _i3.Future<_i2.Version> getVersion() => (super.noSuchMethod(
+        Invocation.method(
+          #getVersion,
+          [],
+        ),
+        returnValue: _i3.Future<_i2.Version>.value(_FakeVersion_25(
+          this,
+          Invocation.method(
+            #getVersion,
+            [],
+          ),
+        )),
+      ) as _i3.Future<_i2.Version>);
+
+  @override
+  _i3.Future<_i2.VM> getVM() => (super.noSuchMethod(
+        Invocation.method(
+          #getVM,
+          [],
+        ),
+        returnValue: _i3.Future<_i2.VM>.value(_FakeVM_26(
+          this,
+          Invocation.method(
+            #getVM,
+            [],
+          ),
+        )),
+      ) as _i3.Future<_i2.VM>);
+
+  @override
+  _i3.Future<_i2.Timeline> getVMTimeline({
+    int? timeOriginMicros,
+    int? timeExtentMicros,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #getVMTimeline,
+          [],
+          {
+            #timeOriginMicros: timeOriginMicros,
+            #timeExtentMicros: timeExtentMicros,
+          },
+        ),
+        returnValue: _i3.Future<_i2.Timeline>.value(_FakeTimeline_27(
+          this,
+          Invocation.method(
+            #getVMTimeline,
+            [],
+            {
+              #timeOriginMicros: timeOriginMicros,
+              #timeExtentMicros: timeExtentMicros,
+            },
+          ),
+        )),
+      ) as _i3.Future<_i2.Timeline>);
+
+  @override
+  _i3.Future<_i2.TimelineFlags> getVMTimelineFlags() => (super.noSuchMethod(
+        Invocation.method(
+          #getVMTimelineFlags,
+          [],
+        ),
+        returnValue: _i3.Future<_i2.TimelineFlags>.value(_FakeTimelineFlags_28(
+          this,
+          Invocation.method(
+            #getVMTimelineFlags,
+            [],
+          ),
+        )),
+      ) as _i3.Future<_i2.TimelineFlags>);
+
+  @override
+  _i3.Future<_i2.Timestamp> getVMTimelineMicros() => (super.noSuchMethod(
+        Invocation.method(
+          #getVMTimelineMicros,
+          [],
+        ),
+        returnValue: _i3.Future<_i2.Timestamp>.value(_FakeTimestamp_29(
+          this,
+          Invocation.method(
+            #getVMTimelineMicros,
+            [],
+          ),
+        )),
+      ) as _i3.Future<_i2.Timestamp>);
+
+  @override
+  _i3.Future<_i2.Success> pause(String? isolateId) => (super.noSuchMethod(
+        Invocation.method(
+          #pause,
+          [isolateId],
+        ),
+        returnValue: _i3.Future<_i2.Success>.value(_FakeSuccess_1(
+          this,
+          Invocation.method(
+            #pause,
+            [isolateId],
+          ),
+        )),
+      ) as _i3.Future<_i2.Success>);
+
+  @override
+  _i3.Future<_i2.Success> kill(String? isolateId) => (super.noSuchMethod(
+        Invocation.method(
+          #kill,
+          [isolateId],
+        ),
+        returnValue: _i3.Future<_i2.Success>.value(_FakeSuccess_1(
+          this,
+          Invocation.method(
+            #kill,
+            [isolateId],
+          ),
+        )),
+      ) as _i3.Future<_i2.Success>);
+
+  @override
+  _i3.Future<_i2.UriList> lookupResolvedPackageUris(
+    String? isolateId,
+    List<String>? uris, {
+    bool? local,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #lookupResolvedPackageUris,
+          [
+            isolateId,
+            uris,
+          ],
+          {#local: local},
+        ),
+        returnValue: _i3.Future<_i2.UriList>.value(_FakeUriList_30(
+          this,
+          Invocation.method(
+            #lookupResolvedPackageUris,
+            [
+              isolateId,
+              uris,
+            ],
+            {#local: local},
+          ),
+        )),
+      ) as _i3.Future<_i2.UriList>);
+
+  @override
+  _i3.Future<_i2.UriList> lookupPackageUris(
+    String? isolateId,
+    List<String>? uris,
+  ) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #lookupPackageUris,
+          [
+            isolateId,
+            uris,
+          ],
+        ),
+        returnValue: _i3.Future<_i2.UriList>.value(_FakeUriList_30(
+          this,
+          Invocation.method(
+            #lookupPackageUris,
+            [
+              isolateId,
+              uris,
+            ],
+          ),
+        )),
+      ) as _i3.Future<_i2.UriList>);
+
+  @override
+  _i3.Future<_i2.Success> registerService(
+    String? service,
+    String? alias,
+  ) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #registerService,
+          [
+            service,
+            alias,
+          ],
+        ),
+        returnValue: _i3.Future<_i2.Success>.value(_FakeSuccess_1(
+          this,
+          Invocation.method(
+            #registerService,
+            [
+              service,
+              alias,
+            ],
+          ),
+        )),
+      ) as _i3.Future<_i2.Success>);
+
+  @override
+  _i3.Future<_i2.ReloadReport> reloadSources(
+    String? isolateId, {
+    bool? force,
+    bool? pause,
+    String? rootLibUri,
+    String? packagesUri,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #reloadSources,
+          [isolateId],
+          {
+            #force: force,
+            #pause: pause,
+            #rootLibUri: rootLibUri,
+            #packagesUri: packagesUri,
+          },
+        ),
+        returnValue: _i3.Future<_i2.ReloadReport>.value(_FakeReloadReport_31(
+          this,
+          Invocation.method(
+            #reloadSources,
+            [isolateId],
+            {
+              #force: force,
+              #pause: pause,
+              #rootLibUri: rootLibUri,
+              #packagesUri: packagesUri,
+            },
+          ),
+        )),
+      ) as _i3.Future<_i2.ReloadReport>);
+
+  @override
+  _i3.Future<_i2.Success> removeBreakpoint(
+    String? isolateId,
+    String? breakpointId,
+  ) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #removeBreakpoint,
+          [
+            isolateId,
+            breakpointId,
+          ],
+        ),
+        returnValue: _i3.Future<_i2.Success>.value(_FakeSuccess_1(
+          this,
+          Invocation.method(
+            #removeBreakpoint,
+            [
+              isolateId,
+              breakpointId,
+            ],
+          ),
+        )),
+      ) as _i3.Future<_i2.Success>);
+
+  @override
+  _i3.Future<_i2.Success> requestHeapSnapshot(String? isolateId) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #requestHeapSnapshot,
+          [isolateId],
+        ),
+        returnValue: _i3.Future<_i2.Success>.value(_FakeSuccess_1(
+          this,
+          Invocation.method(
+            #requestHeapSnapshot,
+            [isolateId],
+          ),
+        )),
+      ) as _i3.Future<_i2.Success>);
+
+  @override
+  _i3.Future<_i2.Success> resume(
+    String? isolateId, {
+    String? step,
+    int? frameIndex,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #resume,
+          [isolateId],
+          {
+            #step: step,
+            #frameIndex: frameIndex,
+          },
+        ),
+        returnValue: _i3.Future<_i2.Success>.value(_FakeSuccess_1(
+          this,
+          Invocation.method(
+            #resume,
+            [isolateId],
+            {
+              #step: step,
+              #frameIndex: frameIndex,
+            },
+          ),
+        )),
+      ) as _i3.Future<_i2.Success>);
+
+  @override
+  _i3.Future<_i2.Breakpoint> setBreakpointState(
+    String? isolateId,
+    String? breakpointId,
+    bool? enable,
+  ) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #setBreakpointState,
+          [
+            isolateId,
+            breakpointId,
+            enable,
+          ],
+        ),
+        returnValue: _i3.Future<_i2.Breakpoint>.value(_FakeBreakpoint_0(
+          this,
+          Invocation.method(
+            #setBreakpointState,
+            [
+              isolateId,
+              breakpointId,
+              enable,
+            ],
+          ),
+        )),
+      ) as _i3.Future<_i2.Breakpoint>);
+
+  @override
+  _i3.Future<_i2.Success> setExceptionPauseMode(
+    String? isolateId,
+    String? mode,
+  ) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #setExceptionPauseMode,
+          [
+            isolateId,
+            mode,
+          ],
+        ),
+        returnValue: _i3.Future<_i2.Success>.value(_FakeSuccess_1(
+          this,
+          Invocation.method(
+            #setExceptionPauseMode,
+            [
+              isolateId,
+              mode,
+            ],
+          ),
+        )),
+      ) as _i3.Future<_i2.Success>);
+
+  @override
+  _i3.Future<_i2.Success> setIsolatePauseMode(
+    String? isolateId, {
+    String? exceptionPauseMode,
+    bool? shouldPauseOnExit,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #setIsolatePauseMode,
+          [isolateId],
+          {
+            #exceptionPauseMode: exceptionPauseMode,
+            #shouldPauseOnExit: shouldPauseOnExit,
+          },
+        ),
+        returnValue: _i3.Future<_i2.Success>.value(_FakeSuccess_1(
+          this,
+          Invocation.method(
+            #setIsolatePauseMode,
+            [isolateId],
+            {
+              #exceptionPauseMode: exceptionPauseMode,
+              #shouldPauseOnExit: shouldPauseOnExit,
+            },
+          ),
+        )),
+      ) as _i3.Future<_i2.Success>);
+
+  @override
+  _i3.Future<_i2.Response> setFlag(
+    String? name,
+    String? value,
+  ) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #setFlag,
+          [
+            name,
+            value,
+          ],
+        ),
+        returnValue: _i3.Future<_i2.Response>.value(_FakeResponse_3(
+          this,
+          Invocation.method(
+            #setFlag,
+            [
+              name,
+              value,
+            ],
+          ),
+        )),
+      ) as _i3.Future<_i2.Response>);
+
+  @override
+  _i3.Future<_i2.Success> setLibraryDebuggable(
+    String? isolateId,
+    String? libraryId,
+    bool? isDebuggable,
+  ) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #setLibraryDebuggable,
+          [
+            isolateId,
+            libraryId,
+            isDebuggable,
+          ],
+        ),
+        returnValue: _i3.Future<_i2.Success>.value(_FakeSuccess_1(
+          this,
+          Invocation.method(
+            #setLibraryDebuggable,
+            [
+              isolateId,
+              libraryId,
+              isDebuggable,
+            ],
+          ),
+        )),
+      ) as _i3.Future<_i2.Success>);
+
+  @override
+  _i3.Future<_i2.Success> setName(
+    String? isolateId,
+    String? name,
+  ) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #setName,
+          [
+            isolateId,
+            name,
+          ],
+        ),
+        returnValue: _i3.Future<_i2.Success>.value(_FakeSuccess_1(
+          this,
+          Invocation.method(
+            #setName,
+            [
+              isolateId,
+              name,
+            ],
+          ),
+        )),
+      ) as _i3.Future<_i2.Success>);
+
+  @override
+  _i3.Future<_i2.Success> setTraceClassAllocation(
+    String? isolateId,
+    String? classId,
+    bool? enable,
+  ) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #setTraceClassAllocation,
+          [
+            isolateId,
+            classId,
+            enable,
+          ],
+        ),
+        returnValue: _i3.Future<_i2.Success>.value(_FakeSuccess_1(
+          this,
+          Invocation.method(
+            #setTraceClassAllocation,
+            [
+              isolateId,
+              classId,
+              enable,
+            ],
+          ),
+        )),
+      ) as _i3.Future<_i2.Success>);
+
+  @override
+  _i3.Future<_i2.Success> setVMName(String? name) => (super.noSuchMethod(
+        Invocation.method(
+          #setVMName,
+          [name],
+        ),
+        returnValue: _i3.Future<_i2.Success>.value(_FakeSuccess_1(
+          this,
+          Invocation.method(
+            #setVMName,
+            [name],
+          ),
+        )),
+      ) as _i3.Future<_i2.Success>);
+
+  @override
+  _i3.Future<_i2.Success> setVMTimelineFlags(List<String>? recordedStreams) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #setVMTimelineFlags,
+          [recordedStreams],
+        ),
+        returnValue: _i3.Future<_i2.Success>.value(_FakeSuccess_1(
+          this,
+          Invocation.method(
+            #setVMTimelineFlags,
+            [recordedStreams],
+          ),
+        )),
+      ) as _i3.Future<_i2.Success>);
+
+  @override
+  _i3.Future<_i2.Success> streamCancel(String? streamId) => (super.noSuchMethod(
+        Invocation.method(
+          #streamCancel,
+          [streamId],
+        ),
+        returnValue: _i3.Future<_i2.Success>.value(_FakeSuccess_1(
+          this,
+          Invocation.method(
+            #streamCancel,
+            [streamId],
+          ),
+        )),
+      ) as _i3.Future<_i2.Success>);
+
+  @override
+  _i3.Future<_i2.Success> streamCpuSamplesWithUserTag(List<String>? userTags) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #streamCpuSamplesWithUserTag,
+          [userTags],
+        ),
+        returnValue: _i3.Future<_i2.Success>.value(_FakeSuccess_1(
+          this,
+          Invocation.method(
+            #streamCpuSamplesWithUserTag,
+            [userTags],
+          ),
+        )),
+      ) as _i3.Future<_i2.Success>);
+
+  @override
+  _i3.Future<_i2.Success> streamListen(String? streamId) => (super.noSuchMethod(
+        Invocation.method(
+          #streamListen,
+          [streamId],
+        ),
+        returnValue: _i3.Future<_i2.Success>.value(_FakeSuccess_1(
+          this,
+          Invocation.method(
+            #streamListen,
+            [streamId],
+          ),
+        )),
+      ) as _i3.Future<_i2.Success>);
+
+  @override
+  _i3.Future<_i2.Response> callMethod(
+    String? method, {
+    String? isolateId,
+    Map<String, dynamic>? args,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #callMethod,
+          [method],
+          {
+            #isolateId: isolateId,
+            #args: args,
+          },
+        ),
+        returnValue: _i3.Future<_i2.Response>.value(_FakeResponse_3(
+          this,
+          Invocation.method(
+            #callMethod,
+            [method],
+            {
+              #isolateId: isolateId,
+              #args: args,
+            },
+          ),
+        )),
+      ) as _i3.Future<_i2.Response>);
+
+  @override
+  _i3.Future<_i2.Response> callServiceExtension(
+    String? method, {
+    String? isolateId,
+    Map<String, dynamic>? args,
+  }) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #callServiceExtension,
+          [method],
+          {
+            #isolateId: isolateId,
+            #args: args,
+          },
+        ),
+        returnValue: _i3.Future<_i2.Response>.value(_FakeResponse_3(
+          this,
+          Invocation.method(
+            #callServiceExtension,
+            [method],
+            {
+              #isolateId: isolateId,
+              #args: args,
+            },
+          ),
+        )),
+      ) as _i3.Future<_i2.Response>);
+
+  @override
+  _i3.Future<void> dispose() => (super.noSuchMethod(
+        Invocation.method(
+          #dispose,
+          [],
+        ),
+        returnValue: _i3.Future<void>.value(),
+        returnValueForMissingStub: _i3.Future<void>.value(),
+      ) as _i3.Future<void>);
+
+  @override
+  _i3.Future<T> wrapFuture<T>(
+    String? name,
+    _i3.Future<T>? future,
+  ) =>
+      (super.noSuchMethod(
+        Invocation.method(
+          #wrapFuture,
+          [
+            name,
+            future,
+          ],
+        ),
+        returnValue: _i4.ifNotNull(
+              _i4.dummyValueOrNull<T>(
+                this,
+                Invocation.method(
+                  #wrapFuture,
+                  [
+                    name,
+                    future,
+                  ],
+                ),
+              ),
+              (T v) => _i3.Future<T>.value(v),
+            ) ??
+            _FakeFuture_32<T>(
+              this,
+              Invocation.method(
+                #wrapFuture,
+                [
+                  name,
+                  future,
+                ],
+              ),
+            ),
+      ) as _i3.Future<T>);
+
+  @override
+  void registerServiceCallback(
+    String? service,
+    _i2.ServiceCallback? cb,
+  ) =>
+      super.noSuchMethod(
+        Invocation.method(
+          #registerServiceCallback,
+          [
+            service,
+            cb,
+          ],
+        ),
+        returnValueForMissingStub: null,
+      );
+}
diff --git a/pkgs/coverage/test/collect_coverage_test.dart b/pkgs/coverage/test/collect_coverage_test.dart
new file mode 100644
index 0000000..7262757
--- /dev/null
+++ b/pkgs/coverage/test/collect_coverage_test.dart
@@ -0,0 +1,325 @@
+// Copyright (c) 2015, 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.
+
+@Retry(3)
+library;
+
+import 'dart:async';
+import 'dart:convert' show json;
+import 'dart:io';
+
+import 'package:coverage/coverage.dart';
+import 'package:coverage/src/util.dart';
+import 'package:path/path.dart' as p;
+import 'package:test/test.dart';
+import 'package:test_process/test_process.dart';
+
+import 'test_util.dart';
+
+final _isolateLibPath = p.join('test', 'test_files', 'test_app_isolate.dart');
+final _collectAppPath = p.join('bin', 'collect_coverage.dart');
+
+final _sampleAppFileUri = p.toUri(p.absolute(testAppPath)).toString();
+final _isolateLibFileUri = p.toUri(p.absolute(_isolateLibPath)).toString();
+
+void main() {
+  test('collect_coverage', () async {
+    final resultString = await _getCoverageResult();
+
+    // analyze the output json
+    final coverage =
+        coverageDataFromJson(json.decode(resultString) as Map<String, dynamic>);
+
+    expect(coverage, isNotEmpty);
+
+    final sources = coverage.sources();
+
+    for (var sampleCoverageData in sources[_sampleAppFileUri]!) {
+      expect(sampleCoverageData['hits'], isNotNull);
+    }
+
+    for (var sampleCoverageData in sources[_isolateLibFileUri]!) {
+      expect(sampleCoverageData['hits'], isNotEmpty);
+    }
+  });
+
+  test('createHitmap returns a sorted hitmap', () async {
+    final coverage = [
+      {
+        'source': 'foo',
+        'script': '{type: @Script, fixedId: true, '
+            'id: bar.dart, uri: bar.dart, _kind: library}',
+        'hits': [
+          45,
+          1,
+          46,
+          1,
+          49,
+          0,
+          50,
+          0,
+          15,
+          1,
+          16,
+          2,
+          17,
+          2,
+        ]
+      }
+    ];
+    // ignore: deprecated_member_use_from_same_package
+    final hitMap = await createHitmap(
+      coverage.cast<Map<String, dynamic>>(),
+    );
+    final expectedHits = {15: 1, 16: 2, 17: 2, 45: 1, 46: 1, 49: 0, 50: 0};
+    expect(hitMap['foo'], expectedHits);
+  });
+
+  test('HitMap.parseJson returns a sorted hitmap', () async {
+    final coverage = [
+      {
+        'source': 'foo',
+        'script': '{type: @Script, fixedId: true, '
+            'id: bar.dart, uri: bar.dart, _kind: library}',
+        'hits': [
+          45,
+          1,
+          46,
+          1,
+          49,
+          0,
+          50,
+          0,
+          15,
+          1,
+          16,
+          2,
+          17,
+          2,
+        ]
+      }
+    ];
+    final hitMap = await HitMap.parseJson(
+      coverage.cast<Map<String, dynamic>>(),
+    );
+    final expectedHits = {15: 1, 16: 2, 17: 2, 45: 1, 46: 1, 49: 0, 50: 0};
+    expect(hitMap['foo']?.lineHits, expectedHits);
+  });
+
+  test('HitMap.parseJson', () async {
+    final resultString = await _collectCoverage(true, true);
+    final jsonResult = json.decode(resultString) as Map<String, dynamic>;
+    final coverage = jsonResult['coverage'] as List;
+    final hitMap = await HitMap.parseJson(
+      coverage.cast<Map<String, dynamic>>(),
+    );
+    expect(hitMap, contains(_sampleAppFileUri));
+
+    final isolateFile = hitMap[_isolateLibFileUri];
+    final expectedHits = {
+      11: 1,
+      12: 1,
+      13: 1,
+      15: 0,
+      19: 1,
+      23: 1,
+      24: 2,
+      28: 1,
+      29: 1,
+      30: 1,
+      32: 0,
+      38: 1,
+      39: 1,
+      41: 1,
+      42: 4,
+      43: 1,
+      44: 3,
+      45: 1,
+      48: 1,
+      49: 1,
+      51: 1,
+      54: 1,
+      55: 1,
+      56: 1,
+      59: 1,
+      60: 1,
+      62: 1,
+      63: 1,
+      64: 1,
+      66: 1,
+      67: 1,
+      68: 1,
+      71: 3,
+    };
+    expect(isolateFile?.lineHits, expectedHits);
+    expect(isolateFile?.funcHits, {11: 1, 19: 1, 23: 1, 28: 1, 38: 1});
+    expect(isolateFile?.funcNames, {
+      11: 'fooSync',
+      19: 'BarClass.BarClass',
+      23: 'BarClass.baz',
+      28: 'fooAsync',
+      38: 'isolateTask'
+    });
+    expect(
+      isolateFile?.branchHits,
+      {
+        11: 1,
+        12: 1,
+        15: 0,
+        19: 1,
+        23: 1,
+        28: 1,
+        29: 1,
+        32: 0,
+        38: 1,
+        42: 1,
+        71: 1,
+      },
+    );
+  });
+
+  test('parseCoverage', () async {
+    final tempDir = await Directory.systemTemp.createTemp('coverage.test.');
+
+    try {
+      final outputFile = File(p.join(tempDir.path, 'coverage.json'));
+
+      final coverageResults = await _getCoverageResult();
+      await outputFile.writeAsString(coverageResults, flush: true);
+
+      // ignore: deprecated_member_use_from_same_package
+      final parsedResult = await parseCoverage([outputFile], 1);
+
+      expect(parsedResult, contains(_sampleAppFileUri));
+      expect(parsedResult, contains(_isolateLibFileUri));
+    } finally {
+      await tempDir.delete(recursive: true);
+    }
+  });
+
+  test('HitMap.parseFiles', () async {
+    final tempDir = await Directory.systemTemp.createTemp('coverage.test.');
+
+    try {
+      final outputFile = File(p.join(tempDir.path, 'coverage.json'));
+
+      final coverageResults = await _getCoverageResult();
+      await outputFile.writeAsString(coverageResults, flush: true);
+
+      final parsedResult = await HitMap.parseFiles([outputFile]);
+
+      expect(parsedResult, contains(_sampleAppFileUri));
+      expect(parsedResult, contains(_isolateLibFileUri));
+    } finally {
+      await tempDir.delete(recursive: true);
+    }
+  });
+
+  test('HitMap.parseFiles with packagesPath and checkIgnoredLines', () async {
+    final tempDir = await Directory.systemTemp.createTemp('coverage.test.');
+
+    try {
+      final outputFile = File(p.join(tempDir.path, 'coverage.json'));
+
+      final coverageResults = await _getCoverageResult();
+      await outputFile.writeAsString(coverageResults, flush: true);
+
+      final parsedResult = await HitMap.parseFiles([outputFile],
+          packagePath: '.', checkIgnoredLines: true);
+
+      // This file has ignore:coverage-file.
+      expect(parsedResult, isNot(contains(_sampleAppFileUri)));
+      expect(parsedResult, contains(_isolateLibFileUri));
+    } finally {
+      await tempDir.delete(recursive: true);
+    }
+  });
+
+  test('mergeHitmaps', () {
+    final resultMap = <String, Map<int, int>>{
+      'foo.dart': {10: 2, 20: 0},
+      'bar.dart': {10: 3, 20: 1, 30: 0},
+    };
+    final newMap = <String, Map<int, int>>{
+      'bar.dart': {10: 2, 20: 0, 40: 3},
+      'baz.dart': {10: 1, 20: 0, 30: 1},
+    };
+    // ignore: deprecated_member_use_from_same_package
+    mergeHitmaps(newMap, resultMap);
+    expect(resultMap, <String, Map<int, int>>{
+      'foo.dart': {10: 2, 20: 0},
+      'bar.dart': {10: 5, 20: 1, 30: 0, 40: 3},
+      'baz.dart': {10: 1, 20: 0, 30: 1},
+    });
+  });
+
+  test('FileHitMaps.merge', () {
+    final resultMap = <String, HitMap>{
+      'foo.dart':
+          HitMap({10: 2, 20: 0}, {15: 0, 25: 1}, {15: 'bobble', 25: 'cobble'}),
+      'bar.dart': HitMap(
+          {10: 3, 20: 1, 30: 0}, {15: 5, 25: 0}, {15: 'gobble', 25: 'wobble'}),
+    };
+    final newMap = <String, HitMap>{
+      'bar.dart': HitMap(
+          {10: 2, 20: 0, 40: 3}, {15: 1, 35: 4}, {15: 'gobble', 35: 'dobble'}),
+      'baz.dart': HitMap(
+          {10: 1, 20: 0, 30: 1}, {15: 0, 25: 2}, {15: 'lobble', 25: 'zobble'}),
+    };
+    resultMap.merge(newMap);
+    expect(resultMap['foo.dart']?.lineHits, <int, int>{10: 2, 20: 0});
+    expect(resultMap['foo.dart']?.funcHits, <int, int>{15: 0, 25: 1});
+    expect(resultMap['foo.dart']?.funcNames,
+        <int, String>{15: 'bobble', 25: 'cobble'});
+    expect(resultMap['bar.dart']?.lineHits,
+        <int, int>{10: 5, 20: 1, 30: 0, 40: 3});
+    expect(resultMap['bar.dart']?.funcHits, <int, int>{15: 6, 25: 0, 35: 4});
+    expect(resultMap['bar.dart']?.funcNames,
+        <int, String>{15: 'gobble', 25: 'wobble', 35: 'dobble'});
+    expect(resultMap['baz.dart']?.lineHits, <int, int>{10: 1, 20: 0, 30: 1});
+    expect(resultMap['baz.dart']?.funcHits, <int, int>{15: 0, 25: 2});
+    expect(resultMap['baz.dart']?.funcNames,
+        <int, String>{15: 'lobble', 25: 'zobble'});
+  });
+}
+
+String? _coverageData;
+
+Future<String> _getCoverageResult() async =>
+    _coverageData ??= await _collectCoverage(false, false);
+
+Future<String> _collectCoverage(
+    bool functionCoverage, bool branchCoverage) async {
+  expect(FileSystemEntity.isFileSync(testAppPath), isTrue);
+
+  final openPort = await getOpenPort();
+
+  // Run the sample app with the right flags.
+  final sampleProcess = await runTestApp(openPort);
+
+  // Capture the VM service URI.
+  final serviceUri = await serviceUriFromProcess(sampleProcess.stdoutStream());
+
+  // Run the collection tool.
+  // TODO: need to get all of this functionality in the lib
+  final toolResult = await TestProcess.start(Platform.resolvedExecutable, [
+    _collectAppPath,
+    if (functionCoverage) '--function-coverage',
+    if (branchCoverage) '--branch-coverage',
+    '--uri',
+    '$serviceUri',
+    '--resume-isolates',
+    '--wait-paused'
+  ]);
+
+  await toolResult.shouldExit(0).timeout(
+        timeout,
+        onTimeout: () =>
+            throw StateError('We timed out waiting for the tool to finish.'),
+      );
+
+  await sampleProcess.shouldExit();
+
+  return toolResult.stdoutStream().join('\n');
+}
diff --git a/pkgs/coverage/test/format_coverage_test.dart b/pkgs/coverage/test/format_coverage_test.dart
new file mode 100644
index 0000000..85493f7
--- /dev/null
+++ b/pkgs/coverage/test/format_coverage_test.dart
@@ -0,0 +1,37 @@
+// Copyright (c) 2024, 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.
+
+import 'dart:io';
+
+import 'package:path/path.dart' as p;
+import 'package:test/test.dart';
+
+import '../bin/format_coverage.dart';
+
+void main() {
+  late Directory testDir;
+  setUp(() {
+    testDir = Directory.systemTemp.createTempSync('coverage_test_temp');
+  });
+
+  tearDown(() async {
+    if (testDir.existsSync()) testDir.deleteSync(recursive: true);
+  });
+
+  test('considers all json files', () async {
+    final fileA = File(p.join(testDir.path, 'coverage_a.json'));
+    fileA.createSync();
+    final fileB = File(p.join(testDir.path, 'coverage_b.json'));
+    fileB.createSync();
+    final fileC = File(p.join(testDir.path, 'not_coverage.foo'));
+    fileC.createSync();
+
+    final files = filesToProcess(testDir.path);
+    expect(files.length, equals(2));
+    expect(
+        files.map((f) => f.path),
+        containsAll(
+            [endsWith('coverage_a.json'), endsWith('coverage_b.json')]));
+  });
+}
diff --git a/pkgs/coverage/test/function_coverage_test.dart b/pkgs/coverage/test/function_coverage_test.dart
new file mode 100644
index 0000000..965d0d0
--- /dev/null
+++ b/pkgs/coverage/test/function_coverage_test.dart
@@ -0,0 +1,107 @@
+// Copyright (c) 2022, 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.
+
+import 'dart:async';
+import 'dart:convert' show json;
+import 'dart:io';
+
+import 'package:coverage/coverage.dart';
+import 'package:coverage/src/util.dart';
+import 'package:path/path.dart' as p;
+import 'package:test/test.dart';
+import 'package:test_process/test_process.dart';
+
+import 'test_util.dart';
+
+final _collectAppPath = p.join('bin', 'collect_coverage.dart');
+final _funcCovApp = p.join('test', 'test_files', 'function_coverage_app.dart');
+final _sampleAppFileUri = p.toUri(p.absolute(_funcCovApp)).toString();
+
+void main() {
+  test('Function coverage', () async {
+    final resultString = await _collectCoverage();
+    final jsonResult = json.decode(resultString) as Map<String, dynamic>;
+    final coverage = jsonResult['coverage'] as List;
+    final hitMap = await HitMap.parseJson(
+      coverage.cast<Map<String, dynamic>>(),
+    );
+
+    // function_coverage_app.dart.
+    expect(hitMap, contains(_sampleAppFileUri));
+    final isolateFile = hitMap[_sampleAppFileUri]!;
+    expect(isolateFile.funcHits, {
+      7: 1,
+      16: 1,
+      21: 1,
+      25: 1,
+      29: 1,
+      36: 1,
+      42: 1,
+      47: 1,
+    });
+    expect(isolateFile.funcNames, {
+      7: 'normalFunction',
+      16: 'SomeClass.SomeClass',
+      21: 'SomeClass.normalMethod',
+      25: 'SomeClass.staticMethod',
+      29: 'SomeClass.abstractMethod',
+      36: 'SomeExtension.extensionMethod',
+      42: 'OtherClass.otherMethod',
+      47: 'main',
+    });
+
+    // test_library.dart.
+    final testLibraryPath =
+        p.absolute(p.join('test', 'test_files', 'test_library.dart'));
+    final testLibraryUri = p.toUri(testLibraryPath).toString();
+    expect(hitMap, contains(testLibraryUri));
+    final libraryfile = hitMap[testLibraryUri]!;
+    expect(libraryfile.funcHits, {7: 1});
+    expect(libraryfile.funcNames, {7: 'libraryFunction'});
+
+    // test_library_part.dart.
+    final testLibraryPartPath =
+        p.absolute(p.join('test', 'test_files', 'test_library_part.dart'));
+    final testLibraryPartUri = p.toUri(testLibraryPartPath).toString();
+    expect(hitMap, contains(testLibraryPartUri));
+    final libraryPartFile = hitMap[testLibraryPartUri]!;
+    expect(libraryPartFile.funcHits, {7: 1});
+    expect(libraryPartFile.funcNames, {7: 'otherLibraryFunction'});
+  });
+}
+
+Future<String> _collectCoverage() async {
+  expect(FileSystemEntity.isFileSync(_funcCovApp), isTrue);
+
+  final openPort = await getOpenPort();
+
+  // Run the sample app with the right flags.
+  final sampleProcess = await TestProcess.start(Platform.resolvedExecutable, [
+    '--enable-vm-service=$openPort',
+    '--pause_isolates_on_exit',
+    _funcCovApp
+  ]);
+
+  final serviceUri = await serviceUriFromProcess(sampleProcess.stdoutStream());
+
+  // Run the collection tool.
+  final toolResult = await TestProcess.start(Platform.resolvedExecutable, [
+    _collectAppPath,
+    '--function-coverage',
+    '--uri',
+    '$serviceUri',
+    '--resume-isolates',
+    '--wait-paused'
+  ]);
+
+  await toolResult.shouldExit(0).timeout(
+        timeout,
+        onTimeout: () =>
+            throw StateError('We timed out waiting for the tool to finish.'),
+      );
+
+  await sampleProcess.shouldExit();
+
+  return toolResult.stdoutStream().join('\n');
+}
diff --git a/pkgs/coverage/test/isolate_paused_listener_test.dart b/pkgs/coverage/test/isolate_paused_listener_test.dart
new file mode 100644
index 0000000..4fc7d4b
--- /dev/null
+++ b/pkgs/coverage/test/isolate_paused_listener_test.dart
@@ -0,0 +1,753 @@
+// Copyright (c) 2024, 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.
+
+import 'dart:async';
+
+import 'package:coverage/src/isolate_paused_listener.dart';
+import 'package:mockito/mockito.dart';
+import 'package:test/test.dart';
+import 'package:vm_service/vm_service.dart';
+
+import 'collect_coverage_mock_test.mocks.dart';
+
+Event event(
+  String id, {
+  String? kind,
+  String? groupId,
+  String? name,
+}) =>
+    Event(
+        kind: kind,
+        isolate: IsolateRef(
+          isolateGroupId: groupId,
+          id: id,
+          name: name,
+        ));
+
+Isolate isolate(
+  String id, {
+  String? groupId,
+  String? name,
+  String? pauseKind,
+}) =>
+    Isolate(
+      isolateGroupId: groupId,
+      id: id,
+      name: name,
+      pauseEvent: pauseKind == null ? null : Event(kind: pauseKind),
+    );
+
+(MockVmService, StreamController<Event>) createServiceAndEventStreams() {
+  final service = MockVmService();
+  when(service.streamListen(any)).thenAnswer((_) async => Success());
+
+  // The VM service events we care about come in on 2 different streams,
+  // onIsolateEvent and onDebugEvent. We want to write tests that send sequences
+  // of events like [I1, D1, I2, D2, I3, D3], but since I and D go to separate
+  // streams, the listener may see them arrive like [I1, I2, I3, D1, D2, D3] or
+  // [D1, D2, D3, I1, I2, I3] or any other interleaving. So instead we send all
+  // the events through a single stream that gets split up. This emulates how
+  // the events work in reality, since they all come from a single web socket.
+  final allEvents = StreamController<Event>();
+  final isolateEvents = StreamController<Event>();
+  final debugEvents = StreamController<Event>();
+  allEvents.stream.listen((Event e) {
+    if (e.kind == EventKind.kIsolateStart ||
+        e.kind == EventKind.kIsolateStart) {
+      isolateEvents.add(e);
+    } else {
+      debugEvents.add(e);
+    }
+  });
+  when(service.onIsolateEvent).thenAnswer((_) => isolateEvents.stream);
+  when(service.onDebugEvent).thenAnswer((_) => debugEvents.stream);
+
+  return (service, allEvents);
+}
+
+void main() {
+  group('IsolateEventBuffer', () {
+    test('buffers events', () async {
+      final received = <String>[];
+      final eventBuffer = IsolateEventBuffer((Event event) async {
+        await Future<void>.delayed(Duration.zero);
+        received.add(event.isolate!.id!);
+      });
+
+      await eventBuffer.add(event('a'));
+      await eventBuffer.add(event('b'));
+      await eventBuffer.add(event('c'));
+      expect(received, <String>[]);
+
+      await eventBuffer.flush();
+      expect(received, ['a', 'b', 'c']);
+
+      await eventBuffer.flush();
+      expect(received, ['a', 'b', 'c']);
+
+      await eventBuffer.add(event('d'));
+      await eventBuffer.add(event('e'));
+      await eventBuffer.add(event('f'));
+      expect(received, ['a', 'b', 'c', 'd', 'e', 'f']);
+
+      await eventBuffer.flush();
+      expect(received, ['a', 'b', 'c', 'd', 'e', 'f']);
+    });
+
+    test('buffers events during flush', () async {
+      final received = <String>[];
+      final pause = Completer<void>();
+      final eventBuffer = IsolateEventBuffer((Event event) async {
+        await pause.future;
+        received.add(event.isolate!.id!);
+      });
+
+      await eventBuffer.add(event('a'));
+      await eventBuffer.add(event('b'));
+      await eventBuffer.add(event('c'));
+      expect(received, <String>[]);
+
+      final flushing = eventBuffer.flush();
+      expect(received, <String>[]);
+
+      await eventBuffer.add(event('d'));
+      await eventBuffer.add(event('e'));
+      await eventBuffer.add(event('f'));
+      expect(received, <String>[]);
+
+      pause.complete();
+      await flushing;
+      expect(received, ['a', 'b', 'c', 'd', 'e', 'f']);
+    });
+  });
+
+  test('IsolateEventBuffer', () {
+    final group = IsolateGroupState();
+    expect(group.running, isEmpty);
+    expect(group.paused, isEmpty);
+    expect(group.noRunningIsolates, isTrue);
+    expect(group.noLiveIsolates, isTrue);
+
+    group.start('a');
+    expect(group.running, unorderedEquals(['a']));
+    expect(group.paused, isEmpty);
+    expect(group.noRunningIsolates, isFalse);
+    expect(group.noLiveIsolates, isFalse);
+
+    group.start('a');
+    expect(group.running, unorderedEquals(['a']));
+    expect(group.paused, isEmpty);
+    expect(group.noRunningIsolates, isFalse);
+    expect(group.noLiveIsolates, isFalse);
+
+    group.start('b');
+    expect(group.running, unorderedEquals(['a', 'b']));
+    expect(group.paused, isEmpty);
+    expect(group.noRunningIsolates, isFalse);
+    expect(group.noLiveIsolates, isFalse);
+
+    group.pause('a');
+    expect(group.running, unorderedEquals(['b']));
+    expect(group.paused, unorderedEquals(['a']));
+    expect(group.noRunningIsolates, isFalse);
+    expect(group.noLiveIsolates, isFalse);
+
+    group.pause('a');
+    expect(group.running, unorderedEquals(['b']));
+    expect(group.paused, unorderedEquals(['a']));
+    expect(group.noRunningIsolates, isFalse);
+    expect(group.noLiveIsolates, isFalse);
+
+    group.pause('c');
+    expect(group.running, unorderedEquals(['b']));
+    expect(group.paused, unorderedEquals(['a', 'c']));
+    expect(group.noRunningIsolates, isFalse);
+    expect(group.noLiveIsolates, isFalse);
+
+    group.start('c');
+    expect(group.running, unorderedEquals(['b', 'c']));
+    expect(group.paused, unorderedEquals(['a']));
+    expect(group.noRunningIsolates, isFalse);
+    expect(group.noLiveIsolates, isFalse);
+
+    group.pause('c');
+    expect(group.running, unorderedEquals(['b']));
+    expect(group.paused, unorderedEquals(['a', 'c']));
+    expect(group.noRunningIsolates, isFalse);
+    expect(group.noLiveIsolates, isFalse);
+
+    group.exit('a');
+    expect(group.running, unorderedEquals(['b']));
+    expect(group.paused, unorderedEquals(['c']));
+    expect(group.noRunningIsolates, isFalse);
+    expect(group.noLiveIsolates, isFalse);
+
+    group.pause('b');
+    expect(group.running, isEmpty);
+    expect(group.paused, unorderedEquals(['b', 'c']));
+    expect(group.noRunningIsolates, isTrue);
+    expect(group.noLiveIsolates, isFalse);
+
+    group.exit('b');
+    expect(group.running, isEmpty);
+    expect(group.paused, unorderedEquals(['c']));
+    expect(group.noRunningIsolates, isTrue);
+    expect(group.noLiveIsolates, isFalse);
+
+    group.exit('c');
+    expect(group.running, isEmpty);
+    expect(group.paused, isEmpty);
+    expect(group.noRunningIsolates, isTrue);
+    expect(group.noLiveIsolates, isTrue);
+  });
+
+  group('listenToIsolateLifecycleEvents', () {
+    late MockVmService service;
+    late StreamController<Event> allEvents;
+    late Completer<List<Isolate>> isolates;
+    late Future<void> backfilled;
+    late Future<void> testEnded;
+
+    late List<String> received;
+    Future<void>? delayTheOnPauseCallback;
+
+    void startEvent(String id) =>
+        allEvents.add(event(id, kind: EventKind.kIsolateStart));
+    void exitEvent(String id) =>
+        allEvents.add(event(id, kind: EventKind.kIsolateExit));
+    void pauseEvent(String id) =>
+        allEvents.add(event(id, kind: EventKind.kPauseExit));
+    void otherEvent(String id, String kind) =>
+        allEvents.add(event(id, kind: kind));
+
+    Future<void> backfill(List<Isolate> isos) async {
+      isolates.complete(isos);
+      await backfilled;
+    }
+
+    // We end the test by sending an exit event with a specific ID.
+    const endTestEventId = 'END';
+    Future<void> endTest() {
+      exitEvent(endTestEventId);
+      return testEnded;
+    }
+
+    setUp(() {
+      (service, allEvents) = createServiceAndEventStreams();
+
+      isolates = Completer<List<Isolate>>();
+      when(service.getVM())
+          .thenAnswer((_) async => VM(isolates: await isolates.future));
+      when(service.getIsolate(any)).thenAnswer((invocation) async {
+        final id = invocation.positionalArguments[0];
+        return (await isolates.future).firstWhere((iso) => iso.id == id);
+      });
+
+      received = <String>[];
+      delayTheOnPauseCallback = null;
+      final testEnder = Completer<void>();
+      testEnded = testEnder.future;
+      backfilled = listenToIsolateLifecycleEvents(
+        service,
+        (iso) {
+          if (iso.id == endTestEventId) return;
+          received.add('Start ${iso.id}');
+        },
+        (iso) async {
+          received.add('Pause ${iso.id}');
+          if (delayTheOnPauseCallback != null) {
+            await delayTheOnPauseCallback;
+            received.add('Pause done ${iso.id}');
+          }
+        },
+        (iso) {
+          if (iso.id == endTestEventId) {
+            testEnder.complete();
+          } else {
+            received.add('Exit ${iso.id}');
+          }
+        },
+      );
+    });
+
+    test('ordinary flows', () async {
+      // Events sent before backfill.
+      startEvent('A');
+      startEvent('C');
+      startEvent('B');
+      pauseEvent('C');
+      pauseEvent('A');
+      startEvent('D');
+      pauseEvent('D');
+      exitEvent('A');
+
+      // Run backfill.
+      await backfill([
+        isolate('B'),
+        isolate('C', pauseKind: EventKind.kPauseExit),
+        isolate('D'),
+        isolate('E'),
+        isolate('F', pauseKind: EventKind.kPauseExit),
+      ]);
+
+      // All the backfill events happen before any of the real events.
+      expect(received, [
+        // Backfill events.
+        'Start B',
+        'Start C',
+        'Pause C',
+        'Start D',
+        'Start E',
+        'Start F',
+        'Pause F',
+
+        // Real events from before backfill.
+        'Start A',
+        'Pause A',
+        'Pause D',
+        'Exit A',
+      ]);
+
+      // Events sent after backfill.
+      received.clear();
+      startEvent('G');
+      exitEvent('C');
+      exitEvent('B');
+      exitEvent('G');
+      exitEvent('D');
+      exitEvent('E');
+      exitEvent('F');
+
+      await endTest();
+      expect(received, [
+        'Start G',
+        'Exit C',
+        'Exit B',
+        'Exit G',
+        'Exit D',
+        'Exit E',
+        'Exit F',
+      ]);
+
+      verify(service.streamListen(EventStreams.kIsolate)).called(1);
+      verify(service.streamListen(EventStreams.kDebug)).called(1);
+    });
+
+    test('pause and exit events without start', () async {
+      await backfill([]);
+
+      pauseEvent('A');
+      exitEvent('B');
+
+      await endTest();
+      expect(received, [
+        'Start A',
+        'Pause A',
+        'Start B',
+        'Exit B',
+      ]);
+    });
+
+    test('pause event after exit is ignored', () async {
+      await backfill([]);
+
+      exitEvent('A');
+      pauseEvent('A');
+
+      await endTest();
+      expect(received, [
+        'Start A',
+        'Exit A',
+      ]);
+    });
+
+    test('event deduping', () async {
+      startEvent('A');
+      startEvent('A');
+      pauseEvent('A');
+      pauseEvent('A');
+      exitEvent('A');
+      exitEvent('A');
+
+      pauseEvent('B');
+      startEvent('B');
+
+      exitEvent('C');
+      startEvent('C');
+
+      await backfill([]);
+      await endTest();
+      expect(received, [
+        'Start A',
+        'Pause A',
+        'Exit A',
+        'Start B',
+        'Pause B',
+        'Start C',
+        'Exit C',
+      ]);
+    });
+
+    test('ignore other events', () async {
+      await backfill([]);
+
+      startEvent('A');
+      pauseEvent('A');
+      otherEvent('A', EventKind.kResume);
+      exitEvent('A');
+
+      startEvent('B');
+      otherEvent('B', EventKind.kPauseBreakpoint);
+      exitEvent('B');
+
+      otherEvent('C', EventKind.kInspect);
+
+      await endTest();
+      expect(received, [
+        'Start A',
+        'Pause A',
+        'Exit A',
+        'Start B',
+        'Exit B',
+      ]);
+    });
+
+    test('exit event during pause callback', () async {
+      final delayingTheOnPauseCallback = Completer<void>();
+      delayTheOnPauseCallback = delayingTheOnPauseCallback.future;
+      await backfill([]);
+
+      startEvent('A');
+      pauseEvent('A');
+      exitEvent('A');
+
+      while (received.length < 2) {
+        await Future<void>.delayed(Duration.zero);
+      }
+
+      expect(received, [
+        'Start A',
+        'Pause A',
+      ]);
+
+      delayingTheOnPauseCallback.complete();
+      await endTest();
+      expect(received, [
+        'Start A',
+        'Pause A',
+        'Pause done A',
+        'Exit A',
+      ]);
+    });
+
+    test('exit event during pause callback, event deduping', () async {
+      final delayingTheOnPauseCallback = Completer<void>();
+      delayTheOnPauseCallback = delayingTheOnPauseCallback.future;
+      await backfill([]);
+
+      startEvent('A');
+      pauseEvent('A');
+      exitEvent('A');
+      pauseEvent('A');
+      pauseEvent('A');
+      exitEvent('A');
+      exitEvent('A');
+
+      while (received.length < 2) {
+        await Future<void>.delayed(Duration.zero);
+      }
+
+      expect(received, [
+        'Start A',
+        'Pause A',
+      ]);
+
+      delayingTheOnPauseCallback.complete();
+      await endTest();
+      expect(received, [
+        'Start A',
+        'Pause A',
+        'Pause done A',
+        'Exit A',
+      ]);
+    });
+  });
+
+  group('IsolatePausedListener', () {
+    late MockVmService service;
+    late StreamController<Event> allEvents;
+    late Future<void> allIsolatesExited;
+
+    late List<String> received;
+    late bool stopped;
+
+    void startEvent(String id, String groupId, [String? name]) =>
+        allEvents.add(event(
+          id,
+          kind: EventKind.kIsolateStart,
+          groupId: groupId,
+          name: name ?? id,
+        ));
+    void exitEvent(String id, String groupId, [String? name]) =>
+        allEvents.add(event(
+          id,
+          kind: EventKind.kIsolateExit,
+          groupId: groupId,
+          name: name ?? id,
+        ));
+    void pauseEvent(String id, String groupId, [String? name]) =>
+        allEvents.add(event(
+          id,
+          kind: EventKind.kPauseExit,
+          groupId: groupId,
+          name: name ?? id,
+        ));
+
+    Future<void> endTest() async {
+      await allIsolatesExited;
+      stopped = true;
+    }
+
+    setUp(() {
+      (service, allEvents) = createServiceAndEventStreams();
+
+      // Backfill was tested above, so this test does everything using events,
+      // for simplicity. No need to report any isolates.
+      when(service.getVM()).thenAnswer((_) async => VM());
+
+      received = <String>[];
+      when(service.resume(any)).thenAnswer((invocation) async {
+        final id = invocation.positionalArguments[0];
+        received.add('Resume $id');
+        return Success();
+      });
+
+      stopped = false;
+      allIsolatesExited = IsolatePausedListener(
+        service,
+        (iso, isLastIsolateInGroup) async {
+          expect(stopped, isFalse);
+          received.add('Pause ${iso.id}. Last in group ${iso.isolateGroupId}? '
+              '${isLastIsolateInGroup ? 'Yes' : 'No'}');
+        },
+        (message) => received.add(message),
+      ).waitUntilAllExited();
+    });
+
+    test('ordinary flows', () async {
+      startEvent('A', '1');
+      startEvent('B', '1');
+      pauseEvent('A', '1');
+      startEvent('C', '1');
+      pauseEvent('B', '1');
+      exitEvent('A', '1');
+      startEvent('D', '2');
+      startEvent('E', '2');
+      startEvent('F', '2');
+      pauseEvent('C', '1');
+      pauseEvent('F', '2');
+      pauseEvent('E', '2');
+      exitEvent('C', '1');
+      exitEvent('E', '2');
+      startEvent('G', '3');
+      exitEvent('F', '2');
+      startEvent('H', '3');
+      startEvent('I', '3');
+      pauseEvent('I', '3');
+      exitEvent('I', '3');
+      pauseEvent('H', '3');
+      exitEvent('H', '3');
+      pauseEvent('D', '2');
+      pauseEvent('G', '3');
+      exitEvent('D', '2');
+      exitEvent('G', '3');
+      exitEvent('B', '1');
+
+      await endTest();
+
+      // Events sent after waitUntilAllExited is finished do nothing.
+      startEvent('Z', '9');
+      pauseEvent('Z', '9');
+      exitEvent('Z', '9');
+
+      expect(received, [
+        'Pause A. Last in group 1? No',
+        'Resume A',
+        'Pause B. Last in group 1? No',
+        'Resume B',
+        'Pause C. Last in group 1? Yes',
+        'Resume C',
+        'Pause F. Last in group 2? No',
+        'Resume F',
+        'Pause E. Last in group 2? No',
+        'Resume E',
+        'Pause I. Last in group 3? No',
+        'Resume I',
+        'Pause H. Last in group 3? No',
+        'Resume H',
+        'Pause D. Last in group 2? Yes',
+        'Resume D',
+        'Pause G. Last in group 3? Yes',
+        'Resume G',
+      ]);
+    });
+
+    test('exit without pausing', () async {
+      // If an isolate exits without pausing, this may mess up coverage
+      // collection (if it happens to be the last isolate in the group, that
+      // group won't be collected). The best we can do is log an error, and make
+      // sure not to wait forever for pause events that aren't coming.
+      startEvent('A', '1');
+      startEvent('B', '1');
+      exitEvent('A', '1');
+      pauseEvent('B', '1');
+      startEvent('C', '2');
+      startEvent('D', '2');
+      pauseEvent('D', '2');
+      exitEvent('D', '2');
+      exitEvent('C', '2');
+      exitEvent('B', '1');
+
+      await endTest();
+
+      // B was paused correctly and was the last to exit isolate 1, so isolate 1
+      // was collected ok.
+      expect(received, [
+        'Pause B. Last in group 1? Yes',
+        'Resume B',
+        'Pause D. Last in group 2? No',
+        'Resume D',
+        'ERROR: An isolate exited without pausing, causing coverage data to '
+            'be lost for group 2.',
+      ]);
+    });
+
+    test('main isolate resumed last', () async {
+      startEvent('A', '1', 'main');
+      startEvent('B', '1', 'main'); // Second isolate named main, ignored.
+      pauseEvent('B', '1', 'main');
+      startEvent('C', '2', 'main'); // Third isolate named main, ignored.
+      pauseEvent('A', '1', 'main');
+      startEvent('D', '2');
+      pauseEvent('C', '2');
+      exitEvent('C', '2');
+      pauseEvent('D', '2');
+      exitEvent('D', '2');
+      exitEvent('B', '1');
+
+      await endTest();
+
+      expect(received, [
+        'Pause B. Last in group 1? No',
+        'Resume B',
+        'Pause C. Last in group 2? No',
+        'Resume C',
+        'Pause D. Last in group 2? Yes',
+        'Resume D',
+        'Pause A. Last in group 1? Yes',
+        'Resume A',
+      ]);
+    });
+
+    test('main isolate exits without pausing', () async {
+      startEvent('A', '1', 'main');
+      startEvent('B', '1');
+      pauseEvent('B', '1');
+      exitEvent('A', '1', 'main');
+      exitEvent('B', '1');
+
+      await endTest();
+
+      expect(received, [
+        'Pause B. Last in group 1? No',
+        'Resume B',
+        'ERROR: An isolate exited without pausing, causing coverage data to '
+            'be lost for group 1.',
+      ]);
+    });
+
+    test('main isolate is the only isolate', () async {
+      startEvent('A', '1', 'main');
+      pauseEvent('A', '1', 'main');
+
+      await endTest();
+
+      expect(received, [
+        'Pause A. Last in group 1? Yes',
+        'Resume A',
+      ]);
+    });
+
+    test('all other isolates exit before main isolate pauses', () async {
+      startEvent('A', '1', 'main');
+      startEvent('B', '1');
+      pauseEvent('B', '1');
+      exitEvent('B', '1');
+
+      await Future<void>.delayed(Duration.zero);
+
+      pauseEvent('A', '1', 'main');
+      exitEvent('A', '1', 'main');
+
+      await endTest();
+
+      expect(received, [
+        'Pause B. Last in group 1? No',
+        'Resume B',
+        'Pause A. Last in group 1? Yes',
+        'Resume A',
+      ]);
+    });
+
+    test('group reopened', () async {
+      // If an isolate is reported in a group after the group as believed to be
+      // closed, reopen the group. This double counts some coverage, but at
+      // least won't miss any.
+
+      startEvent('Z', '9'); // Separate isolate to keep the system alive until
+      pauseEvent('Z', '9'); // the test is complete.
+
+      startEvent('A', '1');
+      startEvent('B', '1');
+      pauseEvent('A', '1');
+      pauseEvent('B', '1');
+      exitEvent('B', '1');
+      exitEvent('A', '1');
+
+      startEvent('D', '2');
+      startEvent('E', '2');
+      pauseEvent('E', '2');
+      pauseEvent('D', '2');
+      exitEvent('E', '2');
+      exitEvent('D', '2');
+
+      startEvent('C', '1');
+      pauseEvent('F', '2');
+      pauseEvent('C', '1');
+      exitEvent('C', '1');
+      exitEvent('F', '2');
+
+      exitEvent('Z', '9');
+
+      await endTest();
+
+      expect(received, [
+        'Pause Z. Last in group 9? Yes',
+        'Resume Z',
+        'Pause A. Last in group 1? No',
+        'Resume A',
+        'Pause B. Last in group 1? Yes',
+        'Resume B',
+        'Pause E. Last in group 2? No',
+        'Resume E',
+        'Pause D. Last in group 2? Yes',
+        'Resume D',
+        'Pause F. Last in group 2? Yes',
+        'Resume F',
+        'Pause C. Last in group 1? Yes',
+        'Resume C',
+      ]);
+    });
+  });
+}
diff --git a/pkgs/coverage/test/lcov_test.dart b/pkgs/coverage/test/lcov_test.dart
new file mode 100644
index 0000000..ca62117
--- /dev/null
+++ b/pkgs/coverage/test/lcov_test.dart
@@ -0,0 +1,364 @@
+// Copyright (c) 2015, 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.
+
+import 'dart:async';
+import 'dart:io';
+
+import 'package:coverage/coverage.dart';
+import 'package:coverage/src/util.dart';
+import 'package:glob/glob.dart';
+import 'package:path/path.dart' as p;
+import 'package:test/test.dart';
+import 'package:test_process/test_process.dart';
+
+final _sampleAppPath = p.join('test', 'test_files', 'test_app.dart');
+final _sampleGeneratedPath = p.join('test', 'test_files', 'test_app.g.dart');
+final _isolateLibPath = p.join('test', 'test_files', 'test_app_isolate.dart');
+
+final _sampleAppFileUri = p.toUri(p.absolute(_sampleAppPath)).toString();
+final _sampleGeneratedFileUri =
+    p.toUri(p.absolute(_sampleGeneratedPath)).toString();
+final _isolateLibFileUri = p.toUri(p.absolute(_isolateLibPath)).toString();
+
+void main() {
+  test('validate hitMap', () async {
+    final hitmap = await _getHitMap();
+
+    expect(hitmap, contains(_sampleAppFileUri));
+    expect(hitmap, contains(_sampleGeneratedFileUri));
+    expect(hitmap, contains(_isolateLibFileUri));
+    expect(hitmap, contains('package:coverage/src/util.dart'));
+
+    final sampleAppHitMap = hitmap[_sampleAppFileUri];
+    final sampleAppHitLines = sampleAppHitMap?.lineHits;
+    final sampleAppHitFuncs = sampleAppHitMap?.funcHits;
+    final sampleAppFuncNames = sampleAppHitMap?.funcNames;
+    final sampleAppBranchHits = sampleAppHitMap?.branchHits;
+
+    expect(sampleAppHitLines, containsPair(53, greaterThanOrEqualTo(1)),
+        reason: 'be careful if you modify the test file');
+    expect(sampleAppHitLines, containsPair(57, 0),
+        reason: 'be careful if you modify the test file');
+    expect(sampleAppHitLines, isNot(contains(39)),
+        reason: 'be careful if you modify the test file');
+    expect(sampleAppHitFuncs, containsPair(52, 1),
+        reason: 'be careful if you modify the test file');
+    expect(sampleAppHitFuncs, containsPair(56, 0),
+        reason: 'be careful if you modify the test file');
+    expect(sampleAppFuncNames, containsPair(52, 'usedMethod'),
+        reason: 'be careful if you modify the test file');
+    expect(sampleAppBranchHits, containsPair(48, 1),
+        reason: 'be careful if you modify the test file');
+  });
+
+  test('validate hitMap, old VM without branch coverage', () async {
+    final hitmap = await _getHitMap();
+
+    expect(hitmap, contains(_sampleAppFileUri));
+    expect(hitmap, contains(_sampleGeneratedFileUri));
+    expect(hitmap, contains(_isolateLibFileUri));
+    expect(hitmap, contains('package:coverage/src/util.dart'));
+
+    final sampleAppHitMap = hitmap[_sampleAppFileUri];
+    final sampleAppHitLines = sampleAppHitMap?.lineHits;
+    final sampleAppHitFuncs = sampleAppHitMap?.funcHits;
+    final sampleAppFuncNames = sampleAppHitMap?.funcNames;
+
+    expect(sampleAppHitLines, containsPair(53, greaterThanOrEqualTo(1)),
+        reason: 'be careful if you modify the test file');
+    expect(sampleAppHitLines, containsPair(57, 0),
+        reason: 'be careful if you modify the test file');
+    expect(sampleAppHitLines, isNot(contains(39)),
+        reason: 'be careful if you modify the test file');
+    expect(sampleAppHitFuncs, containsPair(52, 1),
+        reason: 'be careful if you modify the test file');
+    expect(sampleAppHitFuncs, containsPair(56, 0),
+        reason: 'be careful if you modify the test file');
+    expect(sampleAppFuncNames, containsPair(52, 'usedMethod'),
+        reason: 'be careful if you modify the test file');
+  });
+
+  group('LcovFormatter', () {
+    test('format()', () async {
+      final hitmap = await _getHitMap();
+
+      final resolver = await Resolver.create(packagePath: '.');
+      // ignore: deprecated_member_use_from_same_package
+      final formatter = LcovFormatter(resolver);
+
+      final res = await formatter
+          .format(hitmap.map((key, value) => MapEntry(key, value.lineHits)));
+
+      expect(res, contains(p.absolute(_sampleAppPath)));
+      expect(res, contains(p.absolute(_sampleGeneratedPath)));
+      expect(res, contains(p.absolute(_isolateLibPath)));
+      expect(res, contains(p.absolute(p.join('lib', 'src', 'util.dart'))));
+    });
+
+    test('formatLcov()', () async {
+      final hitmap = await _getHitMap();
+
+      final resolver = await Resolver.create(packagePath: '.');
+      final res = hitmap.formatLcov(resolver);
+
+      expect(res, contains(p.absolute(_sampleAppPath)));
+      expect(res, contains(p.absolute(_sampleGeneratedPath)));
+      expect(res, contains(p.absolute(_isolateLibPath)));
+      expect(res, contains(p.absolute(p.join('lib', 'src', 'util.dart'))));
+    });
+
+    test('formatLcov() includes files in reportOn list', () async {
+      final hitmap = await _getHitMap();
+
+      final resolver = await Resolver.create(packagePath: '.');
+      final res = hitmap.formatLcov(resolver, reportOn: ['lib/', 'test/']);
+
+      expect(res, contains(p.absolute(_sampleAppPath)));
+      expect(res, contains(p.absolute(_sampleGeneratedPath)));
+      expect(res, contains(p.absolute(_isolateLibPath)));
+      expect(res, contains(p.absolute(p.join('lib', 'src', 'util.dart'))));
+    });
+
+    test('formatLcov() excludes files not in reportOn list', () async {
+      final hitmap = await _getHitMap();
+
+      final resolver = await Resolver.create(packagePath: '.');
+      final res = hitmap.formatLcov(resolver, reportOn: ['lib/']);
+
+      expect(res, isNot(contains(p.absolute(_sampleAppPath))));
+      expect(res, isNot(contains(p.absolute(_sampleGeneratedPath))));
+      expect(res, isNot(contains(p.absolute(_isolateLibPath))));
+      expect(res, contains(p.absolute(p.join('lib', 'src', 'util.dart'))));
+    });
+
+    test('formatLcov() excludes files matching glob patterns', () async {
+      final hitmap = await _getHitMap();
+
+      final resolver = await Resolver.create(packagePath: '.');
+      final res = hitmap.formatLcov(
+        resolver,
+        ignoreGlobs: {Glob('**/*.g.dart'), Glob('**/util.dart')},
+      );
+
+      expect(res, contains(p.absolute(_sampleAppPath)));
+      expect(res, isNot(contains(p.absolute(_sampleGeneratedPath))));
+      expect(res, contains(p.absolute(_isolateLibPath)));
+      expect(
+        res,
+        isNot(contains(p.absolute(p.join('lib', 'src', 'util.dart')))),
+      );
+    });
+
+    test(
+        'formatLcov() excludes files matching glob patterns regardless of their'
+        'presence on reportOn list', () async {
+      final hitmap = await _getHitMap();
+
+      final resolver = await Resolver.create(packagePath: '.');
+      final res = hitmap.formatLcov(
+        resolver,
+        reportOn: ['test/'],
+        ignoreGlobs: {Glob('**/*.g.dart')},
+      );
+
+      expect(res, contains(p.absolute(_sampleAppPath)));
+      expect(res, isNot(contains(p.absolute(_sampleGeneratedPath))));
+      expect(res, contains(p.absolute(_isolateLibPath)));
+    });
+
+    test('formatLcov() uses paths relative to basePath', () async {
+      final hitmap = await _getHitMap();
+
+      final resolver = await Resolver.create(packagePath: '.');
+      final res = hitmap.formatLcov(resolver, basePath: p.absolute('lib'));
+
+      expect(
+          res, isNot(contains(p.absolute(p.join('lib', 'src', 'util.dart')))));
+      expect(res, contains(p.join('src', 'util.dart')));
+    });
+  });
+
+  group('PrettyPrintFormatter', () {
+    test('format()', () async {
+      final hitmap = await _getHitMap();
+
+      final resolver = await Resolver.create(packagePath: '.');
+      // ignore: deprecated_member_use_from_same_package
+      final formatter = PrettyPrintFormatter(resolver, Loader());
+
+      final res = await formatter
+          .format(hitmap.map((key, value) => MapEntry(key, value.lineHits)));
+
+      expect(res, contains(p.absolute(_sampleAppPath)));
+      expect(res, contains(p.absolute(_sampleGeneratedPath)));
+      expect(res, contains(p.absolute(_isolateLibPath)));
+      expect(res, contains(p.absolute(p.join('lib', 'src', 'util.dart'))));
+
+      // be very careful if you change the test file
+      expect(res, contains('      0|  return a - b;'));
+
+      expect(res, contains('|  return withTimeout(() async {'),
+          reason: 'be careful if you change lib/src/util.dart');
+
+      final hitLineRegexp = RegExp(r'\s+(\d+)\|  return a \+ b;');
+      final match = hitLineRegexp.allMatches(res).single;
+
+      final hitCount = int.parse(match[1]!);
+      expect(hitCount, greaterThanOrEqualTo(1));
+    });
+
+    test('prettyPrint()', () async {
+      final hitmap = await _getHitMap();
+
+      final resolver = await Resolver.create(packagePath: '.');
+      final res = await hitmap.prettyPrint(resolver, Loader());
+
+      expect(res, contains(p.absolute(_sampleAppPath)));
+      expect(res, contains(p.absolute(_sampleGeneratedPath)));
+      expect(res, contains(p.absolute(_isolateLibPath)));
+      expect(res, contains(p.absolute(p.join('lib', 'src', 'util.dart'))));
+
+      // be very careful if you change the test file
+      expect(res, contains('      0|  return a - b;'));
+
+      expect(res, contains('|  return withTimeout(() async {'),
+          reason: 'be careful if you change lib/src/util.dart');
+
+      final hitLineRegexp = RegExp(r'\s+(\d+)\|  return a \+ b;');
+      final match = hitLineRegexp.allMatches(res).single;
+
+      final hitCount = int.parse(match[1]!);
+      expect(hitCount, greaterThanOrEqualTo(1));
+    });
+
+    test('prettyPrint() includes files in reportOn list', () async {
+      final hitmap = await _getHitMap();
+
+      final resolver = await Resolver.create(packagePath: '.');
+      final res = await hitmap
+          .prettyPrint(resolver, Loader(), reportOn: ['lib/', 'test/']);
+
+      expect(res, contains(p.absolute(_sampleAppPath)));
+      expect(res, contains(p.absolute(_sampleGeneratedPath)));
+      expect(res, contains(p.absolute(_isolateLibPath)));
+      expect(res, contains(p.absolute(p.join('lib', 'src', 'util.dart'))));
+    });
+
+    test('prettyPrint() excludes files not in reportOn list', () async {
+      final hitmap = await _getHitMap();
+
+      final resolver = await Resolver.create(packagePath: '.');
+      final res =
+          await hitmap.prettyPrint(resolver, Loader(), reportOn: ['lib/']);
+
+      expect(res, isNot(contains(p.absolute(_sampleAppPath))));
+      expect(res, isNot(contains(p.absolute(_sampleGeneratedPath))));
+      expect(res, isNot(contains(p.absolute(_isolateLibPath))));
+      expect(res, contains(p.absolute(p.join('lib', 'src', 'util.dart'))));
+    });
+
+    test('prettyPrint() excludes files matching glob patterns', () async {
+      final hitmap = await _getHitMap();
+
+      final resolver = await Resolver.create(packagePath: '.');
+      final res = await hitmap.prettyPrint(
+        resolver,
+        Loader(),
+        ignoreGlobs: {Glob('**/*.g.dart'), Glob('**/util.dart')},
+      );
+
+      expect(res, contains(p.absolute(_sampleAppPath)));
+      expect(res, isNot(contains(p.absolute(_sampleGeneratedPath))));
+      expect(res, contains(p.absolute(_isolateLibPath)));
+      expect(
+        res,
+        isNot(contains(p.absolute(p.join('lib', 'src', 'util.dart')))),
+      );
+    });
+
+    test(
+        'prettyPrint() excludes files matching glob patterns regardless of'
+        'their presence on reportOn list', () async {
+      final hitmap = await _getHitMap();
+
+      final resolver = await Resolver.create(packagePath: '.');
+      final res = await hitmap.prettyPrint(
+        resolver,
+        Loader(),
+        reportOn: ['test/'],
+        ignoreGlobs: {Glob('**/*.g.dart')},
+      );
+
+      expect(res, contains(p.absolute(_sampleAppPath)));
+      expect(res, isNot(contains(p.absolute(_sampleGeneratedPath))));
+      expect(res, contains(p.absolute(_isolateLibPath)));
+    });
+
+    test('prettyPrint() functions', () async {
+      final hitmap = await _getHitMap();
+
+      final resolver = await Resolver.create(packagePath: '.');
+      final res =
+          await hitmap.prettyPrint(resolver, Loader(), reportFuncs: true);
+
+      expect(res, contains(p.absolute(_sampleAppPath)));
+      expect(res, contains(p.absolute(_sampleGeneratedPath)));
+      expect(res, contains(p.absolute(_isolateLibPath)));
+      expect(res, contains(p.absolute(p.join('lib', 'src', 'util.dart'))));
+
+      // be very careful if you change the test file
+      expect(res, contains('      1|Future<void> main() async {'));
+      expect(res, contains('      1|int usedMethod(int a, int b) {'));
+      expect(res, contains('      0|int unusedMethod(int a, int b) {'));
+      expect(res, contains('       |  return a + b;'));
+    });
+
+    test('prettyPrint() branches', () async {
+      final hitmap = await _getHitMap();
+
+      final resolver = await Resolver.create(packagePath: '.');
+      final res =
+          await hitmap.prettyPrint(resolver, Loader(), reportBranches: true);
+
+      expect(res, contains(p.absolute(_sampleAppPath)));
+      expect(res, contains(p.absolute(_sampleGeneratedPath)));
+      expect(res, contains(p.absolute(_isolateLibPath)));
+      expect(res, contains(p.absolute(p.join('lib', 'src', 'util.dart'))));
+
+      // be very careful if you change the test file
+      expect(res, contains('      1|  if (x == answer) {'));
+      expect(res, contains('      0|  while (i < lines.length) {'));
+      expect(res, contains('       |  bar.baz();'));
+    });
+  });
+}
+
+Future<Map<String, HitMap>> _getHitMap() async {
+  expect(FileSystemEntity.isFileSync(_sampleAppPath), isTrue);
+
+  // select service port.
+  final port = await getOpenPort();
+
+  // start sample app.
+  final sampleAppArgs = [
+    '--pause-isolates-on-exit',
+    '--enable-vm-service=$port',
+    '--branch-coverage',
+    _sampleAppPath
+  ];
+  final sampleProcess =
+      await TestProcess.start(Platform.resolvedExecutable, sampleAppArgs);
+
+  final serviceUri = await serviceUriFromProcess(sampleProcess.stdoutStream());
+
+  // collect hit map.
+  final coverageJson = (await collect(serviceUri, true, true, false, <String>{},
+      functionCoverage: true,
+      branchCoverage: true))['coverage'] as List<Map<String, dynamic>>;
+  final hitMap = HitMap.parseJson(coverageJson);
+
+  await sampleProcess.shouldExit(0);
+
+  return hitMap;
+}
diff --git a/pkgs/coverage/test/resolver_test.dart b/pkgs/coverage/test/resolver_test.dart
new file mode 100644
index 0000000..1161aee
--- /dev/null
+++ b/pkgs/coverage/test/resolver_test.dart
@@ -0,0 +1,211 @@
+// Copyright (c) 2016, 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.
+
+import 'package:coverage/src/resolver.dart';
+import 'package:path/path.dart' as p;
+import 'package:test/test.dart';
+import 'package:test_descriptor/test_descriptor.dart' as d;
+
+void main() {
+  group('Default Resolver', () {
+    setUp(() async {
+      final sandboxUriPath = p.toUri(d.sandbox).toString();
+      await d.dir('bar', [
+        d.dir('lib', [
+          d.file('bar.dart', 'final fizz = "bar";'),
+        ])
+      ]).create();
+
+      await d.dir('foo', [
+        d.dir('.dart_tool', [
+          d.file('bad_package_config.json', 'thisIsntAPackageConfigFile!'),
+          d.file('package_config.json', '''
+{
+  "configVersion": 2,
+  "packages": [
+    {
+      "name": "foo",
+      "rootUri": "../",
+      "packageUri": "lib/"
+    },
+    {
+      "name": "bar",
+      "rootUri": "$sandboxUriPath/bar",
+      "packageUri": "lib/"
+    }
+  ]
+}
+'''),
+        ]),
+        d.dir('lib', [
+          d.file('foo.dart', 'final foo = "bar";'),
+        ]),
+      ]).create();
+
+      await d.dir('sdk', [
+        d.dir('io', [
+          d.file('io.dart', 'final io = "hello";'),
+        ]),
+        d.dir('io_patch', [
+          d.file('io.dart', 'final patch = true;'),
+        ]),
+        d.dir('io_dev', [
+          d.file('io.dart', 'final dev = true;'),
+        ]),
+      ]).create();
+    });
+
+    test('can be created from a package_config.json', () async {
+      final resolver = await Resolver.create(
+          packagesPath:
+              p.join(d.sandbox, 'foo', '.dart_tool', 'package_config.json'));
+      expect(resolver.resolve('package:foo/foo.dart'),
+          p.join(d.sandbox, 'foo', 'lib', 'foo.dart'));
+      expect(resolver.resolve('package:bar/bar.dart'),
+          p.join(d.sandbox, 'bar', 'lib', 'bar.dart'));
+    });
+
+    test('can be created from a package directory', () async {
+      final resolver =
+          await Resolver.create(packagePath: p.join(d.sandbox, 'foo'));
+      expect(resolver.resolve('package:foo/foo.dart'),
+          p.join(d.sandbox, 'foo', 'lib', 'foo.dart'));
+    });
+
+    test('errors if the packagesFile is an unknown format', () async {
+      expect(
+          () async => await Resolver.create(
+              packagesPath: p.join(
+                  d.sandbox, 'foo', '.dart_tool', 'bad_package_config.json')),
+          throwsA(isA<FormatException>()));
+    });
+
+    test('resolves dart: URIs', () async {
+      final resolver = await Resolver.create(
+          packagePath: p.join(d.sandbox, 'foo'),
+          sdkRoot: p.join(d.sandbox, 'sdk'));
+      expect(resolver.resolve('dart:io'),
+          p.join(d.sandbox, 'sdk', 'io', 'io.dart'));
+      expect(resolver.resolve('dart:io-patch/io.dart'), null);
+      expect(resolver.resolve('dart:io-dev/io.dart'),
+          p.join(d.sandbox, 'sdk', 'io_dev', 'io.dart'));
+    });
+
+    test('cannot resolve SDK URIs if sdkRoot is null', () async {
+      final resolver =
+          await Resolver.create(packagePath: p.join(d.sandbox, 'foo'));
+      expect(resolver.resolve('dart:convert'), null);
+    });
+
+    test('cannot resolve package URIs if packagePath is null', () async {
+      // ignore: deprecated_member_use_from_same_package
+      final resolver = Resolver();
+      expect(resolver.resolve('package:foo/foo.dart'), null);
+    });
+
+    test('cannot resolve package URIs if packagePath is not found', () async {
+      final resolver =
+          await Resolver.create(packagePath: p.join(d.sandbox, 'foo'));
+      expect(resolver.resolve('package:baz/baz.dart'), null);
+    });
+
+    test('cannot resolve unexpected URI schemes', () async {
+      final resolver =
+          await Resolver.create(packagePath: p.join(d.sandbox, 'foo'));
+      expect(resolver.resolve('thing:foo/foo.dart'), null);
+    });
+  });
+
+  group('Bazel resolver', () {
+    const workspace = 'foo';
+    final resolver = BazelResolver(workspacePath: workspace);
+
+    test('does not resolve SDK URIs', () {
+      expect(resolver.resolve('dart:convert'), null);
+    });
+
+    test('resolves third-party package URIs', () {
+      expect(resolver.resolve('package:foo/bar.dart'),
+          'third_party/dart/foo/lib/bar.dart');
+      expect(resolver.resolve('package:foo/src/bar.dart'),
+          'third_party/dart/foo/lib/src/bar.dart');
+    });
+
+    test('resolves non-third-party package URIs', () {
+      expect(
+          resolver.resolve('package:foo.bar/baz.dart'), 'foo/bar/lib/baz.dart');
+      expect(resolver.resolve('package:foo.bar/src/baz.dart'),
+          'foo/bar/lib/src/baz.dart');
+    });
+
+    test('resolves file URIs', () {
+      expect(
+          resolver
+              .resolve('file://x/y/z.runfiles/$workspace/foo/bar/lib/baz.dart'),
+          'foo/bar/lib/baz.dart');
+      expect(
+          resolver.resolve(
+              'file://x/y/z.runfiles/$workspace/foo/bar/lib/src/baz.dart'),
+          'foo/bar/lib/src/baz.dart');
+    });
+
+    test('resolves HTTPS URIs containing /packages/', () {
+      expect(resolver.resolve('https://host:8080/a/b/packages/foo/bar.dart'),
+          'third_party/dart/foo/lib/bar.dart');
+      expect(
+          resolver.resolve('https://host:8080/a/b/packages/foo/src/bar.dart'),
+          'third_party/dart/foo/lib/src/bar.dart');
+      expect(
+          resolver.resolve('https://host:8080/a/b/packages/foo.bar/baz.dart'),
+          'foo/bar/lib/baz.dart');
+      expect(
+          resolver
+              .resolve('https://host:8080/a/b/packages/foo.bar/src/baz.dart'),
+          'foo/bar/lib/src/baz.dart');
+    });
+
+    test('resolves HTTP URIs containing /packages/', () {
+      expect(resolver.resolve('http://host:8080/a/b/packages/foo/bar.dart'),
+          'third_party/dart/foo/lib/bar.dart');
+      expect(resolver.resolve('http://host:8080/a/b/packages/foo/src/bar.dart'),
+          'third_party/dart/foo/lib/src/bar.dart');
+      expect(resolver.resolve('http://host:8080/a/b/packages/foo.bar/baz.dart'),
+          'foo/bar/lib/baz.dart');
+      expect(
+          resolver
+              .resolve('http://host:8080/a/b/packages/foo.bar/src/baz.dart'),
+          'foo/bar/lib/src/baz.dart');
+    });
+
+    test('resolves HTTPS URIs without /packages/', () {
+      expect(
+          resolver
+              .resolve('https://host:8080/third_party/dart/foo/lib/bar.dart'),
+          'third_party/dart/foo/lib/bar.dart');
+      expect(
+          resolver.resolve(
+              'https://host:8080/third_party/dart/foo/lib/src/bar.dart'),
+          'third_party/dart/foo/lib/src/bar.dart');
+      expect(resolver.resolve('https://host:8080/foo/lib/bar.dart'),
+          'foo/lib/bar.dart');
+      expect(resolver.resolve('https://host:8080/foo/lib/src/bar.dart'),
+          'foo/lib/src/bar.dart');
+    });
+
+    test('resolves HTTP URIs without /packages/', () {
+      expect(
+          resolver
+              .resolve('http://host:8080/third_party/dart/foo/lib/bar.dart'),
+          'third_party/dart/foo/lib/bar.dart');
+      expect(
+          resolver.resolve(
+              'http://host:8080/third_party/dart/foo/lib/src/bar.dart'),
+          'third_party/dart/foo/lib/src/bar.dart');
+      expect(resolver.resolve('http://host:8080/foo/lib/bar.dart'),
+          'foo/lib/bar.dart');
+      expect(resolver.resolve('http://host:8080/foo/lib/src/bar.dart'),
+          'foo/lib/src/bar.dart');
+    });
+  });
+}
diff --git a/pkgs/coverage/test/run_and_collect_test.dart b/pkgs/coverage/test/run_and_collect_test.dart
new file mode 100644
index 0000000..e371f90
--- /dev/null
+++ b/pkgs/coverage/test/run_and_collect_test.dart
@@ -0,0 +1,128 @@
+// Copyright (c) 2015, 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.
+
+import 'package:coverage/coverage.dart';
+import 'package:path/path.dart' as p;
+import 'package:test/test.dart';
+
+import 'test_util.dart';
+
+final _isolateLibPath = p.join('test', 'test_files', 'test_app_isolate.dart');
+
+final _sampleAppFileUri = p.toUri(p.absolute(testAppPath)).toString();
+final _isolateLibFileUri = p.toUri(p.absolute(_isolateLibPath)).toString();
+
+void main() {
+  test('runAndCollect', () async {
+    // use runAndCollect and verify that the results match w/ running manually
+    final coverage = coverageDataFromJson(await runAndCollect(testAppPath));
+    expect(coverage, isNotEmpty);
+
+    final sources = coverage.sources();
+
+    for (var sampleCoverageData in sources[_sampleAppFileUri]!) {
+      expect(sampleCoverageData['hits'], isNotNull);
+    }
+
+    for (var sampleCoverageData in sources[_isolateLibFileUri]!) {
+      expect(sampleCoverageData['hits'], isNotEmpty);
+    }
+
+    final hitMap = await HitMap.parseJson(coverage, checkIgnoredLines: true);
+    checkHitmap(hitMap);
+    final resolver = await Resolver.create();
+    final ignoredLinesInFilesCache = <String, List<List<int>>?>{};
+    final hitMap2 = HitMap.parseJsonSync(coverage,
+        checkIgnoredLines: true,
+        ignoredLinesInFilesCache: ignoredLinesInFilesCache,
+        resolver: resolver);
+    checkHitmap(hitMap2);
+    checkIgnoredLinesInFilesCache(ignoredLinesInFilesCache);
+
+    // Asking again the cache should answer questions about ignored lines,
+    // so providing a resolver that throws when asked for files should be ok.
+    final hitMap3 = HitMap.parseJsonSync(coverage,
+        checkIgnoredLines: true,
+        ignoredLinesInFilesCache: ignoredLinesInFilesCache,
+        resolver: ThrowingResolver());
+    checkHitmap(hitMap3);
+    checkIgnoredLinesInFilesCache(ignoredLinesInFilesCache);
+  });
+}
+
+class ThrowingResolver implements Resolver {
+  @override
+  List<String> get failed => throw UnimplementedError();
+
+  @override
+  String? get packagePath => throw UnimplementedError();
+
+  @override
+  String? get packagesPath => throw UnimplementedError();
+
+  @override
+  String? resolve(String scriptUri) => throw UnimplementedError();
+
+  @override
+  String? resolveSymbolicLinks(String path) => throw UnimplementedError();
+
+  @override
+  String? get sdkRoot => throw UnimplementedError();
+}
+
+void checkIgnoredLinesInFilesCache(
+    Map<String, List<List<int>>?> ignoredLinesInFilesCache) {
+  final keys = ignoredLinesInFilesCache.keys.toList();
+  final testAppKey =
+      keys.where((element) => element.endsWith('test_app.dart')).single;
+  final testAppIsolateKey =
+      keys.where((element) => element.endsWith('test_app_isolate.dart')).single;
+  final packageUtilKey = keys
+      .where((element) => element.endsWith('package:coverage/src/util.dart'))
+      .single;
+  expect(ignoredLinesInFilesCache[packageUtilKey], isEmpty);
+  expect(ignoredLinesInFilesCache[testAppKey], null /* means whole file */);
+  expect(ignoredLinesInFilesCache[testAppIsolateKey], [
+    [51, 51],
+    [53, 57],
+    [62, 65],
+    [66, 72]
+  ]);
+}
+
+void checkHitmap(Map<String, HitMap> hitMap) {
+  expect(hitMap, isNot(contains(_sampleAppFileUri)));
+
+  final actualHitMap = hitMap[_isolateLibFileUri];
+  final actualLineHits = actualHitMap?.lineHits;
+  final expectedLineHits = {
+    11: 1,
+    12: 1,
+    13: 1,
+    15: 0,
+    19: 1,
+    23: 1,
+    24: 2,
+    28: 1,
+    29: 1,
+    30: 1,
+    32: 0,
+    38: 1,
+    39: 1,
+    41: 1,
+    42: 4,
+    43: 1,
+    44: 3,
+    45: 1,
+    48: 1,
+    49: 1,
+    59: 1,
+    60: 1
+  };
+
+  expect(actualLineHits, expectedLineHits);
+  expect(actualHitMap?.funcHits, isNull);
+  expect(actualHitMap?.funcNames, isNull);
+  expect(actualHitMap?.branchHits, isNull);
+}
diff --git a/pkgs/coverage/test/test_files/chrome_precise_report.txt b/pkgs/coverage/test/test_files/chrome_precise_report.txt
new file mode 100644
index 0000000..41a3e64
--- /dev/null
+++ b/pkgs/coverage/test/test_files/chrome_precise_report.txt
@@ -0,0 +1 @@
+[{"scriptId":"5","url":"http://localhost:33587/JvrQonmMf3ATS3rRCO76ZTlBfGvy%2Fj69/packages/test/src/runner/browser/static/host.dart.js","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":598832,"count":1}],"isBlockCoverage":true},{"functionName":"dartProgram","ranges":[{"startOffset":1228,"endOffset":598788,"count":1}],"isBlockCoverage":true},{"functionName":"copyProperties","ranges":[{"startOffset":1255,"endOffset":1430,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1465,"endOffset":2035,"count":1},{"startOffset":1646,"endOffset":1659,"count":0},{"startOffset":1822,"endOffset":1884,"count":0},{"startOffset":1886,"endOffset":1989,"count":0},{"startOffset":1995,"endOffset":2034,"count":0}],"isBlockCoverage":true},{"functionName":"cls","ranges":[{"startOffset":1492,"endOffset":1510,"count":1}],"isBlockCoverage":true},{"functionName":"setFunctionNamesIfNecessary","ranges":[{"startOffset":2041,"endOffset":2464,"count":1},{"startOffset":2168,"endOffset":2460,"count":0}],"isBlockCoverage":true},{"functionName":"t","ranges":[{"startOffset":2093,"endOffset":2113,"count":0}],"isBlockCoverage":false},{"functionName":"inherit","ranges":[{"startOffset":2467,"endOffset":2862,"count":1},{"startOffset":2710,"endOffset":2858,"count":0}],"isBlockCoverage":true},{"functionName":"inheritMany","ranges":[{"startOffset":2865,"endOffset":2982,"count":1}],"isBlockCoverage":true},{"functionName":"mixin","ranges":[{"startOffset":2985,"endOffset":3106,"count":1}],"isBlockCoverage":true},{"functionName":"lazy","ranges":[{"startOffset":3109,"endOffset":3858,"count":1}],"isBlockCoverage":true},{"functionName":"holder.<computed>","ranges":[{"startOffset":3271,"endOffset":3853,"count":1},{"startOffset":3606,"endOffset":3644,"count":0},{"startOffset":3716,"endOffset":3736,"count":0}],"isBlockCoverage":true},{"functionName":"holder.<computed>","ranges":[{"startOffset":3311,"endOffset":3364,"count":0}],"isBlockCoverage":false},{"functionName":"holder.<computed>","ranges":[{"startOffset":3766,"endOffset":3817,"count":1}],"isBlockCoverage":true},{"functionName":"makeConstList","ranges":[{"startOffset":3861,"endOffset":3976,"count":1}],"isBlockCoverage":true},{"functionName":"convertToFastObject","ranges":[{"startOffset":3979,"endOffset":4116,"count":1}],"isBlockCoverage":true},{"functionName":"t","ranges":[{"startOffset":4026,"endOffset":4046,"count":1}],"isBlockCoverage":true},{"functionName":"convertAllToFastObject","ranges":[{"startOffset":4119,"endOffset":4270,"count":1}],"isBlockCoverage":true},{"functionName":"tearOffGetter","ranges":[{"startOffset":4300,"endOffset":5215,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff","ranges":[{"startOffset":5218,"endOffset":5626,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":5357,"endOffset":5539,"count":1}],"isBlockCoverage":true},{"functionName":"installTearOff","ranges":[{"startOffset":5652,"endOffset":6582,"count":1}],"isBlockCoverage":true},{"functionName":"installStaticTearOff","ranges":[{"startOffset":6585,"endOffset":6908,"count":1}],"isBlockCoverage":true},{"functionName":"installInstanceTearOff","ranges":[{"startOffset":6911,"endOffset":7260,"count":1}],"isBlockCoverage":true},{"functionName":"setOrUpdateInterceptorsByTag","ranges":[{"startOffset":7263,"endOffset":7466,"count":1},{"startOffset":7427,"endOffset":7465,"count":0}],"isBlockCoverage":true},{"functionName":"setOrUpdateLeafTags","ranges":[{"startOffset":7469,"endOffset":7645,"count":1},{"startOffset":7606,"endOffset":7644,"count":0}],"isBlockCoverage":true},{"functionName":"updateTypes","ranges":[{"startOffset":7648,"endOffset":7801,"count":0}],"isBlockCoverage":false},{"functionName":"updateHolder","ranges":[{"startOffset":7804,"endOffset":7908,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":7929,"endOffset":9593,"count":1}],"isBlockCoverage":true},{"functionName":"mkInstance","ranges":[{"startOffset":7963,"endOffset":8325,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":8083,"endOffset":8316,"count":1}],"isBlockCoverage":true},{"functionName":"mkStatic","ranges":[{"startOffset":8344,"endOffset":8674,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":8449,"endOffset":8665,"count":1}],"isBlockCoverage":true},{"functionName":"initializeDeferredHunk","ranges":[{"startOffset":9599,"endOffset":9720,"count":0}],"isBlockCoverage":false},{"functionName":"getGlobalFromName","ranges":[{"startOffset":9723,"endOffset":9920,"count":0}],"isBlockCoverage":false},{"functionName":"JS_CONST","ranges":[{"startOffset":9952,"endOffset":9979,"count":0}],"isBlockCoverage":false},{"functionName":"hexDigitValue","ranges":[{"startOffset":10000,"endOffset":10228,"count":1},{"startOffset":10205,"endOffset":10227,"count":0}],"isBlockCoverage":true},{"functionName":"SubListIterable$","ranges":[{"startOffset":10252,"endOffset":10660,"count":0}],"isBlockCoverage":false},{"functionName":"MappedIterable_MappedIterable","ranges":[{"startOffset":10697,"endOffset":11098,"count":0}],"isBlockCoverage":false},{"functionName":"IterableElementError_noElement","ranges":[{"startOffset":11136,"endOffset":11199,"count":0}],"isBlockCoverage":false},{"functionName":"IterableElementError_tooFew","ranges":[{"startOffset":11234,"endOffset":11303,"count":0}],"isBlockCoverage":false},{"functionName":"CodeUnits","ranges":[{"startOffset":11320,"endOffset":11375,"count":0}],"isBlockCoverage":false},{"functionName":"EfficientLengthIterable","ranges":[{"startOffset":11406,"endOffset":11448,"count":0}],"isBlockCoverage":false},{"functionName":"ListIterable","ranges":[{"startOffset":11468,"endOffset":11499,"count":0}],"isBlockCoverage":false},{"functionName":"SubListIterable","ranges":[{"startOffset":11522,"endOffset":11702,"count":0}],"isBlockCoverage":false},{"functionName":"ListIterator","ranges":[{"startOffset":11722,"endOffset":11941,"count":0}],"isBlockCoverage":false},{"functionName":"MappedIterable","ranges":[{"startOffset":11963,"endOffset":12085,"count":0}],"isBlockCoverage":false},{"functionName":"EfficientLengthMappedIterable","ranges":[{"startOffset":12122,"endOffset":12259,"count":0}],"isBlockCoverage":false},{"functionName":"MappedIterator","ranges":[{"startOffset":12281,"endOffset":12439,"count":0}],"isBlockCoverage":false},{"functionName":"MappedListIterable","ranges":[{"startOffset":12465,"endOffset":12578,"count":0}],"isBlockCoverage":false},{"functionName":"WhereIterable","ranges":[{"startOffset":12599,"endOffset":12720,"count":0}],"isBlockCoverage":false},{"functionName":"WhereIterator","ranges":[{"startOffset":12741,"endOffset":12851,"count":0}],"isBlockCoverage":false},{"functionName":"ExpandIterable","ranges":[{"startOffset":12873,"endOffset":12995,"count":0}],"isBlockCoverage":false},{"functionName":"ExpandIterator","ranges":[{"startOffset":13017,"endOffset":13211,"count":0}],"isBlockCoverage":false},{"functionName":"SkipWhileIterable","ranges":[{"startOffset":13236,"endOffset":13361,"count":0}],"isBlockCoverage":false},{"functionName":"SkipWhileIterator","ranges":[{"startOffset":13386,"endOffset":13540,"count":0}],"isBlockCoverage":false},{"functionName":"EmptyIterator","ranges":[{"startOffset":13561,"endOffset":13616,"count":1}],"isBlockCoverage":true},{"functionName":"FixedLengthListMixin","ranges":[{"startOffset":13644,"endOffset":13683,"count":0}],"isBlockCoverage":false},{"functionName":"UnmodifiableListMixin","ranges":[{"startOffset":13712,"endOffset":13752,"count":0}],"isBlockCoverage":false},{"functionName":"UnmodifiableListBase","ranges":[{"startOffset":13780,"endOffset":13819,"count":0}],"isBlockCoverage":false},{"functionName":"ReversedListIterable","ranges":[{"startOffset":13847,"endOffset":13938,"count":0}],"isBlockCoverage":false},{"functionName":"Symbol","ranges":[{"startOffset":13952,"endOffset":14013,"count":1}],"isBlockCoverage":true},{"functionName":"ConstantMap__throwUnmodifiable","ranges":[{"startOffset":14051,"endOffset":14153,"count":0}],"isBlockCoverage":false},{"functionName":"instantiate1","ranges":[{"startOffset":14173,"endOffset":14345,"count":0}],"isBlockCoverage":false},{"functionName":"unminifyOrTag","ranges":[{"startOffset":14366,"endOffset":14570,"count":0}],"isBlockCoverage":false},{"functionName":"getType","ranges":[{"startOffset":14585,"endOffset":14656,"count":1}],"isBlockCoverage":true},{"functionName":"isJsIndexable","ranges":[{"startOffset":14677,"endOffset":14915,"count":0}],"isBlockCoverage":false},{"functionName":"S","ranges":[{"startOffset":14924,"endOffset":15426,"count":1},{"startOffset":15015,"endOffset":15425,"count":0}],"isBlockCoverage":true},{"functionName":"Primitives_objectHashCode","ranges":[{"startOffset":15459,"endOffset":15659,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_parseInt","ranges":[{"startOffset":15686,"endOffset":16847,"count":1},{"startOffset":15821,"endOffset":15869,"count":0},{"startOffset":15981,"endOffset":15988,"count":0},{"startOffset":16026,"endOffset":16051,"count":0},{"startOffset":16201,"endOffset":16328,"count":0},{"startOffset":16338,"endOffset":16456,"count":0},{"startOffset":16466,"endOffset":16539,"count":0},{"startOffset":16541,"endOffset":16846,"count":0}],"isBlockCoverage":true},{"functionName":"Primitives_objectTypeName","ranges":[{"startOffset":16880,"endOffset":17014,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives__objectClassName","ranges":[{"startOffset":17049,"endOffset":18437,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_currentUri","ranges":[{"startOffset":18466,"endOffset":18560,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives__fromCharCodeApply","ranges":[{"startOffset":18597,"endOffset":19022,"count":1},{"startOffset":18798,"endOffset":19021,"count":0}],"isBlockCoverage":true},{"functionName":"Primitives_stringFromCodePoints","ranges":[{"startOffset":19061,"endOffset":19851,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_stringFromCharCodes","ranges":[{"startOffset":19889,"endOffset":20367,"count":1},{"startOffset":20086,"endOffset":20133,"count":0},{"startOffset":20163,"endOffset":20210,"count":0},{"startOffset":20244,"endOffset":20296,"count":0}],"isBlockCoverage":true},{"functionName":"Primitives_stringFromNativeUint8List","ranges":[{"startOffset":20411,"endOffset":20838,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_stringFromCharCode","ranges":[{"startOffset":20875,"endOffset":21388,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_lazyAsJsDate","ranges":[{"startOffset":21419,"endOffset":21566,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_getYear","ranges":[{"startOffset":21592,"endOffset":21708,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_getMonth","ranges":[{"startOffset":21735,"endOffset":21848,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_getDay","ranges":[{"startOffset":21873,"endOffset":21985,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_getHours","ranges":[{"startOffset":22012,"endOffset":22125,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_getMinutes","ranges":[{"startOffset":22154,"endOffset":22269,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_getSeconds","ranges":[{"startOffset":22298,"endOffset":22413,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_getMilliseconds","ranges":[{"startOffset":22447,"endOffset":22567,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_functionNoSuchMethod","ranges":[{"startOffset":22606,"endOffset":23376,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_applyFunction","ranges":[{"startOffset":23408,"endOffset":25001,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives__genericApplyFunction2","ranges":[{"startOffset":25042,"endOffset":28197,"count":0}],"isBlockCoverage":false},{"functionName":"iae","ranges":[{"startOffset":28208,"endOffset":28295,"count":0}],"isBlockCoverage":false},{"functionName":"ioore","ranges":[{"startOffset":28308,"endOffset":28473,"count":0}],"isBlockCoverage":false},{"functionName":"diagnoseIndexError","ranges":[{"startOffset":28499,"endOffset":29047,"count":0}],"isBlockCoverage":false},{"functionName":"diagnoseRangeError","ranges":[{"startOffset":29073,"endOffset":29430,"count":0}],"isBlockCoverage":false},{"functionName":"argumentErrorValue","ranges":[{"startOffset":29456,"endOffset":29540,"count":0}],"isBlockCoverage":false},{"functionName":"checkNum","ranges":[{"startOffset":29556,"endOffset":29696,"count":0}],"isBlockCoverage":false},{"functionName":"wrapException","ranges":[{"startOffset":29717,"endOffset":30104,"count":0}],"isBlockCoverage":false},{"functionName":"toStringWrapper","ranges":[{"startOffset":30127,"endOffset":30193,"count":0}],"isBlockCoverage":false},{"functionName":"throwExpression","ranges":[{"startOffset":30216,"endOffset":30269,"count":0}],"isBlockCoverage":false},{"functionName":"throwConcurrentModificationError","ranges":[{"startOffset":30309,"endOffset":30410,"count":0}],"isBlockCoverage":false},{"functionName":"TypeErrorDecoder_extractPattern","ranges":[{"startOffset":30449,"endOffset":31458,"count":0}],"isBlockCoverage":false},{"functionName":"TypeErrorDecoder_provokeCallErrorOn","ranges":[{"startOffset":31501,"endOffset":31745,"count":0}],"isBlockCoverage":false},{"functionName":"TypeErrorDecoder_provokePropertyErrorOn","ranges":[{"startOffset":31792,"endOffset":31974,"count":0}],"isBlockCoverage":false},{"functionName":"NullError$","ranges":[{"startOffset":31992,"endOffset":32102,"count":0}],"isBlockCoverage":false},{"functionName":"JsNoSuchMethodError$","ranges":[{"startOffset":32130,"endOffset":32326,"count":0}],"isBlockCoverage":false},{"functionName":"unwrapException","ranges":[{"startOffset":32349,"endOffset":36809,"count":0}],"isBlockCoverage":false},{"functionName":"getTraceFromException","ranges":[{"startOffset":36838,"endOffset":37203,"count":0}],"isBlockCoverage":false},{"functionName":"fillLiteralMap","ranges":[{"startOffset":37225,"endOffset":37561,"count":0}],"isBlockCoverage":false},{"functionName":"invokeClosure","ranges":[{"startOffset":37582,"endOffset":38172,"count":1},{"startOffset":37758,"endOffset":37800,"count":0},{"startOffset":37864,"endOffset":37916,"count":0},{"startOffset":37925,"endOffset":37983,"count":0},{"startOffset":37992,"endOffset":38056,"count":0},{"startOffset":38064,"endOffset":38171,"count":0}],"isBlockCoverage":true},{"functionName":"convertDartClosureToJS","ranges":[{"startOffset":38202,"endOffset":38679,"count":1},{"startOffset":38314,"endOffset":38321,"count":0},{"startOffset":38390,"endOffset":38407,"count":0}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":38426,"endOffset":38578,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":38476,"endOffset":38569,"count":1}],"isBlockCoverage":true},{"functionName":"Closure_fromTearOff","ranges":[{"startOffset":38706,"endOffset":41471,"count":1},{"startOffset":39469,"endOffset":39486,"count":0},{"startOffset":40204,"endOffset":40709,"count":0}],"isBlockCoverage":true},{"functionName":"static_tear_off","ranges":[{"startOffset":39300,"endOffset":39368,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":40070,"endOffset":40176,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":40110,"endOffset":40165,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":40461,"endOffset":40599,"count":0}],"isBlockCoverage":false},{"functionName":"Closure_cspForwardCall","ranges":[{"startOffset":41501,"endOffset":42886,"count":1},{"startOffset":41627,"endOffset":41634,"count":0},{"startOffset":41646,"endOffset":41801,"count":0},{"startOffset":41810,"endOffset":41967,"count":0},{"startOffset":41976,"endOffset":42139,"count":0},{"startOffset":42148,"endOffset":42317,"count":0},{"startOffset":42326,"endOffset":42501,"count":0},{"startOffset":42510,"endOffset":42691,"count":0}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":41671,"endOffset":41781,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":41835,"endOffset":41947,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":42001,"endOffset":42119,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":42173,"endOffset":42297,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":42351,"endOffset":42481,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":42535,"endOffset":42671,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":42726,"endOffset":42851,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":42762,"endOffset":42838,"count":0}],"isBlockCoverage":false},{"functionName":"Closure_forwardCallTo","ranges":[{"startOffset":42915,"endOffset":44616,"count":1},{"startOffset":43278,"endOffset":43304,"count":0},{"startOffset":43569,"endOffset":43586,"count":0},{"startOffset":43798,"endOffset":43916,"count":0},{"startOffset":44191,"endOffset":44208,"count":0},{"startOffset":44406,"endOffset":44518,"count":0}],"isBlockCoverage":true},{"functionName":"Closure_cspForwardInterceptedCall","ranges":[{"startOffset":44657,"endOffset":46449,"count":1},{"startOffset":44855,"endOffset":44862,"count":0},{"startOffset":44874,"endOffset":44974,"count":0},{"startOffset":44983,"endOffset":45158,"count":0},{"startOffset":45167,"endOffset":45346,"count":0},{"startOffset":45355,"endOffset":45540,"count":0},{"startOffset":45549,"endOffset":45740,"count":0},{"startOffset":45749,"endOffset":45946,"count":0},{"startOffset":45955,"endOffset":46158,"count":0}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":45008,"endOffset":45128,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":45192,"endOffset":45316,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":45380,"endOffset":45510,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":45574,"endOffset":45710,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":45774,"endOffset":45916,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":45980,"endOffset":46128,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":46193,"endOffset":46401,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":46235,"endOffset":46388,"count":0}],"isBlockCoverage":false},{"functionName":"Closure_forwardInterceptedCallTo","ranges":[{"startOffset":46489,"endOffset":48059,"count":1},{"startOffset":47112,"endOffset":47138,"count":0},{"startOffset":47326,"endOffset":47636,"count":0},{"startOffset":47950,"endOffset":47967,"count":0}],"isBlockCoverage":true},{"functionName":"closureFromTearOff","ranges":[{"startOffset":48085,"endOffset":48339,"count":1}],"isBlockCoverage":true},{"functionName":"BoundClosure_selfOf","ranges":[{"startOffset":48366,"endOffset":48419,"count":0}],"isBlockCoverage":false},{"functionName":"BoundClosure_receiverOf","ranges":[{"startOffset":48450,"endOffset":48507,"count":0}],"isBlockCoverage":false},{"functionName":"BoundClosure_computeFieldNamed","ranges":[{"startOffset":48545,"endOffset":48918,"count":1}],"isBlockCoverage":true},{"functionName":"stringTypeCheck","ranges":[{"startOffset":48941,"endOffset":49144,"count":1},{"startOffset":48992,"endOffset":49005,"count":0},{"startOffset":49064,"endOffset":49143,"count":0}],"isBlockCoverage":true},{"functionName":"stringTypeCast","ranges":[{"startOffset":49166,"endOffset":49339,"count":1},{"startOffset":49220,"endOffset":49236,"count":0},{"startOffset":49259,"endOffset":49338,"count":0}],"isBlockCoverage":true},{"functionName":"doubleTypeCheck","ranges":[{"startOffset":49362,"endOffset":49565,"count":0}],"isBlockCoverage":false},{"functionName":"numTypeCheck","ranges":[{"startOffset":49585,"endOffset":49785,"count":0}],"isBlockCoverage":false},{"functionName":"boolTypeCheck","ranges":[{"startOffset":49806,"endOffset":50008,"count":0}],"isBlockCoverage":false},{"functionName":"intTypeCheck","ranges":[{"startOffset":50028,"endOffset":50259,"count":1},{"startOffset":50079,"endOffset":50092,"count":0},{"startOffset":50182,"endOffset":50258,"count":0}],"isBlockCoverage":true},{"functionName":"intTypeCast","ranges":[{"startOffset":50278,"endOffset":50479,"count":1},{"startOffset":50363,"endOffset":50379,"count":0},{"startOffset":50402,"endOffset":50478,"count":0}],"isBlockCoverage":true},{"functionName":"propertyTypeError","ranges":[{"startOffset":50504,"endOffset":50660,"count":0}],"isBlockCoverage":false},{"functionName":"interceptedTypeCheck","ranges":[{"startOffset":50688,"endOffset":50942,"count":1},{"startOffset":50800,"endOffset":50830,"count":0},{"startOffset":50892,"endOffset":50941,"count":0}],"isBlockCoverage":true},{"functionName":"stringSuperNativeTypeCheck","ranges":[{"startOffset":50976,"endOffset":51227,"count":0}],"isBlockCoverage":false},{"functionName":"listTypeCheck","ranges":[{"startOffset":51248,"endOffset":51467,"count":1},{"startOffset":51380,"endOffset":51466,"count":0}],"isBlockCoverage":true},{"functionName":"listSuperNativeTypeCheck","ranges":[{"startOffset":51499,"endOffset":51766,"count":0}],"isBlockCoverage":false},{"functionName":"extractFunctionTypeObjectFromInternal","ranges":[{"startOffset":51811,"endOffset":52082,"count":1},{"startOffset":52062,"endOffset":52081,"count":0}],"isBlockCoverage":true},{"functionName":"functionTypeTest","ranges":[{"startOffset":52106,"endOffset":52520,"count":1},{"startOffset":52204,"endOffset":52217,"count":0},{"startOffset":52417,"endOffset":52430,"count":0}],"isBlockCoverage":true},{"functionName":"functionTypeCheck","ranges":[{"startOffset":52545,"endOffset":53038,"count":1},{"startOffset":52686,"endOffset":52699,"count":0},{"startOffset":52824,"endOffset":52979,"count":0}],"isBlockCoverage":true},{"functionName":"futureOrCheck","ranges":[{"startOffset":53059,"endOffset":53270,"count":1},{"startOffset":53106,"endOffset":53153,"count":0},{"startOffset":53163,"endOffset":53248,"count":0}],"isBlockCoverage":true},{"functionName":"TypeErrorImplementation$","ranges":[{"startOffset":53302,"endOffset":53507,"count":0}],"isBlockCoverage":false},{"functionName":"CastErrorImplementation$","ranges":[{"startOffset":53539,"endOffset":53744,"count":0}],"isBlockCoverage":false},{"functionName":"_typeDescription","ranges":[{"startOffset":53768,"endOffset":54148,"count":0}],"isBlockCoverage":false},{"functionName":"throwCyclicInit","ranges":[{"startOffset":54171,"endOffset":54292,"count":0}],"isBlockCoverage":false},{"functionName":"RuntimeError$","ranges":[{"startOffset":54313,"endOffset":54380,"count":0}],"isBlockCoverage":false},{"functionName":"getIsolateAffinityTag","ranges":[{"startOffset":54409,"endOffset":54472,"count":1}],"isBlockCoverage":true},{"functionName":"setRuntimeTypeInfo","ranges":[{"startOffset":54498,"endOffset":54572,"count":1}],"isBlockCoverage":true},{"functionName":"getRuntimeTypeInfo","ranges":[{"startOffset":54598,"endOffset":54689,"count":1},{"startOffset":54651,"endOffset":54658,"count":0}],"isBlockCoverage":true},{"functionName":"getRuntimeTypeArguments","ranges":[{"startOffset":54720,"endOffset":54876,"count":0}],"isBlockCoverage":false},{"functionName":"getRuntimeTypeArgumentIntercepted","ranges":[{"startOffset":54917,"endOffset":55240,"count":1},{"startOffset":55207,"endOffset":55213,"count":0}],"isBlockCoverage":true},{"functionName":"getRuntimeTypeArgument","ranges":[{"startOffset":55270,"endOffset":55575,"count":1},{"startOffset":55542,"endOffset":55548,"count":0}],"isBlockCoverage":true},{"functionName":"getTypeArgumentByIndex","ranges":[{"startOffset":55605,"endOffset":55768,"count":1}],"isBlockCoverage":true},{"functionName":"runtimeTypeToString","ranges":[{"startOffset":55795,"endOffset":55864,"count":0}],"isBlockCoverage":false},{"functionName":"_runtimeTypeToString","ranges":[{"startOffset":55892,"endOffset":57053,"count":0}],"isBlockCoverage":false},{"functionName":"_functionRtiToString","ranges":[{"startOffset":57081,"endOffset":59945,"count":0}],"isBlockCoverage":false},{"functionName":"_joinArguments","ranges":[{"startOffset":59967,"endOffset":60636,"count":0}],"isBlockCoverage":false},{"functionName":"substitute","ranges":[{"startOffset":60654,"endOffset":61121,"count":1},{"startOffset":60849,"endOffset":60856,"count":0},{"startOffset":60992,"endOffset":61120,"count":0}],"isBlockCoverage":true},{"functionName":"checkSubtype","ranges":[{"startOffset":61141,"endOffset":61627,"count":1},{"startOffset":61512,"endOffset":61525,"count":0}],"isBlockCoverage":true},{"functionName":"assertSubtype","ranges":[{"startOffset":61648,"endOffset":62224,"count":1},{"startOffset":61923,"endOffset":62223,"count":0}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":61987,"endOffset":62115,"count":0}],"isBlockCoverage":false},{"functionName":"assertIsSubtype","ranges":[{"startOffset":62247,"endOffset":62611,"count":1},{"startOffset":62464,"endOffset":62605,"count":0}],"isBlockCoverage":true},{"functionName":"throwTypeError","ranges":[{"startOffset":62633,"endOffset":62746,"count":0}],"isBlockCoverage":false},{"functionName":"areSubtypes","ranges":[{"startOffset":62765,"endOffset":63196,"count":1},{"startOffset":62841,"endOffset":62853,"count":0},{"startOffset":62875,"endOffset":63042,"count":0},{"startOffset":63158,"endOffset":63171,"count":0}],"isBlockCoverage":true},{"functionName":"computeSignature","ranges":[{"startOffset":63220,"endOffset":63407,"count":0}],"isBlockCoverage":false},{"functionName":"isSupertypeOfNullRecursive","ranges":[{"startOffset":63441,"endOffset":63818,"count":0}],"isBlockCoverage":false},{"functionName":"checkSubtypeOfRuntimeType","ranges":[{"startOffset":63851,"endOffset":64616,"count":1},{"startOffset":63918,"endOffset":64038,"count":0},{"startOffset":64201,"endOffset":64290,"count":0}],"isBlockCoverage":true},{"functionName":"assertSubtypeOfRuntimeType","ranges":[{"startOffset":64650,"endOffset":64869,"count":1},{"startOffset":64755,"endOffset":64842,"count":0}],"isBlockCoverage":true},{"functionName":"_isSubtype","ranges":[{"startOffset":64887,"endOffset":67156,"count":1},{"startOffset":65190,"endOffset":65202,"count":0},{"startOffset":65318,"endOffset":65331,"count":0},{"startOffset":65421,"endOffset":65427,"count":0},{"startOffset":65435,"endOffset":65465,"count":0},{"startOffset":65507,"endOffset":65520,"count":0},{"startOffset":65562,"endOffset":65575,"count":0},{"startOffset":65945,"endOffset":65951,"count":0},{"startOffset":65992,"endOffset":66068,"count":0},{"startOffset":66152,"endOffset":66605,"count":0},{"startOffset":66860,"endOffset":66873,"count":0},{"startOffset":67044,"endOffset":67050,"count":0}],"isBlockCoverage":true},{"functionName":"_isFunctionSubtype","ranges":[{"startOffset":67182,"endOffset":69335,"count":1},{"startOffset":67490,"endOffset":67503,"count":0},{"startOffset":67571,"endOffset":67584,"count":0},{"startOffset":67698,"endOffset":67711,"count":0},{"startOffset":67752,"endOffset":67765,"count":0},{"startOffset":67825,"endOffset":67838,"count":0},{"startOffset":68299,"endOffset":68331,"count":0},{"startOffset":68388,"endOffset":68401,"count":0},{"startOffset":68503,"endOffset":68516,"count":0},{"startOffset":68659,"endOffset":68672,"count":0},{"startOffset":68848,"endOffset":68861,"count":0},{"startOffset":68938,"endOffset":69054,"count":0},{"startOffset":69179,"endOffset":69334,"count":0}],"isBlockCoverage":true},{"functionName":"namedParametersSubtypeCheck","ranges":[{"startOffset":69370,"endOffset":69743,"count":0}],"isBlockCoverage":false},{"functionName":"instantiatedGenericFunctionType","ranges":[{"startOffset":69782,"endOffset":69981,"count":0}],"isBlockCoverage":false},{"functionName":"finishBindInstantiatedFunctionType","ranges":[{"startOffset":70023,"endOffset":70893,"count":0}],"isBlockCoverage":false},{"functionName":"bindInstantiatedType","ranges":[{"startOffset":70921,"endOffset":71830,"count":0}],"isBlockCoverage":false},{"functionName":"bindInstantiatedTypes","ranges":[{"startOffset":71859,"endOffset":72120,"count":0}],"isBlockCoverage":false},{"functionName":"JsLinkedHashMap_JsLinkedHashMap$es6","ranges":[{"startOffset":72163,"endOffset":72233,"count":1}],"isBlockCoverage":true},{"functionName":"defineProperty","ranges":[{"startOffset":72255,"endOffset":72427,"count":0}],"isBlockCoverage":false},{"functionName":"lookupAndCacheInterceptor","ranges":[{"startOffset":72460,"endOffset":74952,"count":0}],"isBlockCoverage":false},{"functionName":"patchInteriorProto","ranges":[{"startOffset":74978,"endOffset":75265,"count":0}],"isBlockCoverage":false},{"functionName":"makeLeafDispatchRecord","ranges":[{"startOffset":75295,"endOffset":75430,"count":1}],"isBlockCoverage":true},{"functionName":"makeDefaultDispatchRecord","ranges":[{"startOffset":75463,"endOffset":75734,"count":1}],"isBlockCoverage":true},{"functionName":"initNativeDispatch","ranges":[{"startOffset":75760,"endOffset":75916,"count":1},{"startOffset":75826,"endOffset":75833,"count":0}],"isBlockCoverage":true},{"functionName":"initNativeDispatchContinue","ranges":[{"startOffset":75950,"endOffset":77230,"count":1}],"isBlockCoverage":true},{"functionName":"fun","ranges":[{"startOffset":76329,"endOffset":76351,"count":0}],"isBlockCoverage":false},{"functionName":"initHooks","ranges":[{"startOffset":77247,"endOffset":78506,"count":1},{"startOffset":77761,"endOffset":78174,"count":0}],"isBlockCoverage":true},{"functionName":"applyHooksTransformer","ranges":[{"startOffset":78535,"endOffset":78613,"count":1}],"isBlockCoverage":true},{"functionName":"JSSyntaxRegExp_makeNative","ranges":[{"startOffset":78646,"endOffset":79188,"count":0}],"isBlockCoverage":false},{"functionName":"stringContainsUnchecked","ranges":[{"startOffset":79219,"endOffset":79767,"count":0}],"isBlockCoverage":false},{"functionName":"stringReplaceFirstRE","ranges":[{"startOffset":79795,"endOffset":80070,"count":0}],"isBlockCoverage":false},{"functionName":"stringReplaceAllUnchecked","ranges":[{"startOffset":80103,"endOffset":81120,"count":0}],"isBlockCoverage":false},{"functionName":"stringReplaceFirstUnchecked","ranges":[{"startOffset":81155,"endOffset":82205,"count":0}],"isBlockCoverage":false},{"functionName":"stringReplaceRangeUnchecked","ranges":[{"startOffset":82240,"endOffset":82446,"count":0}],"isBlockCoverage":false},{"functionName":"ConstantMapView","ranges":[{"startOffset":82469,"endOffset":82552,"count":0}],"isBlockCoverage":false},{"functionName":"ConstantMap","ranges":[{"startOffset":82571,"endOffset":82601,"count":0}],"isBlockCoverage":false},{"functionName":"ConstantStringMap","ranges":[{"startOffset":82626,"endOffset":82792,"count":1}],"isBlockCoverage":true},{"functionName":"Instantiation","ranges":[{"startOffset":82813,"endOffset":82845,"count":0}],"isBlockCoverage":false},{"functionName":"Instantiation1","ranges":[{"startOffset":82867,"endOffset":82960,"count":0}],"isBlockCoverage":false},{"functionName":"JSInvocationMirror","ranges":[{"startOffset":82986,"endOffset":83199,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_functionNoSuchMethod_closure","ranges":[{"startOffset":83246,"endOffset":83401,"count":0}],"isBlockCoverage":false},{"functionName":"TypeErrorDecoder","ranges":[{"startOffset":83425,"endOffset":83645,"count":0}],"isBlockCoverage":false},{"functionName":"NullError","ranges":[{"startOffset":83662,"endOffset":83747,"count":0}],"isBlockCoverage":false},{"functionName":"JsNoSuchMethodError","ranges":[{"startOffset":83774,"endOffset":83900,"count":0}],"isBlockCoverage":false},{"functionName":"UnknownJsTypeError","ranges":[{"startOffset":83926,"endOffset":83991,"count":0}],"isBlockCoverage":false},{"functionName":"ExceptionAndStackTrace","ranges":[{"startOffset":84021,"endOffset":84127,"count":0}],"isBlockCoverage":false},{"functionName":"unwrapException_saveStackTrace","ranges":[{"startOffset":84165,"endOffset":84236,"count":0}],"isBlockCoverage":false},{"functionName":"_StackTrace","ranges":[{"startOffset":84255,"endOffset":84353,"count":0}],"isBlockCoverage":false},{"functionName":"Closure","ranges":[{"startOffset":84368,"endOffset":84394,"count":0}],"isBlockCoverage":false},{"functionName":"TearOffClosure","ranges":[{"startOffset":84416,"endOffset":84449,"count":0}],"isBlockCoverage":false},{"functionName":"StaticClosure","ranges":[{"startOffset":84470,"endOffset":84502,"count":1}],"isBlockCoverage":true},{"functionName":"BoundClosure","ranges":[{"startOffset":84522,"endOffset":84673,"count":1}],"isBlockCoverage":true},{"functionName":"TypeErrorImplementation","ranges":[{"startOffset":84704,"endOffset":84773,"count":0}],"isBlockCoverage":false},{"functionName":"CastErrorImplementation","ranges":[{"startOffset":84804,"endOffset":84873,"count":0}],"isBlockCoverage":false},{"functionName":"RuntimeError","ranges":[{"startOffset":84893,"endOffset":84951,"count":0}],"isBlockCoverage":false},{"functionName":"TypeImpl","ranges":[{"startOffset":84967,"endOffset":85065,"count":0}],"isBlockCoverage":false},{"functionName":"JsLinkedHashMap","ranges":[{"startOffset":85088,"endOffset":85289,"count":1}],"isBlockCoverage":true},{"functionName":"JsLinkedHashMap_values_closure","ranges":[{"startOffset":85327,"endOffset":85401,"count":0}],"isBlockCoverage":false},{"functionName":"LinkedHashMapCell","ranges":[{"startOffset":85426,"endOffset":85584,"count":1}],"isBlockCoverage":true},{"functionName":"LinkedHashMapKeyIterable","ranges":[{"startOffset":85616,"endOffset":85720,"count":0}],"isBlockCoverage":false},{"functionName":"LinkedHashMapKeyIterator","ranges":[{"startOffset":85752,"endOffset":85950,"count":0}],"isBlockCoverage":false},{"functionName":"initHooks_closure","ranges":[{"startOffset":85975,"endOffset":86037,"count":1}],"isBlockCoverage":true},{"functionName":"initHooks_closure0","ranges":[{"startOffset":86063,"endOffset":86133,"count":1}],"isBlockCoverage":true},{"functionName":"initHooks_closure1","ranges":[{"startOffset":86159,"endOffset":86231,"count":1}],"isBlockCoverage":true},{"functionName":"JSSyntaxRegExp","ranges":[{"startOffset":86253,"endOffset":86424,"count":0}],"isBlockCoverage":false},{"functionName":"_MatchImplementation","ranges":[{"startOffset":86452,"endOffset":86517,"count":0}],"isBlockCoverage":false},{"functionName":"_AllMatchesIterable","ranges":[{"startOffset":86544,"endOffset":86674,"count":0}],"isBlockCoverage":false},{"functionName":"_AllMatchesIterator","ranges":[{"startOffset":86701,"endOffset":86887,"count":0}],"isBlockCoverage":false},{"functionName":"StringMatch","ranges":[{"startOffset":86906,"endOffset":86990,"count":0}],"isBlockCoverage":false},{"functionName":"_StringAllMatchesIterable","ranges":[{"startOffset":87023,"endOffset":87163,"count":0}],"isBlockCoverage":false},{"functionName":"_StringAllMatchesIterator","ranges":[{"startOffset":87196,"endOffset":87384,"count":0}],"isBlockCoverage":false},{"functionName":"_ensureNativeList","ranges":[{"startOffset":87409,"endOffset":87450,"count":0}],"isBlockCoverage":false},{"functionName":"NativeInt8List__create1","ranges":[{"startOffset":87481,"endOffset":87535,"count":0}],"isBlockCoverage":false},{"functionName":"_checkValidIndex","ranges":[{"startOffset":87559,"endOffset":87716,"count":1},{"startOffset":87653,"endOffset":87710,"count":0}],"isBlockCoverage":true},{"functionName":"_checkValidRange","ranges":[{"startOffset":87740,"endOffset":88027,"count":0}],"isBlockCoverage":false},{"functionName":"NativeByteBuffer","ranges":[{"startOffset":88051,"endOffset":88086,"count":0}],"isBlockCoverage":false},{"functionName":"NativeTypedData","ranges":[{"startOffset":88109,"endOffset":88143,"count":0}],"isBlockCoverage":false},{"functionName":"NativeTypedArray","ranges":[{"startOffset":88167,"endOffset":88202,"count":0}],"isBlockCoverage":false},{"functionName":"NativeTypedArrayOfDouble","ranges":[{"startOffset":88234,"endOffset":88277,"count":0}],"isBlockCoverage":false},{"functionName":"NativeTypedArrayOfInt","ranges":[{"startOffset":88306,"endOffset":88346,"count":0}],"isBlockCoverage":false},{"functionName":"NativeInt16List","ranges":[{"startOffset":88369,"endOffset":88403,"count":0}],"isBlockCoverage":false},{"functionName":"NativeInt32List","ranges":[{"startOffset":88426,"endOffset":88460,"count":0}],"isBlockCoverage":false},{"functionName":"NativeInt8List","ranges":[{"startOffset":88482,"endOffset":88515,"count":0}],"isBlockCoverage":false},{"functionName":"NativeUint16List","ranges":[{"startOffset":88539,"endOffset":88574,"count":0}],"isBlockCoverage":false},{"functionName":"NativeUint32List","ranges":[{"startOffset":88598,"endOffset":88633,"count":0}],"isBlockCoverage":false},{"functionName":"NativeUint8ClampedList","ranges":[{"startOffset":88663,"endOffset":88704,"count":0}],"isBlockCoverage":false},{"functionName":"NativeUint8List","ranges":[{"startOffset":88727,"endOffset":88761,"count":0}],"isBlockCoverage":false},{"functionName":"_NativeTypedArrayOfDouble_NativeTypedArray_ListMixin","ranges":[{"startOffset":88821,"endOffset":88892,"count":0}],"isBlockCoverage":false},{"functionName":"_NativeTypedArrayOfDouble_NativeTypedArray_ListMixin_FixedLengthListMixin","ranges":[{"startOffset":88973,"endOffset":89065,"count":0}],"isBlockCoverage":false},{"functionName":"_NativeTypedArrayOfInt_NativeTypedArray_ListMixin","ranges":[{"startOffset":89122,"endOffset":89190,"count":0}],"isBlockCoverage":false},{"functionName":"_NativeTypedArrayOfInt_NativeTypedArray_ListMixin_FixedLengthListMixin","ranges":[{"startOffset":89268,"endOffset":89357,"count":0}],"isBlockCoverage":false},{"functionName":"extractKeys","ranges":[{"startOffset":89376,"endOffset":89483,"count":0}],"isBlockCoverage":false},{"functionName":"printString","ranges":[{"startOffset":89502,"endOffset":89949,"count":0}],"isBlockCoverage":false},{"functionName":"makeDispatchRecord","ranges":[{"startOffset":89987,"endOffset":90120,"count":1}],"isBlockCoverage":true},{"functionName":"getNativeInterceptor","ranges":[{"startOffset":90148,"endOffset":91834,"count":1},{"startOffset":90602,"endOffset":90616,"count":0},{"startOffset":90731,"endOffset":90881,"count":0},{"startOffset":90889,"endOffset":90978,"count":0},{"startOffset":90979,"endOffset":91030,"count":0},{"startOffset":91071,"endOffset":91833,"count":0}],"isBlockCoverage":true},{"functionName":"JSArray_JSArray$fixed","ranges":[{"startOffset":91863,"endOffset":92096,"count":0}],"isBlockCoverage":false},{"functionName":"JSArray_JSArray$markFixed","ranges":[{"startOffset":92129,"endOffset":92239,"count":0}],"isBlockCoverage":false},{"functionName":"JSArray_markFixedList","ranges":[{"startOffset":92268,"endOffset":92371,"count":1}],"isBlockCoverage":true},{"functionName":"JSArray_markUnmodifiableList","ranges":[{"startOffset":92407,"endOffset":92516,"count":0}],"isBlockCoverage":false},{"functionName":"JSString__isWhitespace","ranges":[{"startOffset":92546,"endOffset":93301,"count":0}],"isBlockCoverage":false},{"functionName":"JSString__skipLeadingWhitespace","ranges":[{"startOffset":93340,"endOffset":93658,"count":0}],"isBlockCoverage":false},{"functionName":"JSString__skipTrailingWhitespace","ranges":[{"startOffset":93698,"endOffset":94027,"count":0}],"isBlockCoverage":false},{"functionName":"getInterceptor$","ranges":[{"startOffset":94050,"endOffset":94813,"count":1},{"startOffset":94193,"endOffset":94238,"count":0},{"startOffset":94426,"endOffset":94452,"count":0},{"startOffset":94569,"endOffset":94695,"count":0}],"isBlockCoverage":true},{"functionName":"getInterceptor$ansx","ranges":[{"startOffset":94840,"endOffset":95426,"count":0}],"isBlockCoverage":false},{"functionName":"getInterceptor$asx","ranges":[{"startOffset":95452,"endOffset":95962,"count":1},{"startOffset":95520,"endOffset":95548,"count":0},{"startOffset":95585,"endOffset":95601,"count":0},{"startOffset":95718,"endOffset":95844,"count":0},{"startOffset":95909,"endOffset":95961,"count":0}],"isBlockCoverage":true},{"functionName":"getInterceptor$ax","ranges":[{"startOffset":95987,"endOffset":96421,"count":1},{"startOffset":96044,"endOffset":96060,"count":0},{"startOffset":96177,"endOffset":96303,"count":0},{"startOffset":96368,"endOffset":96420,"count":0}],"isBlockCoverage":true},{"functionName":"getInterceptor$n","ranges":[{"startOffset":96445,"endOffset":96718,"count":0}],"isBlockCoverage":false},{"functionName":"getInterceptor$s","ranges":[{"startOffset":96742,"endOffset":97015,"count":1},{"startOffset":96838,"endOffset":97014,"count":0}],"isBlockCoverage":true},{"functionName":"getInterceptor$x","ranges":[{"startOffset":97039,"endOffset":97396,"count":1},{"startOffset":97096,"endOffset":97112,"count":0},{"startOffset":97152,"endOffset":97278,"count":0}],"isBlockCoverage":true},{"functionName":"get$hashCode$","ranges":[{"startOffset":97417,"endOffset":97508,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator$ax","ranges":[{"startOffset":97531,"endOffset":97624,"count":0}],"isBlockCoverage":false},{"functionName":"get$length$asx","ranges":[{"startOffset":97646,"endOffset":97738,"count":1}],"isBlockCoverage":true},{"functionName":"get$onClick$x","ranges":[{"startOffset":97759,"endOffset":97850,"count":1}],"isBlockCoverage":true},{"functionName":"$add$ansx","ranges":[{"startOffset":97867,"endOffset":98056,"count":0}],"isBlockCoverage":false},{"functionName":"$eq$","ranges":[{"startOffset":98068,"endOffset":98298,"count":1},{"startOffset":98129,"endOffset":98147,"count":0},{"startOffset":98232,"endOffset":98297,"count":0}],"isBlockCoverage":true},{"functionName":"$gt$n","ranges":[{"startOffset":98311,"endOffset":98496,"count":1},{"startOffset":98429,"endOffset":98495,"count":0}],"isBlockCoverage":true},{"functionName":"$index$asx","ranges":[{"startOffset":98514,"endOffset":98872,"count":1},{"startOffset":98581,"endOffset":98800,"count":0}],"isBlockCoverage":true},{"functionName":"$indexSet$ax","ranges":[{"startOffset":98892,"endOffset":98998,"count":1}],"isBlockCoverage":true},{"functionName":"_codeUnitAt$1$s","ranges":[{"startOffset":99021,"endOffset":99122,"count":1}],"isBlockCoverage":true},{"functionName":"_removeChild$1$x","ranges":[{"startOffset":99146,"endOffset":99248,"count":0}],"isBlockCoverage":false},{"functionName":"_removeEventListener$3$x","ranges":[{"startOffset":99280,"endOffset":99406,"count":0}],"isBlockCoverage":false},{"functionName":"addEventListener$3$x","ranges":[{"startOffset":99434,"endOffset":99556,"count":1}],"isBlockCoverage":true},{"functionName":"codeUnitAt$1$s","ranges":[{"startOffset":99578,"endOffset":99678,"count":0}],"isBlockCoverage":false},{"functionName":"contains$1$asx","ranges":[{"startOffset":99700,"endOffset":99800,"count":0}],"isBlockCoverage":false},{"functionName":"elementAt$1$ax","ranges":[{"startOffset":99822,"endOffset":99922,"count":0}],"isBlockCoverage":false},{"functionName":"endsWith$1$s","ranges":[{"startOffset":99942,"endOffset":100040,"count":0}],"isBlockCoverage":false},{"functionName":"fillRange$3$x","ranges":[{"startOffset":100061,"endOffset":100176,"count":1}],"isBlockCoverage":true},{"functionName":"indexOf$2$s","ranges":[{"startOffset":100195,"endOffset":100300,"count":0}],"isBlockCoverage":false},{"functionName":"matchAsPrefix$2$s","ranges":[{"startOffset":100325,"endOffset":100436,"count":0}],"isBlockCoverage":false},{"functionName":"noSuchMethod$1$","ranges":[{"startOffset":100459,"endOffset":100560,"count":0}],"isBlockCoverage":false},{"functionName":"padRight$1$s","ranges":[{"startOffset":100580,"endOffset":100678,"count":0}],"isBlockCoverage":false},{"functionName":"postMessage$3$x","ranges":[{"startOffset":100701,"endOffset":100818,"count":1}],"isBlockCoverage":true},{"functionName":"replaceFirst$2$s","ranges":[{"startOffset":100842,"endOffset":100952,"count":0}],"isBlockCoverage":false},{"functionName":"replaceRange$3$asx","ranges":[{"startOffset":100978,"endOffset":101098,"count":0}],"isBlockCoverage":false},{"functionName":"startsWith$1$s","ranges":[{"startOffset":101120,"endOffset":101220,"count":0}],"isBlockCoverage":false},{"functionName":"startsWith$2$s","ranges":[{"startOffset":101242,"endOffset":101350,"count":0}],"isBlockCoverage":false},{"functionName":"substring$1$s","ranges":[{"startOffset":101371,"endOffset":101470,"count":0}],"isBlockCoverage":false},{"functionName":"substring$2$s","ranges":[{"startOffset":101491,"endOffset":101598,"count":1}],"isBlockCoverage":true},{"functionName":"toString$0$","ranges":[{"startOffset":101617,"endOffset":101706,"count":0}],"isBlockCoverage":false},{"functionName":"trim$0$s","ranges":[{"startOffset":101722,"endOffset":101808,"count":0}],"isBlockCoverage":false},{"functionName":"waitUntilDone$0$x","ranges":[{"startOffset":101833,"endOffset":101928,"count":0}],"isBlockCoverage":false},{"functionName":"Interceptor","ranges":[{"startOffset":101947,"endOffset":101977,"count":0}],"isBlockCoverage":false},{"functionName":"JSBool","ranges":[{"startOffset":101991,"endOffset":102016,"count":0}],"isBlockCoverage":false},{"functionName":"JSNull","ranges":[{"startOffset":102030,"endOffset":102055,"count":0}],"isBlockCoverage":false},{"functionName":"JavaScriptObject","ranges":[{"startOffset":102079,"endOffset":102114,"count":0}],"isBlockCoverage":false},{"functionName":"PlainJavaScriptObject","ranges":[{"startOffset":102143,"endOffset":102183,"count":0}],"isBlockCoverage":false},{"functionName":"UnknownJavaScriptObject","ranges":[{"startOffset":102214,"endOffset":102256,"count":0}],"isBlockCoverage":false},{"functionName":"JavaScriptFunction","ranges":[{"startOffset":102282,"endOffset":102319,"count":0}],"isBlockCoverage":false},{"functionName":"JSArray","ranges":[{"startOffset":102334,"endOffset":102383,"count":0}],"isBlockCoverage":true},{"functionName":"JSUnmodifiableArray","ranges":[{"startOffset":102410,"endOffset":102471,"count":0}],"isBlockCoverage":false},{"functionName":"ArrayIterator","ranges":[{"startOffset":102492,"endOffset":102698,"count":0}],"isBlockCoverage":false},{"functionName":"JSNumber","ranges":[{"startOffset":102714,"endOffset":102741,"count":0}],"isBlockCoverage":false},{"functionName":"JSInt","ranges":[{"startOffset":102754,"endOffset":102778,"count":0}],"isBlockCoverage":true},{"functionName":"JSDouble","ranges":[{"startOffset":102794,"endOffset":102821,"count":0}],"isBlockCoverage":false},{"functionName":"JSString","ranges":[{"startOffset":102837,"endOffset":102864,"count":0}],"isBlockCoverage":true},{"functionName":"_AsyncRun__initializeScheduleImmediate","ranges":[{"startOffset":102922,"endOffset":103739,"count":1},{"startOffset":103025,"endOffset":103089,"count":0},{"startOffset":103548,"endOffset":103738,"count":0}],"isBlockCoverage":true},{"functionName":"_AsyncRun__scheduleImmediateJsOverride","ranges":[{"startOffset":103785,"endOffset":103984,"count":0}],"isBlockCoverage":false},{"functionName":"_AsyncRun__scheduleImmediateWithSetImmediate","ranges":[{"startOffset":104036,"endOffset":104236,"count":0}],"isBlockCoverage":false},{"functionName":"_AsyncRun__scheduleImmediateWithTimer","ranges":[{"startOffset":104281,"endOffset":104400,"count":0}],"isBlockCoverage":false},{"functionName":"Timer__createTimer","ranges":[{"startOffset":104426,"endOffset":104694,"count":0}],"isBlockCoverage":false},{"functionName":"Timer__createPeriodicTimer","ranges":[{"startOffset":104728,"endOffset":105021,"count":1},{"startOffset":104985,"endOffset":104988,"count":0}],"isBlockCoverage":true},{"functionName":"_TimerImpl$","ranges":[{"startOffset":105040,"endOffset":105179,"count":0}],"isBlockCoverage":false},{"functionName":"_TimerImpl$periodic","ranges":[{"startOffset":105206,"endOffset":105354,"count":1}],"isBlockCoverage":true},{"functionName":"_makeAsyncAwaitCompleter","ranges":[{"startOffset":105386,"endOffset":105529,"count":1}],"isBlockCoverage":true},{"functionName":"_asyncStartSync","ranges":[{"startOffset":105552,"endOffset":105848,"count":1}],"isBlockCoverage":true},{"functionName":"_asyncAwait","ranges":[{"startOffset":105867,"endOffset":106009,"count":1}],"isBlockCoverage":true},{"functionName":"_asyncReturn","ranges":[{"startOffset":106029,"endOffset":106143,"count":1}],"isBlockCoverage":true},{"functionName":"_asyncRethrow","ranges":[{"startOffset":106164,"endOffset":106332,"count":0}],"isBlockCoverage":false},{"functionName":"_awaitOnObject","ranges":[{"startOffset":106354,"endOffset":107170,"count":1},{"startOffset":106791,"endOffset":107164,"count":0}],"isBlockCoverage":true},{"functionName":"_wrapJsFunctionForAsync","ranges":[{"startOffset":107201,"endOffset":107687,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":107246,"endOffset":107537,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":107283,"endOffset":107528,"count":1},{"startOffset":107425,"endOffset":107518,"count":0}],"isBlockCoverage":true},{"functionName":"_Future$zoneValue","ranges":[{"startOffset":107712,"endOffset":107914,"count":0}],"isBlockCoverage":false},{"functionName":"_Future__chainForeignFuture","ranges":[{"startOffset":107949,"endOffset":108400,"count":0}],"isBlockCoverage":false},{"functionName":"_Future__chainCoreFuture","ranges":[{"startOffset":108432,"endOffset":109081,"count":0}],"isBlockCoverage":false},{"functionName":"_Future__propagateToListeners","ranges":[{"startOffset":109118,"endOffset":112741,"count":1},{"startOffset":109462,"endOffset":109649,"count":0},{"startOffset":110172,"endOffset":110183,"count":0},{"startOffset":110194,"endOffset":110220,"count":0},{"startOffset":110323,"endOffset":110467,"count":0},{"startOffset":110515,"endOffset":110754,"count":0},{"startOffset":110835,"endOffset":110858,"count":0},{"startOffset":110970,"endOffset":111079,"count":0},{"startOffset":111261,"endOffset":111383,"count":0},{"startOffset":111427,"endOffset":111453,"count":0},{"startOffset":111547,"endOffset":112035,"count":0},{"startOffset":112531,"endOffset":112674,"count":0}],"isBlockCoverage":true},{"functionName":"_registerErrorHandler","ranges":[{"startOffset":112770,"endOffset":113325,"count":0}],"isBlockCoverage":false},{"functionName":"_microtaskLoop","ranges":[{"startOffset":113347,"endOffset":113621,"count":1}],"isBlockCoverage":true},{"functionName":"_startMicrotaskLoop","ranges":[{"startOffset":113648,"endOffset":113983,"count":1},{"startOffset":113877,"endOffset":113969,"count":0}],"isBlockCoverage":true},{"functionName":"_scheduleAsyncCallback","ranges":[{"startOffset":114013,"endOffset":114484,"count":1},{"startOffset":114386,"endOffset":114478,"count":0}],"isBlockCoverage":true},{"functionName":"_schedulePriorityAsyncCallback","ranges":[{"startOffset":114522,"endOffset":115197,"count":0}],"isBlockCoverage":false},{"functionName":"scheduleMicrotask","ranges":[{"startOffset":115222,"endOffset":115926,"count":0}],"isBlockCoverage":false},{"functionName":"StreamIterator_StreamIterator","ranges":[{"startOffset":115963,"endOffset":116090,"count":0}],"isBlockCoverage":false},{"functionName":"StreamController_StreamController","ranges":[{"startOffset":116131,"endOffset":116365,"count":1}],"isBlockCoverage":true},{"functionName":"_runGuarded","ranges":[{"startOffset":116384,"endOffset":116791,"count":1},{"startOffset":116615,"endOffset":116785,"count":0}],"isBlockCoverage":true},{"functionName":"_nullDataHandler","ranges":[{"startOffset":116815,"endOffset":116838,"count":0}],"isBlockCoverage":false},{"functionName":"_nullErrorHandler","ranges":[{"startOffset":116863,"endOffset":117021,"count":0}],"isBlockCoverage":false},{"functionName":"_nullDoneHandler","ranges":[{"startOffset":117045,"endOffset":117063,"count":0}],"isBlockCoverage":false},{"functionName":"Timer_Timer$periodic","ranges":[{"startOffset":117091,"endOffset":117502,"count":1},{"startOffset":117293,"endOffset":117345,"count":0}],"isBlockCoverage":true},{"functionName":"_ZoneSpecification$","ranges":[{"startOffset":117529,"endOffset":117972,"count":1}],"isBlockCoverage":true},{"functionName":"_parentDelegate","ranges":[{"startOffset":117995,"endOffset":118126,"count":1},{"startOffset":118068,"endOffset":118125,"count":0}],"isBlockCoverage":true},{"functionName":"_rootHandleUncaughtError","ranges":[{"startOffset":118158,"endOffset":118395,"count":0}],"isBlockCoverage":false},{"functionName":"_rootRun","ranges":[{"startOffset":118411,"endOffset":118914,"count":1},{"startOffset":118731,"endOffset":118749,"count":0},{"startOffset":118859,"endOffset":118860,"count":0}],"isBlockCoverage":true},{"functionName":"_rootRunUnary","ranges":[{"startOffset":118935,"endOffset":119510,"count":1},{"startOffset":119455,"endOffset":119456,"count":0}],"isBlockCoverage":true},{"functionName":"_rootRunBinary","ranges":[{"startOffset":119532,"endOffset":120183,"count":0}],"isBlockCoverage":false},{"functionName":"_rootRegisterCallback","ranges":[{"startOffset":120212,"endOffset":120314,"count":1}],"isBlockCoverage":true},{"functionName":"_rootRegisterUnaryCallback","ranges":[{"startOffset":120348,"endOffset":120466,"count":1}],"isBlockCoverage":true},{"functionName":"_rootRegisterBinaryCallback","ranges":[{"startOffset":120501,"endOffset":120627,"count":1}],"isBlockCoverage":true},{"functionName":"_rootErrorCallback","ranges":[{"startOffset":120653,"endOffset":120783,"count":0}],"isBlockCoverage":false},{"functionName":"_rootScheduleMicrotask","ranges":[{"startOffset":120813,"endOffset":121143,"count":1},{"startOffset":121071,"endOffset":121101,"count":0}],"isBlockCoverage":true},{"functionName":"_rootCreateTimer","ranges":[{"startOffset":121167,"endOffset":121430,"count":0}],"isBlockCoverage":false},{"functionName":"_rootCreatePeriodicTimer","ranges":[{"startOffset":121462,"endOffset":121766,"count":1}],"isBlockCoverage":true},{"functionName":"_rootPrint","ranges":[{"startOffset":121784,"endOffset":121874,"count":0}],"isBlockCoverage":false},{"functionName":"_printToZone","ranges":[{"startOffset":121894,"endOffset":121956,"count":0}],"isBlockCoverage":false},{"functionName":"_rootFork","ranges":[{"startOffset":121973,"endOffset":123508,"count":1},{"startOffset":122278,"endOffset":122319,"count":0},{"startOffset":123450,"endOffset":123483,"count":0}],"isBlockCoverage":true},{"functionName":"runZoned","ranges":[{"startOffset":123524,"endOffset":125443,"count":1},{"startOffset":124003,"endOffset":124288,"count":0},{"startOffset":124511,"endOffset":125049,"count":0},{"startOffset":125155,"endOffset":125442,"count":0}],"isBlockCoverage":true},{"functionName":"_runZoned","ranges":[{"startOffset":125460,"endOffset":125673,"count":1}],"isBlockCoverage":true},{"functionName":"_AsyncRun__initializeScheduleImmediate_internalCallback","ranges":[{"startOffset":125736,"endOffset":125836,"count":1}],"isBlockCoverage":true},{"functionName":"_AsyncRun__initializeScheduleImmediate_closure","ranges":[{"startOffset":125890,"endOffset":126032,"count":1}],"isBlockCoverage":true},{"functionName":"_AsyncRun__scheduleImmediateJsOverride_internalCallback","ranges":[{"startOffset":126095,"endOffset":126197,"count":0}],"isBlockCoverage":false},{"functionName":"_AsyncRun__scheduleImmediateWithSetImmediate_internalCallback","ranges":[{"startOffset":126266,"endOffset":126374,"count":0}],"isBlockCoverage":false},{"functionName":"_TimerImpl","ranges":[{"startOffset":126392,"endOffset":126443,"count":1}],"isBlockCoverage":true},{"functionName":"_TimerImpl_internalCallback","ranges":[{"startOffset":126478,"endOffset":126579,"count":0}],"isBlockCoverage":false},{"functionName":"_TimerImpl$periodic_closure","ranges":[{"startOffset":126614,"endOffset":126784,"count":1}],"isBlockCoverage":true},{"functionName":"_AsyncAwaitCompleter","ranges":[{"startOffset":126812,"endOffset":126934,"count":1}],"isBlockCoverage":true},{"functionName":"_AsyncAwaitCompleter_complete_closure","ranges":[{"startOffset":126979,"endOffset":127087,"count":0}],"isBlockCoverage":false},{"functionName":"_AsyncAwaitCompleter_completeError_closure","ranges":[{"startOffset":127137,"endOffset":127270,"count":0}],"isBlockCoverage":false},{"functionName":"_awaitOnObject_closure","ranges":[{"startOffset":127300,"endOffset":127373,"count":1}],"isBlockCoverage":true},{"functionName":"_awaitOnObject_closure0","ranges":[{"startOffset":127404,"endOffset":127478,"count":1}],"isBlockCoverage":true},{"functionName":"_wrapJsFunctionForAsync_closure","ranges":[{"startOffset":127517,"endOffset":127597,"count":1}],"isBlockCoverage":true},{"functionName":"Future","ranges":[{"startOffset":127611,"endOffset":127636,"count":0}],"isBlockCoverage":false},{"functionName":"_Completer","ranges":[{"startOffset":127654,"endOffset":127683,"count":0}],"isBlockCoverage":false},{"functionName":"_AsyncCompleter","ranges":[{"startOffset":127706,"endOffset":127791,"count":1}],"isBlockCoverage":true},{"functionName":"_SyncCompleter","ranges":[{"startOffset":127813,"endOffset":127897,"count":1}],"isBlockCoverage":true},{"functionName":"_FutureListener","ranges":[{"startOffset":127920,"endOffset":128132,"count":1}],"isBlockCoverage":true},{"functionName":"_Future","ranges":[{"startOffset":128147,"endOffset":128297,"count":1}],"isBlockCoverage":true},{"functionName":"_Future__addListener_closure","ranges":[{"startOffset":128333,"endOffset":128435,"count":1}],"isBlockCoverage":true},{"functionName":"_Future__prependListeners_closure","ranges":[{"startOffset":128476,"endOffset":128581,"count":0}],"isBlockCoverage":false},{"functionName":"_Future__chainForeignFuture_closure","ranges":[{"startOffset":128624,"endOffset":128704,"count":0}],"isBlockCoverage":false},{"functionName":"_Future__chainForeignFuture_closure0","ranges":[{"startOffset":128748,"endOffset":128829,"count":0}],"isBlockCoverage":false},{"functionName":"_Future__chainForeignFuture_closure1","ranges":[{"startOffset":128873,"endOffset":129000,"count":0}],"isBlockCoverage":false},{"functionName":"_Future__asyncComplete_closure","ranges":[{"startOffset":129038,"endOffset":129139,"count":1}],"isBlockCoverage":true},{"functionName":"_Future__chainFuture_closure","ranges":[{"startOffset":129175,"endOffset":129274,"count":0}],"isBlockCoverage":false},{"functionName":"_Future__asyncCompleteError_closure","ranges":[{"startOffset":129317,"endOffset":129455,"count":0}],"isBlockCoverage":false},{"functionName":"_Future__propagateToListeners_handleWhenCompleteCallback","ranges":[{"startOffset":129519,"endOffset":129716,"count":0}],"isBlockCoverage":false},{"functionName":"_Future__propagateToListeners_handleWhenCompleteCallback_closure","ranges":[{"startOffset":129788,"endOffset":129905,"count":0}],"isBlockCoverage":false},{"functionName":"_Future__propagateToListeners_handleValueCallback","ranges":[{"startOffset":129962,"endOffset":130120,"count":1}],"isBlockCoverage":true},{"functionName":"_Future__propagateToListeners_handleError","ranges":[{"startOffset":130169,"endOffset":130313,"count":0}],"isBlockCoverage":false},{"functionName":"_AsyncCallbackEntry","ranges":[{"startOffset":130340,"endOffset":130430,"count":1}],"isBlockCoverage":true},{"functionName":"Stream","ranges":[{"startOffset":130444,"endOffset":130469,"count":0}],"isBlockCoverage":false},{"functionName":"Stream_pipe_closure","ranges":[{"startOffset":130496,"endOffset":130568,"count":1}],"isBlockCoverage":true},{"functionName":"Stream_length_closure","ranges":[{"startOffset":130597,"endOffset":130690,"count":0}],"isBlockCoverage":false},{"functionName":"Stream_length_closure0","ranges":[{"startOffset":130720,"endOffset":130815,"count":0}],"isBlockCoverage":false},{"functionName":"StreamSubscription","ranges":[{"startOffset":130841,"endOffset":130878,"count":0}],"isBlockCoverage":false},{"functionName":"StreamTransformerBase","ranges":[{"startOffset":130907,"endOffset":130947,"count":0}],"isBlockCoverage":false},{"functionName":"_StreamController","ranges":[{"startOffset":130972,"endOffset":131008,"count":0}],"isBlockCoverage":false},{"functionName":"_StreamController__subscribe_closure","ranges":[{"startOffset":131052,"endOffset":131132,"count":1}],"isBlockCoverage":true},{"functionName":"_StreamController__recordCancel_complete","ranges":[{"startOffset":131180,"endOffset":131264,"count":0}],"isBlockCoverage":false},{"functionName":"_SyncStreamControllerDispatch","ranges":[{"startOffset":131301,"endOffset":131349,"count":0}],"isBlockCoverage":false},{"functionName":"_SyncStreamController","ranges":[{"startOffset":131378,"endOffset":131643,"count":1}],"isBlockCoverage":true},{"functionName":"_ControllerStream","ranges":[{"startOffset":131668,"endOffset":131760,"count":1}],"isBlockCoverage":true},{"functionName":"_ControllerSubscription","ranges":[{"startOffset":131791,"endOffset":132051,"count":1}],"isBlockCoverage":true},{"functionName":"_StreamSinkWrapper","ranges":[{"startOffset":132077,"endOffset":132173,"count":1}],"isBlockCoverage":true},{"functionName":"_AddStreamState_cancel_closure","ranges":[{"startOffset":132211,"endOffset":132285,"count":0}],"isBlockCoverage":false},{"functionName":"_BufferingStreamSubscription","ranges":[{"startOffset":132321,"endOffset":132368,"count":0}],"isBlockCoverage":false},{"functionName":"_BufferingStreamSubscription__sendError_sendError","ranges":[{"startOffset":132425,"endOffset":132577,"count":0}],"isBlockCoverage":false},{"functionName":"_BufferingStreamSubscription__sendDone_sendDone","ranges":[{"startOffset":132632,"endOffset":132723,"count":0}],"isBlockCoverage":false},{"functionName":"_StreamImpl","ranges":[{"startOffset":132742,"endOffset":132772,"count":0}],"isBlockCoverage":false},{"functionName":"_DelayedEvent","ranges":[{"startOffset":132793,"endOffset":132825,"count":0}],"isBlockCoverage":false},{"functionName":"_DelayedData","ranges":[{"startOffset":132845,"endOffset":132950,"count":0}],"isBlockCoverage":false},{"functionName":"_DelayedError","ranges":[{"startOffset":132971,"endOffset":133084,"count":0}],"isBlockCoverage":false},{"functionName":"_DelayedDone","ranges":[{"startOffset":133104,"endOffset":133135,"count":1}],"isBlockCoverage":true},{"functionName":"_PendingEvents","ranges":[{"startOffset":133157,"endOffset":133190,"count":0}],"isBlockCoverage":false},{"functionName":"_PendingEvents_schedule_closure","ranges":[{"startOffset":133229,"endOffset":133334,"count":0}],"isBlockCoverage":false},{"functionName":"_StreamImplEvents","ranges":[{"startOffset":133359,"endOffset":133515,"count":0}],"isBlockCoverage":false},{"functionName":"_DoneStreamSubscription","ranges":[{"startOffset":133546,"endOffset":133698,"count":0}],"isBlockCoverage":false},{"functionName":"_StreamIterator","ranges":[{"startOffset":133721,"endOffset":133881,"count":0}],"isBlockCoverage":false},{"functionName":"_EmptyStream","ranges":[{"startOffset":133901,"endOffset":133955,"count":0}],"isBlockCoverage":false},{"functionName":"Timer","ranges":[{"startOffset":133968,"endOffset":133992,"count":0}],"isBlockCoverage":false},{"functionName":"AsyncError","ranges":[{"startOffset":134010,"endOffset":134096,"count":0}],"isBlockCoverage":false},{"functionName":"_ZoneFunction","ranges":[{"startOffset":134117,"endOffset":134229,"count":1}],"isBlockCoverage":true},{"functionName":"ZoneSpecification","ranges":[{"startOffset":134254,"endOffset":134290,"count":0}],"isBlockCoverage":false},{"functionName":"_ZoneSpecification","ranges":[{"startOffset":134316,"endOffset":134791,"count":1}],"isBlockCoverage":true},{"functionName":"ZoneDelegate","ranges":[{"startOffset":134811,"endOffset":134842,"count":0}],"isBlockCoverage":false},{"functionName":"Zone","ranges":[{"startOffset":134854,"endOffset":134877,"count":0}],"isBlockCoverage":false},{"functionName":"_ZoneDelegate","ranges":[{"startOffset":134898,"endOffset":134967,"count":0}],"isBlockCoverage":false},{"functionName":"_Zone","ranges":[{"startOffset":134980,"endOffset":135004,"count":0}],"isBlockCoverage":false},{"functionName":"_CustomZone","ranges":[{"startOffset":135023,"endOffset":135402,"count":1}],"isBlockCoverage":true},{"functionName":"_CustomZone_bindCallback_closure","ranges":[{"startOffset":135442,"endOffset":135573,"count":0}],"isBlockCoverage":false},{"functionName":"_CustomZone_bindUnaryCallback_closure","ranges":[{"startOffset":135618,"endOffset":135785,"count":1}],"isBlockCoverage":true},{"functionName":"_CustomZone_bindCallbackGuarded_closure","ranges":[{"startOffset":135832,"endOffset":135947,"count":1}],"isBlockCoverage":true},{"functionName":"_CustomZone_bindUnaryCallbackGuarded_closure","ranges":[{"startOffset":135999,"endOffset":136142,"count":1}],"isBlockCoverage":true},{"functionName":"_rootHandleUncaughtError_closure","ranges":[{"startOffset":136182,"endOffset":136291,"count":0}],"isBlockCoverage":false},{"functionName":"_RootZone","ranges":[{"startOffset":136308,"endOffset":136336,"count":1}],"isBlockCoverage":true},{"functionName":"_RootZone_bindCallback_closure","ranges":[{"startOffset":136374,"endOffset":136494,"count":0}],"isBlockCoverage":false},{"functionName":"_RootZone_bindCallbackGuarded_closure","ranges":[{"startOffset":136539,"endOffset":136643,"count":0}],"isBlockCoverage":false},{"functionName":"_RootZone_bindUnaryCallbackGuarded_closure","ranges":[{"startOffset":136693,"endOffset":136825,"count":0}],"isBlockCoverage":false},{"functionName":"runZoned_closure","ranges":[{"startOffset":136849,"endOffset":136910,"count":1}],"isBlockCoverage":true},{"functionName":"HashMap_HashMap","ranges":[{"startOffset":136933,"endOffset":136996,"count":1}],"isBlockCoverage":true},{"functionName":"_HashMap__getTableEntry","ranges":[{"startOffset":137027,"endOffset":137130,"count":0}],"isBlockCoverage":false},{"functionName":"_HashMap__setTableEntry","ranges":[{"startOffset":137161,"endOffset":137288,"count":0}],"isBlockCoverage":false},{"functionName":"_HashMap__newHashTable","ranges":[{"startOffset":137318,"endOffset":137510,"count":0}],"isBlockCoverage":false},{"functionName":"LinkedHashMap_LinkedHashMap$_literal","ranges":[{"startOffset":137554,"endOffset":137777,"count":0}],"isBlockCoverage":false},{"functionName":"LinkedHashMap_LinkedHashMap$_empty","ranges":[{"startOffset":137819,"endOffset":137889,"count":1}],"isBlockCoverage":true},{"functionName":"LinkedHashMap__makeEmpty","ranges":[{"startOffset":137921,"endOffset":137989,"count":1}],"isBlockCoverage":true},{"functionName":"LinkedHashSet_LinkedHashSet","ranges":[{"startOffset":138024,"endOffset":138085,"count":1}],"isBlockCoverage":true},{"functionName":"_LinkedHashSet__newHashTable","ranges":[{"startOffset":138121,"endOffset":138287,"count":0}],"isBlockCoverage":false},{"functionName":"IterableBase_iterableToShortString","ranges":[{"startOffset":138329,"endOffset":139079,"count":0}],"isBlockCoverage":false},{"functionName":"IterableBase_iterableToFullString","ranges":[{"startOffset":139120,"endOffset":139770,"count":0}],"isBlockCoverage":false},{"functionName":"_isToStringVisiting","ranges":[{"startOffset":139797,"endOffset":139972,"count":0}],"isBlockCoverage":false},{"functionName":"_iterablePartsToStrings","ranges":[{"startOffset":140003,"endOffset":142710,"count":0}],"isBlockCoverage":false},{"functionName":"MapBase_mapToString","ranges":[{"startOffset":142737,"endOffset":143352,"count":0}],"isBlockCoverage":false},{"functionName":"_HashMap","ranges":[{"startOffset":143368,"endOffset":143571,"count":1}],"isBlockCoverage":true},{"functionName":"_HashMapKeyIterable","ranges":[{"startOffset":143598,"endOffset":143685,"count":0}],"isBlockCoverage":false},{"functionName":"_HashMapKeyIterator","ranges":[{"startOffset":143712,"endOffset":143907,"count":0}],"isBlockCoverage":false},{"functionName":"_LinkedHashSet","ranges":[{"startOffset":143929,"endOffset":144201,"count":1}],"isBlockCoverage":true},{"functionName":"_LinkedHashSetCell","ranges":[{"startOffset":144227,"endOffset":144358,"count":0}],"isBlockCoverage":false},{"functionName":"_LinkedHashSetIterator","ranges":[{"startOffset":144388,"endOffset":144596,"count":0}],"isBlockCoverage":false},{"functionName":"IterableBase","ranges":[{"startOffset":144616,"endOffset":144647,"count":0}],"isBlockCoverage":false},{"functionName":"ListBase","ranges":[{"startOffset":144663,"endOffset":144690,"count":0}],"isBlockCoverage":false},{"functionName":"ListMixin","ranges":[{"startOffset":144707,"endOffset":144735,"count":0}],"isBlockCoverage":false},{"functionName":"MapBase","ranges":[{"startOffset":144750,"endOffset":144776,"count":0}],"isBlockCoverage":false},{"functionName":"MapBase_mapToString_closure","ranges":[{"startOffset":144811,"endOffset":144911,"count":0}],"isBlockCoverage":false},{"functionName":"MapMixin","ranges":[{"startOffset":144927,"endOffset":144954,"count":0}],"isBlockCoverage":false},{"functionName":"_UnmodifiableMapMixin","ranges":[{"startOffset":144983,"endOffset":145023,"count":0}],"isBlockCoverage":false},{"functionName":"MapView","ranges":[{"startOffset":145038,"endOffset":145064,"count":0}],"isBlockCoverage":false},{"functionName":"UnmodifiableMapView","ranges":[{"startOffset":145091,"endOffset":145178,"count":1}],"isBlockCoverage":true},{"functionName":"_SetBase","ranges":[{"startOffset":145194,"endOffset":145221,"count":0}],"isBlockCoverage":false},{"functionName":"_ListBase_Object_ListMixin","ranges":[{"startOffset":145255,"endOffset":145300,"count":0}],"isBlockCoverage":false},{"functionName":"_UnmodifiableMapView_MapView__UnmodifiableMapMixin","ranges":[{"startOffset":145358,"endOffset":145427,"count":0}],"isBlockCoverage":false},{"functionName":"_parseJson","ranges":[{"startOffset":145445,"endOffset":145914,"count":1},{"startOffset":145555,"endOffset":145607,"count":0},{"startOffset":145686,"endOffset":145846,"count":0}],"isBlockCoverage":true},{"functionName":"_convertJsonToDartLazy","ranges":[{"startOffset":145944,"endOffset":146324,"count":1}],"isBlockCoverage":true},{"functionName":"Utf8Decoder__convertIntercepted","ranges":[{"startOffset":146363,"endOffset":146629,"count":1},{"startOffset":146529,"endOffset":146609,"count":0}],"isBlockCoverage":true},{"functionName":"Utf8Decoder__convertInterceptedUint8List","ranges":[{"startOffset":146677,"endOffset":147268,"count":0}],"isBlockCoverage":false},{"functionName":"Utf8Decoder__useTextDecoderChecked","ranges":[{"startOffset":147310,"endOffset":147479,"count":0}],"isBlockCoverage":false},{"functionName":"Utf8Decoder__useTextDecoderUnchecked","ranges":[{"startOffset":147523,"endOffset":147743,"count":0}],"isBlockCoverage":false},{"functionName":"Utf8Decoder__unsafe","ranges":[{"startOffset":147770,"endOffset":148014,"count":0}],"isBlockCoverage":false},{"functionName":"Utf8Decoder__makeDecoder","ranges":[{"startOffset":148046,"endOffset":148262,"count":0}],"isBlockCoverage":false},{"functionName":"_scanOneByteCharacters","ranges":[{"startOffset":148292,"endOffset":148695,"count":1},{"startOffset":148570,"endOffset":148589,"count":0},{"startOffset":148635,"endOffset":148651,"count":0}],"isBlockCoverage":true},{"functionName":"Base64Codec__checkPadding","ranges":[{"startOffset":148728,"endOffset":149339,"count":0}],"isBlockCoverage":false},{"functionName":"JsonUnsupportedObjectError$","ranges":[{"startOffset":149374,"endOffset":149504,"count":0}],"isBlockCoverage":false},{"functionName":"_defaultToEncodable","ranges":[{"startOffset":149531,"endOffset":149587,"count":0}],"isBlockCoverage":false},{"functionName":"_JsonStringStringifier_stringify","ranges":[{"startOffset":149627,"endOffset":149885,"count":1},{"startOffset":149869,"endOffset":149873,"count":0}],"isBlockCoverage":true},{"functionName":"_JsonStringStringifier_printOn","ranges":[{"startOffset":149923,"endOffset":150125,"count":1}],"isBlockCoverage":true},{"functionName":"_JsonMap","ranges":[{"startOffset":150141,"endOffset":150254,"count":1}],"isBlockCoverage":true},{"functionName":"_JsonMapKeyIterable","ranges":[{"startOffset":150281,"endOffset":150355,"count":0}],"isBlockCoverage":false},{"functionName":"AsciiCodec","ranges":[{"startOffset":150373,"endOffset":150435,"count":1}],"isBlockCoverage":true},{"functionName":"_UnicodeSubsetEncoder","ranges":[{"startOffset":150464,"endOffset":150504,"count":0}],"isBlockCoverage":false},{"functionName":"AsciiEncoder","ranges":[{"startOffset":150524,"endOffset":150586,"count":1}],"isBlockCoverage":true},{"functionName":"Base64Codec","ranges":[{"startOffset":150605,"endOffset":150663,"count":1}],"isBlockCoverage":true},{"functionName":"Base64Encoder","ranges":[{"startOffset":150684,"endOffset":150744,"count":1}],"isBlockCoverage":true},{"functionName":"Codec","ranges":[{"startOffset":150757,"endOffset":150781,"count":0}],"isBlockCoverage":false},{"functionName":"_FusedCodec","ranges":[{"startOffset":150800,"endOffset":150919,"count":0}],"isBlockCoverage":false},{"functionName":"Converter","ranges":[{"startOffset":150936,"endOffset":150964,"count":0}],"isBlockCoverage":false},{"functionName":"Encoding","ranges":[{"startOffset":150980,"endOffset":151007,"count":0}],"isBlockCoverage":false},{"functionName":"JsonUnsupportedObjectError","ranges":[{"startOffset":151041,"endOffset":151150,"count":0}],"isBlockCoverage":false},{"functionName":"JsonCyclicError","ranges":[{"startOffset":151173,"endOffset":151271,"count":0}],"isBlockCoverage":false},{"functionName":"JsonCodec","ranges":[{"startOffset":151288,"endOffset":151378,"count":1}],"isBlockCoverage":true},{"functionName":"JsonEncoder","ranges":[{"startOffset":151397,"endOffset":151487,"count":1}],"isBlockCoverage":true},{"functionName":"JsonDecoder","ranges":[{"startOffset":151506,"endOffset":151564,"count":1}],"isBlockCoverage":true},{"functionName":"_JsonStringifier","ranges":[{"startOffset":151588,"endOffset":151623,"count":0}],"isBlockCoverage":false},{"functionName":"_JsonStringifier_writeMap_closure","ranges":[{"startOffset":151664,"endOffset":151776,"count":1}],"isBlockCoverage":true},{"functionName":"_JsonStringStringifier","ranges":[{"startOffset":151806,"endOffset":151942,"count":1}],"isBlockCoverage":true},{"functionName":"Utf8Codec","ranges":[{"startOffset":151959,"endOffset":152022,"count":1}],"isBlockCoverage":true},{"functionName":"Utf8Encoder","ranges":[{"startOffset":152041,"endOffset":152071,"count":1}],"isBlockCoverage":true},{"functionName":"_Utf8Encoder","ranges":[{"startOffset":152091,"endOffset":152192,"count":0}],"isBlockCoverage":false},{"functionName":"Utf8Decoder","ranges":[{"startOffset":152211,"endOffset":152276,"count":1}],"isBlockCoverage":true},{"functionName":"_Utf8Decoder","ranges":[{"startOffset":152296,"endOffset":152498,"count":1}],"isBlockCoverage":true},{"functionName":"_Utf8Decoder_convert_addSingleBytes","ranges":[{"startOffset":152541,"endOffset":152721,"count":1}],"isBlockCoverage":true},{"functionName":"int_parse","ranges":[{"startOffset":152738,"endOffset":153106,"count":1},{"startOffset":152965,"endOffset":153105,"count":0}],"isBlockCoverage":true},{"functionName":"Error__objectToString","ranges":[{"startOffset":153135,"endOffset":153309,"count":0}],"isBlockCoverage":false},{"functionName":"List_List$filled","ranges":[{"startOffset":153333,"endOffset":153687,"count":0}],"isBlockCoverage":false},{"functionName":"List_List$from","ranges":[{"startOffset":153709,"endOffset":154115,"count":0}],"isBlockCoverage":false},{"functionName":"List_List$unmodifiable","ranges":[{"startOffset":154145,"endOffset":154366,"count":0}],"isBlockCoverage":false},{"functionName":"String_String$fromCharCodes","ranges":[{"startOffset":154401,"endOffset":155216,"count":1},{"startOffset":154876,"endOffset":154928,"count":0},{"startOffset":154950,"endOffset":155215,"count":0}],"isBlockCoverage":true},{"functionName":"String_String$fromCharCode","ranges":[{"startOffset":155250,"endOffset":155332,"count":0}],"isBlockCoverage":false},{"functionName":"String__stringFromIterable","ranges":[{"startOffset":155366,"endOffset":156339,"count":0}],"isBlockCoverage":false},{"functionName":"RegExp_RegExp","ranges":[{"startOffset":156360,"endOffset":156499,"count":0}],"isBlockCoverage":false},{"functionName":"StringBuffer__writeAll","ranges":[{"startOffset":156529,"endOffset":157013,"count":0}],"isBlockCoverage":false},{"functionName":"NoSuchMethodError$","ranges":[{"startOffset":157039,"endOffset":157217,"count":0}],"isBlockCoverage":false},{"functionName":"Uri_base","ranges":[{"startOffset":157233,"endOffset":157431,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__uriEncode","ranges":[{"startOffset":157454,"endOffset":158643,"count":0}],"isBlockCoverage":false},{"functionName":"DateTime__fourDigits","ranges":[{"startOffset":158671,"endOffset":158964,"count":0}],"isBlockCoverage":false},{"functionName":"DateTime__threeDigits","ranges":[{"startOffset":158993,"endOffset":159121,"count":0}],"isBlockCoverage":false},{"functionName":"DateTime__twoDigits","ranges":[{"startOffset":159148,"endOffset":159231,"count":0}],"isBlockCoverage":false},{"functionName":"Duration$","ranges":[{"startOffset":159248,"endOffset":159321,"count":1}],"isBlockCoverage":true},{"functionName":"Error_safeToString","ranges":[{"startOffset":159347,"endOffset":159619,"count":0}],"isBlockCoverage":false},{"functionName":"ArgumentError$","ranges":[{"startOffset":159641,"endOffset":159728,"count":0}],"isBlockCoverage":false},{"functionName":"ArgumentError$value","ranges":[{"startOffset":159755,"endOffset":159857,"count":0}],"isBlockCoverage":false},{"functionName":"RangeError$value","ranges":[{"startOffset":159881,"endOffset":159996,"count":0}],"isBlockCoverage":false},{"functionName":"RangeError$range","ranges":[{"startOffset":160020,"endOffset":160181,"count":0}],"isBlockCoverage":false},{"functionName":"RangeError_checkValueInInterval","ranges":[{"startOffset":160220,"endOffset":160409,"count":0}],"isBlockCoverage":false},{"functionName":"RangeError_checkValidRange","ranges":[{"startOffset":160443,"endOffset":160875,"count":1},{"startOffset":160520,"endOffset":160540,"count":0},{"startOffset":160589,"endOffset":160665,"count":0},{"startOffset":160743,"endOffset":160819,"count":0}],"isBlockCoverage":true},{"functionName":"RangeError_checkNotNegative","ranges":[{"startOffset":160910,"endOffset":161106,"count":0}],"isBlockCoverage":false},{"functionName":"IndexError$","ranges":[{"startOffset":161125,"endOffset":161363,"count":0}],"isBlockCoverage":false},{"functionName":"UnsupportedError$","ranges":[{"startOffset":161388,"endOffset":161459,"count":0}],"isBlockCoverage":false},{"functionName":"UnimplementedError$","ranges":[{"startOffset":161486,"endOffset":161559,"count":0}],"isBlockCoverage":false},{"functionName":"StateError$","ranges":[{"startOffset":161578,"endOffset":161643,"count":0}],"isBlockCoverage":false},{"functionName":"ConcurrentModificationError$","ranges":[{"startOffset":161679,"endOffset":161775,"count":0}],"isBlockCoverage":false},{"functionName":"FormatException$","ranges":[{"startOffset":161799,"endOffset":161901,"count":0}],"isBlockCoverage":false},{"functionName":"List_List$generate","ranges":[{"startOffset":161927,"endOffset":162297,"count":1}],"isBlockCoverage":true},{"functionName":"Uri_parse","ranges":[{"startOffset":162314,"endOffset":168453,"count":1},{"startOffset":162832,"endOffset":162938,"count":0},{"startOffset":162980,"endOffset":163068,"count":0},{"startOffset":163649,"endOffset":163694,"count":0},{"startOffset":163774,"endOffset":163797,"count":0},{"startOffset":163894,"endOffset":163917,"count":0},{"startOffset":163983,"endOffset":164000,"count":0},{"startOffset":164205,"endOffset":164232,"count":0},{"startOffset":164283,"endOffset":164308,"count":0},{"startOffset":164355,"endOffset":164382,"count":0},{"startOffset":164432,"endOffset":164455,"count":0},{"startOffset":164497,"endOffset":164520,"count":0},{"startOffset":164568,"endOffset":164594,"count":0},{"startOffset":164644,"endOffset":164667,"count":0},{"startOffset":164709,"endOffset":164731,"count":0},{"startOffset":164797,"endOffset":164813,"count":0},{"startOffset":164867,"endOffset":167872,"count":0},{"startOffset":167927,"endOffset":168319,"count":0}],"isBlockCoverage":true},{"functionName":"Uri_decodeComponent","ranges":[{"startOffset":168480,"endOffset":168661,"count":0}],"isBlockCoverage":false},{"functionName":"Uri_splitQueryString","ranges":[{"startOffset":168689,"endOffset":168954,"count":1}],"isBlockCoverage":true},{"functionName":"Uri__parseIPv4Address","ranges":[{"startOffset":168983,"endOffset":170538,"count":0}],"isBlockCoverage":false},{"functionName":"Uri_parseIPv6Address","ranges":[{"startOffset":170566,"endOffset":173975,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__Uri$notSimple","ranges":[{"startOffset":174002,"endOffset":175800,"count":1},{"startOffset":174254,"endOffset":174277,"count":0},{"startOffset":174370,"endOffset":174515,"count":0},{"startOffset":174608,"endOffset":174632,"count":0},{"startOffset":174717,"endOffset":174774,"count":0},{"startOffset":174901,"endOffset":174925,"count":0},{"startOffset":175007,"endOffset":175031,"count":0},{"startOffset":175196,"endOffset":175202,"count":0},{"startOffset":175211,"endOffset":175291,"count":0},{"startOffset":175429,"endOffset":175453,"count":0},{"startOffset":175507,"endOffset":175535,"count":0},{"startOffset":175639,"endOffset":175645,"count":0},{"startOffset":175734,"endOffset":175785,"count":0}],"isBlockCoverage":true},{"functionName":"_Uri__Uri","ranges":[{"startOffset":175817,"endOffset":177057,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__defaultPort","ranges":[{"startOffset":177082,"endOffset":177220,"count":1},{"startOffset":177148,"endOffset":177219,"count":0}],"isBlockCoverage":true},{"functionName":"_Uri__fail","ranges":[{"startOffset":177238,"endOffset":177345,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__Uri$file","ranges":[{"startOffset":177367,"endOffset":177497,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__checkNonWindowsPathReservedCharacters","ranges":[{"startOffset":177548,"endOffset":177751,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__checkWindowsPathReservedCharacters","ranges":[{"startOffset":177799,"endOffset":178489,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__checkWindowsDriveLetter","ranges":[{"startOffset":178526,"endOffset":179005,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__makeFileUri","ranges":[{"startOffset":179030,"endOffset":179320,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__makeWindowsFileUrl","ranges":[{"startOffset":179352,"endOffset":181689,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__makePort","ranges":[{"startOffset":181711,"endOffset":181840,"count":1},{"startOffset":181808,"endOffset":181815,"count":0}],"isBlockCoverage":true},{"functionName":"_Uri__makeHost","ranges":[{"startOffset":181862,"endOffset":182764,"count":1},{"startOffset":181952,"endOffset":181959,"count":0},{"startOffset":181993,"endOffset":182003,"count":0},{"startOffset":182067,"endOffset":182435,"count":0},{"startOffset":182479,"endOffset":182497,"count":0},{"startOffset":182603,"endOffset":182701,"count":0}],"isBlockCoverage":true},{"functionName":"_Uri__normalizeRegName","ranges":[{"startOffset":182794,"endOffset":186280,"count":1},{"startOffset":182973,"endOffset":182991,"count":0},{"startOffset":183204,"endOffset":184074,"count":0},{"startOffset":184178,"endOffset":184209,"count":0},{"startOffset":184281,"endOffset":184310,"count":0},{"startOffset":184389,"endOffset":184714,"count":0},{"startOffset":184747,"endOffset":185904,"count":0},{"startOffset":186013,"endOffset":186268,"count":0},{"startOffset":186269,"endOffset":186273,"count":0}],"isBlockCoverage":true},{"functionName":"_Uri__makeScheme","ranges":[{"startOffset":186304,"endOffset":187376,"count":1},{"startOffset":186414,"endOffset":186424,"count":0},{"startOffset":186532,"endOffset":186609,"count":0},{"startOffset":186653,"endOffset":186671,"count":0},{"startOffset":186911,"endOffset":186942,"count":0},{"startOffset":187014,"endOffset":187041,"count":0},{"startOffset":187069,"endOffset":187121,"count":0},{"startOffset":187178,"endOffset":187203,"count":0},{"startOffset":187337,"endOffset":187359,"count":0}],"isBlockCoverage":true},{"functionName":"_Uri__canonicalizeScheme","ranges":[{"startOffset":187408,"endOffset":187669,"count":1},{"startOffset":187478,"endOffset":187668,"count":0}],"isBlockCoverage":true},{"functionName":"_Uri__makeUserInfo","ranges":[{"startOffset":187695,"endOffset":187864,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__makePath","ranges":[{"startOffset":187886,"endOffset":189059,"count":1},{"startOffset":188222,"endOffset":188245,"count":0},{"startOffset":188255,"endOffset":188280,"count":0},{"startOffset":188343,"endOffset":188423,"count":0},{"startOffset":188520,"endOffset":188795,"count":0},{"startOffset":188827,"endOffset":188878,"count":0},{"startOffset":188965,"endOffset":188987,"count":0}],"isBlockCoverage":true},{"functionName":"_Uri__normalizePath","ranges":[{"startOffset":189086,"endOffset":189363,"count":1},{"startOffset":189174,"endOffset":189190,"count":0},{"startOffset":189191,"endOffset":189237,"count":0},{"startOffset":189247,"endOffset":189311,"count":0}],"isBlockCoverage":true},{"functionName":"_Uri__makeQuery","ranges":[{"startOffset":189386,"endOffset":189559,"count":1},{"startOffset":189539,"endOffset":189558,"count":0}],"isBlockCoverage":true},{"functionName":"_Uri__makeFragment","ranges":[{"startOffset":189585,"endOffset":189750,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__normalizeEscape","ranges":[{"startOffset":189779,"endOffset":190943,"count":1},{"startOffset":189942,"endOffset":189962,"count":0},{"startOffset":190024,"endOffset":190035,"count":0},{"startOffset":190351,"endOffset":190362,"count":0},{"startOffset":190534,"endOffset":190565,"count":0},{"startOffset":190630,"endOffset":190655,"count":0},{"startOffset":190678,"endOffset":190787,"count":0},{"startOffset":190845,"endOffset":190923,"count":0}],"isBlockCoverage":true},{"functionName":"_Uri__escapeChar","ranges":[{"startOffset":190967,"endOffset":192472,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__normalizeOrSubstring","ranges":[{"startOffset":192506,"endOffset":192779,"count":1},{"startOffset":192768,"endOffset":192772,"count":0}],"isBlockCoverage":true},{"functionName":"_Uri__normalize","ranges":[{"startOffset":192802,"endOffset":196002,"count":1},{"startOffset":193232,"endOffset":193251,"count":0},{"startOffset":193299,"endOffset":193317,"count":0},{"startOffset":193526,"endOffset":193556,"count":0},{"startOffset":193627,"endOffset":193656,"count":0},{"startOffset":193933,"endOffset":194100,"count":0},{"startOffset":194114,"endOffset":195678,"count":0},{"startOffset":195738,"endOffset":195990,"count":0},{"startOffset":195991,"endOffset":195995,"count":0}],"isBlockCoverage":true},{"functionName":"_Uri__mayContainDotSegments","ranges":[{"startOffset":196037,"endOffset":196202,"count":1},{"startOffset":196122,"endOffset":196134,"count":0}],"isBlockCoverage":true},{"functionName":"_Uri__removeDotSegments","ranges":[{"startOffset":196233,"endOffset":197172,"count":1},{"startOffset":196374,"endOffset":197171,"count":0}],"isBlockCoverage":true},{"functionName":"_Uri__normalizeRelativePath","ranges":[{"startOffset":197207,"endOffset":198750,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__escapeScheme","ranges":[{"startOffset":198776,"endOffset":199463,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__toWindowsFilePath","ranges":[{"startOffset":199494,"endOffset":200490,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__hexCharPairToByte","ranges":[{"startOffset":200521,"endOffset":201052,"count":1},{"startOffset":200917,"endOffset":201009,"count":0}],"isBlockCoverage":true},{"functionName":"_Uri__uriDecode","ranges":[{"startOffset":201075,"endOffset":202742,"count":1},{"startOffset":201518,"endOffset":201552,"count":0},{"startOffset":201719,"endOffset":201730,"count":0},{"startOffset":201831,"endOffset":201913,"count":0},{"startOffset":202110,"endOffset":202185,"count":0},{"startOffset":202270,"endOffset":202327,"count":0},{"startOffset":202497,"endOffset":202532,"count":0}],"isBlockCoverage":true},{"functionName":"_Uri__isAlphabeticCharacter","ranges":[{"startOffset":202777,"endOffset":202890,"count":1}],"isBlockCoverage":true},{"functionName":"UriData__writeUri","ranges":[{"startOffset":202915,"endOffset":203591,"count":0}],"isBlockCoverage":false},{"functionName":"UriData__validateMimeType","ranges":[{"startOffset":203624,"endOffset":203975,"count":0}],"isBlockCoverage":false},{"functionName":"UriData__parse","ranges":[{"startOffset":203997,"endOffset":205905,"count":0}],"isBlockCoverage":false},{"functionName":"UriData__uriEncodeBytes","ranges":[{"startOffset":205936,"endOffset":207460,"count":0}],"isBlockCoverage":false},{"functionName":"_createTables","ranges":[{"startOffset":207481,"endOffset":213521,"count":1}],"isBlockCoverage":true},{"functionName":"_scan","ranges":[{"startOffset":213534,"endOffset":214326,"count":1},{"startOffset":213774,"endOffset":213792,"count":0},{"startOffset":213934,"endOffset":213964,"count":0},{"startOffset":214075,"endOffset":214085,"count":0},{"startOffset":214130,"endOffset":214158,"count":0}],"isBlockCoverage":true},{"functionName":"NoSuchMethodError_toString_closure","ranges":[{"startOffset":214368,"endOffset":214471,"count":0}],"isBlockCoverage":false},{"functionName":"bool","ranges":[{"startOffset":214483,"endOffset":214506,"count":0}],"isBlockCoverage":false},{"functionName":"DateTime","ranges":[{"startOffset":214522,"endOffset":214608,"count":0}],"isBlockCoverage":false},{"functionName":"double","ranges":[{"startOffset":214622,"endOffset":214647,"count":0}],"isBlockCoverage":false},{"functionName":"Duration","ranges":[{"startOffset":214663,"endOffset":214719,"count":1}],"isBlockCoverage":true},{"functionName":"Duration_toString_sixDigits","ranges":[{"startOffset":214754,"endOffset":214800,"count":0}],"isBlockCoverage":false},{"functionName":"Duration_toString_twoDigits","ranges":[{"startOffset":214835,"endOffset":214881,"count":0}],"isBlockCoverage":false},{"functionName":"Error","ranges":[{"startOffset":214894,"endOffset":214918,"count":0}],"isBlockCoverage":false},{"functionName":"NullThrownError","ranges":[{"startOffset":214941,"endOffset":214975,"count":0}],"isBlockCoverage":false},{"functionName":"ArgumentError","ranges":[{"startOffset":214996,"endOffset":215154,"count":0}],"isBlockCoverage":false},{"functionName":"RangeError","ranges":[{"startOffset":215172,"endOffset":215373,"count":0}],"isBlockCoverage":false},{"functionName":"IndexError","ranges":[{"startOffset":215391,"endOffset":215571,"count":0}],"isBlockCoverage":false},{"functionName":"NoSuchMethodError","ranges":[{"startOffset":215596,"endOffset":215830,"count":0}],"isBlockCoverage":false},{"functionName":"UnsupportedError","ranges":[{"startOffset":215854,"endOffset":215916,"count":0}],"isBlockCoverage":false},{"functionName":"UnimplementedError","ranges":[{"startOffset":215942,"endOffset":216006,"count":0}],"isBlockCoverage":false},{"functionName":"StateError","ranges":[{"startOffset":216024,"endOffset":216080,"count":0}],"isBlockCoverage":false},{"functionName":"ConcurrentModificationError","ranges":[{"startOffset":216115,"endOffset":216195,"count":0}],"isBlockCoverage":false},{"functionName":"OutOfMemoryError","ranges":[{"startOffset":216219,"endOffset":216254,"count":1}],"isBlockCoverage":true},{"functionName":"StackOverflowError","ranges":[{"startOffset":216280,"endOffset":216317,"count":0}],"isBlockCoverage":false},{"functionName":"CyclicInitializationError","ranges":[{"startOffset":216350,"endOffset":216426,"count":0}],"isBlockCoverage":false},{"functionName":"_Exception","ranges":[{"startOffset":216444,"endOffset":216500,"count":0}],"isBlockCoverage":false},{"functionName":"FormatException","ranges":[{"startOffset":216523,"endOffset":216640,"count":0}],"isBlockCoverage":false},{"functionName":"Function","ranges":[{"startOffset":216656,"endOffset":216683,"count":0}],"isBlockCoverage":false},{"functionName":"int","ranges":[{"startOffset":216694,"endOffset":216716,"count":0}],"isBlockCoverage":false},{"functionName":"Iterable","ranges":[{"startOffset":216732,"endOffset":216759,"count":0}],"isBlockCoverage":false},{"functionName":"Iterator","ranges":[{"startOffset":216775,"endOffset":216802,"count":0}],"isBlockCoverage":false},{"functionName":"List","ranges":[{"startOffset":216814,"endOffset":216837,"count":0}],"isBlockCoverage":false},{"functionName":"Map","ranges":[{"startOffset":216848,"endOffset":216870,"count":0}],"isBlockCoverage":false},{"functionName":"Null","ranges":[{"startOffset":216882,"endOffset":216905,"count":0}],"isBlockCoverage":false},{"functionName":"num","ranges":[{"startOffset":216916,"endOffset":216938,"count":0}],"isBlockCoverage":false},{"functionName":"Object","ranges":[{"startOffset":216952,"endOffset":216977,"count":0}],"isBlockCoverage":true},{"functionName":"Match","ranges":[{"startOffset":216990,"endOffset":217014,"count":0}],"isBlockCoverage":false},{"functionName":"StackTrace","ranges":[{"startOffset":217032,"endOffset":217061,"count":0}],"isBlockCoverage":false},{"functionName":"_StringStackTrace","ranges":[{"startOffset":217086,"endOffset":217153,"count":0}],"isBlockCoverage":false},{"functionName":"String","ranges":[{"startOffset":217167,"endOffset":217192,"count":0}],"isBlockCoverage":false},{"functionName":"StringBuffer","ranges":[{"startOffset":217212,"endOffset":217272,"count":1}],"isBlockCoverage":true},{"functionName":"Symbol0","ranges":[{"startOffset":217287,"endOffset":217313,"count":0}],"isBlockCoverage":false},{"functionName":"Uri_splitQueryString_closure","ranges":[{"startOffset":217349,"endOffset":217424,"count":1}],"isBlockCoverage":true},{"functionName":"Uri__parseIPv4Address_error","ranges":[{"startOffset":217459,"endOffset":217529,"count":0}],"isBlockCoverage":false},{"functionName":"Uri_parseIPv6Address_error","ranges":[{"startOffset":217563,"endOffset":217632,"count":0}],"isBlockCoverage":false},{"functionName":"Uri_parseIPv6Address_parseHex","ranges":[{"startOffset":217669,"endOffset":217768,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri","ranges":[{"startOffset":217780,"endOffset":218078,"count":1}],"isBlockCoverage":true},{"functionName":"_Uri__Uri$notSimple_closure","ranges":[{"startOffset":218113,"endOffset":218213,"count":1}],"isBlockCoverage":true},{"functionName":"_Uri__checkNonWindowsPathReservedCharacters_closure","ranges":[{"startOffset":218272,"endOffset":218375,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__makePath_closure","ranges":[{"startOffset":218405,"endOffset":218446,"count":0}],"isBlockCoverage":false},{"functionName":"UriData","ranges":[{"startOffset":218461,"endOffset":218582,"count":0}],"isBlockCoverage":false},{"functionName":"_createTables_closure","ranges":[{"startOffset":218611,"endOffset":218651,"count":1}],"isBlockCoverage":true},{"functionName":"_createTables_build","ranges":[{"startOffset":218678,"endOffset":218742,"count":1}],"isBlockCoverage":true},{"functionName":"_createTables_setChars","ranges":[{"startOffset":218772,"endOffset":218813,"count":1}],"isBlockCoverage":true},{"functionName":"_createTables_setRange","ranges":[{"startOffset":218843,"endOffset":218884,"count":1}],"isBlockCoverage":true},{"functionName":"_SimpleUri","ranges":[{"startOffset":218902,"endOffset":219213,"count":0}],"isBlockCoverage":false},{"functionName":"_DataUri","ranges":[{"startOffset":219229,"endOffset":219531,"count":0}],"isBlockCoverage":false},{"functionName":"convertNativePromiseToDartFuture","ranges":[{"startOffset":219571,"endOffset":219951,"count":0}],"isBlockCoverage":false},{"functionName":"_StructuredClone","ranges":[{"startOffset":219975,"endOffset":220010,"count":0}],"isBlockCoverage":false},{"functionName":"_StructuredClone_walk_closure","ranges":[{"startOffset":220047,"endOffset":220148,"count":1}],"isBlockCoverage":true},{"functionName":"_AcceptStructuredClone","ranges":[{"startOffset":220178,"endOffset":220219,"count":0}],"isBlockCoverage":false},{"functionName":"_AcceptStructuredClone_walk_closure","ranges":[{"startOffset":220262,"endOffset":220369,"count":1}],"isBlockCoverage":true},{"functionName":"_StructuredCloneDart2Js","ranges":[{"startOffset":220400,"endOffset":220496,"count":1}],"isBlockCoverage":true},{"functionName":"_AcceptStructuredCloneDart2Js","ranges":[{"startOffset":220533,"endOffset":220664,"count":1}],"isBlockCoverage":true},{"functionName":"convertNativePromiseToDartFuture_closure","ranges":[{"startOffset":220712,"endOffset":220800,"count":0}],"isBlockCoverage":false},{"functionName":"convertNativePromiseToDartFuture_closure0","ranges":[{"startOffset":220849,"endOffset":220938,"count":0}],"isBlockCoverage":false},{"functionName":"SvgElement","ranges":[{"startOffset":220956,"endOffset":220985,"count":0}],"isBlockCoverage":false},{"functionName":"Uint8List","ranges":[{"startOffset":221002,"endOffset":221030,"count":0}],"isBlockCoverage":false},{"functionName":"_convertDartFunctionFast","ranges":[{"startOffset":221062,"endOffset":221474,"count":1},{"startOffset":221174,"endOffset":221190,"count":0}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":221203,"endOffset":221337,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":221239,"endOffset":221328,"count":0}],"isBlockCoverage":false},{"functionName":"_callDartFunctionFast","ranges":[{"startOffset":221503,"endOffset":221700,"count":0}],"isBlockCoverage":false},{"functionName":"allowInterop","ranges":[{"startOffset":221720,"endOffset":222089,"count":1},{"startOffset":221983,"endOffset":221992,"count":0}],"isBlockCoverage":true},{"functionName":"max","ranges":[{"startOffset":222100,"endOffset":222411,"count":0}],"isBlockCoverage":false},{"functionName":"window","ranges":[{"startOffset":222437,"endOffset":222476,"count":1}],"isBlockCoverage":true},{"functionName":"WebSocket_WebSocket","ranges":[{"startOffset":222503,"endOffset":222557,"count":1}],"isBlockCoverage":true},{"functionName":"_EventStreamSubscription$","ranges":[{"startOffset":222590,"endOffset":222884,"count":1},{"startOffset":222677,"endOffset":222683,"count":0}],"isBlockCoverage":true},{"functionName":"_convertNativeToDart_Window","ranges":[{"startOffset":222919,"endOffset":223033,"count":1},{"startOffset":222966,"endOffset":222973,"count":0}],"isBlockCoverage":true},{"functionName":"_DOMWindowCrossFrame__createSafe","ranges":[{"startOffset":223073,"endOffset":223232,"count":1},{"startOffset":223119,"endOffset":223169,"count":0}],"isBlockCoverage":true},{"functionName":"_wrapZone","ranges":[{"startOffset":223249,"endOffset":223507,"count":1},{"startOffset":223425,"endOffset":223441,"count":0}],"isBlockCoverage":true},{"functionName":"HtmlElement","ranges":[{"startOffset":223526,"endOffset":223556,"count":0}],"isBlockCoverage":false},{"functionName":"AnchorElement","ranges":[{"startOffset":223577,"endOffset":223609,"count":0}],"isBlockCoverage":false},{"functionName":"AreaElement","ranges":[{"startOffset":223628,"endOffset":223658,"count":0}],"isBlockCoverage":false},{"functionName":"Blob","ranges":[{"startOffset":223670,"endOffset":223693,"count":0}],"isBlockCoverage":false},{"functionName":"CharacterData","ranges":[{"startOffset":223714,"endOffset":223746,"count":0}],"isBlockCoverage":false},{"functionName":"DomException","ranges":[{"startOffset":223766,"endOffset":223797,"count":0}],"isBlockCoverage":false},{"functionName":"DomTokenList","ranges":[{"startOffset":223817,"endOffset":223848,"count":0}],"isBlockCoverage":false},{"functionName":"Element","ranges":[{"startOffset":223863,"endOffset":223889,"count":0}],"isBlockCoverage":false},{"functionName":"Event","ranges":[{"startOffset":223902,"endOffset":223926,"count":0}],"isBlockCoverage":false},{"functionName":"EventTarget","ranges":[{"startOffset":223945,"endOffset":223975,"count":0}],"isBlockCoverage":false},{"functionName":"File","ranges":[{"startOffset":223987,"endOffset":224010,"count":0}],"isBlockCoverage":false},{"functionName":"FormElement","ranges":[{"startOffset":224029,"endOffset":224059,"count":0}],"isBlockCoverage":false},{"functionName":"HtmlCollection","ranges":[{"startOffset":224081,"endOffset":224114,"count":0}],"isBlockCoverage":false},{"functionName":"IFrameElement","ranges":[{"startOffset":224135,"endOffset":224167,"count":0}],"isBlockCoverage":false},{"functionName":"Location","ranges":[{"startOffset":224183,"endOffset":224210,"count":0}],"isBlockCoverage":false},{"functionName":"MessageEvent","ranges":[{"startOffset":224230,"endOffset":224261,"count":0}],"isBlockCoverage":false},{"functionName":"MessagePort","ranges":[{"startOffset":224280,"endOffset":224310,"count":0}],"isBlockCoverage":false},{"functionName":"MouseEvent","ranges":[{"startOffset":224328,"endOffset":224357,"count":0}],"isBlockCoverage":false},{"functionName":"Node","ranges":[{"startOffset":224369,"endOffset":224392,"count":0}],"isBlockCoverage":false},{"functionName":"SelectElement","ranges":[{"startOffset":224413,"endOffset":224445,"count":0}],"isBlockCoverage":false},{"functionName":"UIEvent","ranges":[{"startOffset":224460,"endOffset":224486,"count":0}],"isBlockCoverage":false},{"functionName":"Window","ranges":[{"startOffset":224500,"endOffset":224525,"count":0}],"isBlockCoverage":false},{"functionName":"_EventStream","ranges":[{"startOffset":224545,"endOffset":224707,"count":0}],"isBlockCoverage":false},{"functionName":"_ElementEventStreamImpl","ranges":[{"startOffset":224738,"endOffset":224911,"count":1}],"isBlockCoverage":true},{"functionName":"_EventStreamSubscription","ranges":[{"startOffset":224943,"endOffset":225168,"count":1}],"isBlockCoverage":true},{"functionName":"_EventStreamSubscription_closure","ranges":[{"startOffset":225208,"endOffset":225285,"count":1}],"isBlockCoverage":true},{"functionName":"ImmutableListMixin","ranges":[{"startOffset":225311,"endOffset":225348,"count":0}],"isBlockCoverage":false},{"functionName":"FixedSizeListIterator","ranges":[{"startOffset":225377,"endOffset":225561,"count":0}],"isBlockCoverage":false},{"functionName":"_DOMWindowCrossFrame","ranges":[{"startOffset":225589,"endOffset":225655,"count":1}],"isBlockCoverage":true},{"functionName":"_HtmlCollection_Interceptor_ListMixin","ranges":[{"startOffset":225700,"endOffset":225756,"count":0}],"isBlockCoverage":false},{"functionName":"_HtmlCollection_Interceptor_ListMixin_ImmutableListMixin","ranges":[{"startOffset":225820,"endOffset":225895,"count":0}],"isBlockCoverage":false},{"functionName":"NullStreamSink","ranges":[{"startOffset":225924,"endOffset":226081,"count":0}],"isBlockCoverage":false},{"functionName":"NullStreamSink_addStream_closure","ranges":[{"startOffset":226117,"endOffset":226193,"count":0}],"isBlockCoverage":false},{"functionName":"Context_Context","ranges":[{"startOffset":226225,"endOffset":226413,"count":0}],"isBlockCoverage":false},{"functionName":"_parseUri","ranges":[{"startOffset":226430,"endOffset":226613,"count":0}],"isBlockCoverage":false},{"functionName":"_validateArgList","ranges":[{"startOffset":226637,"endOffset":227693,"count":0}],"isBlockCoverage":false},{"functionName":"Context","ranges":[{"startOffset":227708,"endOffset":227798,"count":0}],"isBlockCoverage":false},{"functionName":"Context_join_closure","ranges":[{"startOffset":227826,"endOffset":227865,"count":0}],"isBlockCoverage":false},{"functionName":"Context_joinAll_closure","ranges":[{"startOffset":227896,"endOffset":227938,"count":0}],"isBlockCoverage":false},{"functionName":"Context_split_closure","ranges":[{"startOffset":227967,"endOffset":228007,"count":0}],"isBlockCoverage":false},{"functionName":"_validateArgList_closure","ranges":[{"startOffset":228039,"endOffset":228082,"count":0}],"isBlockCoverage":false},{"functionName":"InternalStyle","ranges":[{"startOffset":228110,"endOffset":228142,"count":0}],"isBlockCoverage":false},{"functionName":"StreamChannelController$","ranges":[{"startOffset":228174,"endOffset":228991,"count":1}],"isBlockCoverage":true},{"functionName":"StreamChannelController","ranges":[{"startOffset":229022,"endOffset":229129,"count":1}],"isBlockCoverage":true},{"functionName":"isAlphabetic","ranges":[{"startOffset":229149,"endOffset":229311,"count":0}],"isBlockCoverage":false},{"functionName":"isDriveLetter","ranges":[{"startOffset":229332,"endOffset":229761,"count":0}],"isBlockCoverage":false},{"functionName":"ParsedPath_ParsedPath$parse","ranges":[{"startOffset":229808,"endOffset":231004,"count":0}],"isBlockCoverage":false},{"functionName":"ParsedPath","ranges":[{"startOffset":231022,"endOffset":231169,"count":0}],"isBlockCoverage":false},{"functionName":"ParsedPath_normalize_closure","ranges":[{"startOffset":231205,"endOffset":231277,"count":0}],"isBlockCoverage":false},{"functionName":"PathException$","ranges":[{"startOffset":231299,"endOffset":231367,"count":0}],"isBlockCoverage":false},{"functionName":"PathException","ranges":[{"startOffset":231388,"endOffset":231447,"count":0}],"isBlockCoverage":false},{"functionName":"Style__getPlatformStyle","ranges":[{"startOffset":231490,"endOffset":231852,"count":0}],"isBlockCoverage":false},{"functionName":"Style","ranges":[{"startOffset":231865,"endOffset":231889,"count":0}],"isBlockCoverage":false},{"functionName":"PosixStyle","ranges":[{"startOffset":231914,"endOffset":231998,"count":0}],"isBlockCoverage":false},{"functionName":"UrlStyle","ranges":[{"startOffset":232018,"endOffset":232098,"count":0}],"isBlockCoverage":false},{"functionName":"WindowsStyle","ranges":[{"startOffset":232122,"endOffset":232211,"count":0}],"isBlockCoverage":false},{"functionName":"WindowsStyle_absolutePathToUri_closure","ranges":[{"startOffset":232253,"endOffset":232310,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_Chain$parse","ranges":[{"startOffset":232344,"endOffset":233600,"count":0}],"isBlockCoverage":false},{"functionName":"Chain","ranges":[{"startOffset":233613,"endOffset":233663,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_Chain$parse_closure","ranges":[{"startOffset":233696,"endOffset":233740,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_Chain$parse_closure0","ranges":[{"startOffset":233774,"endOffset":233819,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_toTrace_closure","ranges":[{"startOffset":233848,"endOffset":233888,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_toString_closure0","ranges":[{"startOffset":233919,"endOffset":233961,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_toString__closure0","ranges":[{"startOffset":233993,"endOffset":234036,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_toString_closure","ranges":[{"startOffset":234066,"endOffset":234134,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_toString__closure","ranges":[{"startOffset":234165,"endOffset":234234,"count":0}],"isBlockCoverage":false},{"functionName":"Frame_Frame$parseVM","ranges":[{"startOffset":234273,"endOffset":234389,"count":0}],"isBlockCoverage":false},{"functionName":"Frame_Frame$parseV8","ranges":[{"startOffset":234416,"endOffset":234532,"count":0}],"isBlockCoverage":false},{"functionName":"Frame_Frame$parseFirefox","ranges":[{"startOffset":234564,"endOffset":234685,"count":0}],"isBlockCoverage":false},{"functionName":"Frame_Frame$parseFriendly","ranges":[{"startOffset":234718,"endOffset":234840,"count":0}],"isBlockCoverage":false},{"functionName":"Frame__uriOrPathToUri","ranges":[{"startOffset":234869,"endOffset":235427,"count":0}],"isBlockCoverage":false},{"functionName":"Frame__catchFormatException","ranges":[{"startOffset":235462,"endOffset":235866,"count":0}],"isBlockCoverage":false},{"functionName":"Frame","ranges":[{"startOffset":235879,"endOffset":236016,"count":0}],"isBlockCoverage":false},{"functionName":"Frame_Frame$parseVM_closure","ranges":[{"startOffset":236051,"endOffset":236122,"count":0}],"isBlockCoverage":false},{"functionName":"Frame_Frame$parseV8_closure","ranges":[{"startOffset":236157,"endOffset":236228,"count":0}],"isBlockCoverage":false},{"functionName":"Frame_Frame$parseV8_closure_parseLocation","ranges":[{"startOffset":236277,"endOffset":236362,"count":0}],"isBlockCoverage":false},{"functionName":"Frame_Frame$parseFirefox_closure","ranges":[{"startOffset":236402,"endOffset":236478,"count":0}],"isBlockCoverage":false},{"functionName":"Frame_Frame$parseFriendly_closure","ranges":[{"startOffset":236519,"endOffset":236596,"count":0}],"isBlockCoverage":false},{"functionName":"LazyTrace","ranges":[{"startOffset":236620,"endOffset":236712,"count":0}],"isBlockCoverage":false},{"functionName":"LazyTrace_terse_closure","ranges":[{"startOffset":236739,"endOffset":236806,"count":0}],"isBlockCoverage":false},{"functionName":"Trace_Trace$from","ranges":[{"startOffset":236839,"endOffset":237153,"count":0}],"isBlockCoverage":false},{"functionName":"Trace_Trace$parse","ranges":[{"startOffset":237178,"endOffset":238690,"count":0}],"isBlockCoverage":false},{"functionName":"Trace__parseVM","ranges":[{"startOffset":238712,"endOffset":239434,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseV8","ranges":[{"startOffset":239455,"endOffset":240083,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseJSCore","ranges":[{"startOffset":240108,"endOffset":240613,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseFirefox","ranges":[{"startOffset":240639,"endOffset":241158,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseFriendly","ranges":[{"startOffset":241185,"endOffset":241840,"count":0}],"isBlockCoverage":false},{"functionName":"Trace","ranges":[{"startOffset":241853,"endOffset":241933,"count":0}],"isBlockCoverage":false},{"functionName":"Trace_Trace$from_closure","ranges":[{"startOffset":241965,"endOffset":242033,"count":0}],"isBlockCoverage":false},{"functionName":"Trace__parseVM_closure","ranges":[{"startOffset":242063,"endOffset":242104,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseV8_closure","ranges":[{"startOffset":242133,"endOffset":242173,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseV8_closure0","ranges":[{"startOffset":242203,"endOffset":242244,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseJSCore_closure","ranges":[{"startOffset":242277,"endOffset":242321,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseJSCore_closure0","ranges":[{"startOffset":242355,"endOffset":242400,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseFirefox_closure","ranges":[{"startOffset":242434,"endOffset":242479,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseFirefox_closure0","ranges":[{"startOffset":242514,"endOffset":242560,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseFriendly_closure","ranges":[{"startOffset":242595,"endOffset":242641,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseFriendly_closure0","ranges":[{"startOffset":242677,"endOffset":242724,"count":0}],"isBlockCoverage":false},{"functionName":"Trace_terse_closure","ranges":[{"startOffset":242751,"endOffset":242789,"count":0}],"isBlockCoverage":false},{"functionName":"Trace_foldFrames_closure","ranges":[{"startOffset":242821,"endOffset":242896,"count":0}],"isBlockCoverage":false},{"functionName":"Trace_foldFrames_closure0","ranges":[{"startOffset":242929,"endOffset":242999,"count":0}],"isBlockCoverage":false},{"functionName":"Trace_toString_closure0","ranges":[{"startOffset":243030,"endOffset":243072,"count":0}],"isBlockCoverage":false},{"functionName":"Trace_toString_closure","ranges":[{"startOffset":243102,"endOffset":243170,"count":0}],"isBlockCoverage":false},{"functionName":"UnparsedFrame","ranges":[{"startOffset":243198,"endOffset":243437,"count":0}],"isBlockCoverage":false},{"functionName":"GuaranteeChannel$","ranges":[{"startOffset":243471,"endOffset":243729,"count":1}],"isBlockCoverage":true},{"functionName":"GuaranteeChannel","ranges":[{"startOffset":243753,"endOffset":243940,"count":1}],"isBlockCoverage":true},{"functionName":"GuaranteeChannel_closure","ranges":[{"startOffset":243972,"endOffset":244068,"count":1}],"isBlockCoverage":true},{"functionName":"GuaranteeChannel__closure","ranges":[{"startOffset":244101,"endOffset":244170,"count":1}],"isBlockCoverage":true},{"functionName":"_GuaranteeSink","ranges":[{"startOffset":244192,"endOffset":244487,"count":1}],"isBlockCoverage":true},{"functionName":"_GuaranteeSink_addStream_closure","ranges":[{"startOffset":244527,"endOffset":244603,"count":1}],"isBlockCoverage":true},{"functionName":"main","ranges":[{"startOffset":244615,"endOffset":244926,"count":1},{"startOffset":244690,"endOffset":244714,"count":0}],"isBlockCoverage":true},{"functionName":"_connectToServer","ranges":[{"startOffset":244950,"endOffset":245613,"count":1}],"isBlockCoverage":true},{"functionName":"_connectToIframe","ranges":[{"startOffset":245637,"endOffset":247021,"count":1}],"isBlockCoverage":true},{"functionName":"_TestRunner","ranges":[{"startOffset":247040,"endOffset":247070,"count":0}],"isBlockCoverage":false},{"functionName":"_JSApi","ranges":[{"startOffset":247084,"endOffset":247109,"count":0}],"isBlockCoverage":false},{"functionName":"main_closure","ranges":[{"startOffset":247129,"endOffset":247160,"count":1}],"isBlockCoverage":true},{"functionName":"main__closure","ranges":[{"startOffset":247181,"endOffset":247246,"count":1}],"isBlockCoverage":true},{"functionName":"main__closure0","ranges":[{"startOffset":247268,"endOffset":247334,"count":1}],"isBlockCoverage":true},{"functionName":"main__closure1","ranges":[{"startOffset":247356,"endOffset":247422,"count":1}],"isBlockCoverage":true},{"functionName":"main__closure2","ranges":[{"startOffset":247444,"endOffset":247510,"count":1}],"isBlockCoverage":true},{"functionName":"main__closure3","ranges":[{"startOffset":247532,"endOffset":247598,"count":1}],"isBlockCoverage":true},{"functionName":"main_closure0","ranges":[{"startOffset":247619,"endOffset":247651,"count":1}],"isBlockCoverage":true},{"functionName":"_connectToServer_closure","ranges":[{"startOffset":247683,"endOffset":247756,"count":1}],"isBlockCoverage":true},{"functionName":"_connectToServer_closure0","ranges":[{"startOffset":247789,"endOffset":247862,"count":1}],"isBlockCoverage":true},{"functionName":"_connectToIframe_closure","ranges":[{"startOffset":247894,"endOffset":248068,"count":1}],"isBlockCoverage":true},{"functionName":"_connectToIframe_closure0","ranges":[{"startOffset":248101,"endOffset":248175,"count":1}],"isBlockCoverage":true},{"functionName":"_connectToIframe_closure1","ranges":[{"startOffset":248208,"endOffset":248315,"count":1}],"isBlockCoverage":true},{"functionName":"_MultiChannel$","ranges":[{"startOffset":248349,"endOffset":248683,"count":1}],"isBlockCoverage":true},{"functionName":"_MultiChannel","ranges":[{"startOffset":248704,"endOffset":249002,"count":1}],"isBlockCoverage":true},{"functionName":"_MultiChannel_closure","ranges":[{"startOffset":249031,"endOffset":249119,"count":1}],"isBlockCoverage":true},{"functionName":"_MultiChannel_closure0","ranges":[{"startOffset":249149,"endOffset":249215,"count":1}],"isBlockCoverage":true},{"functionName":"_MultiChannel_closure1","ranges":[{"startOffset":249245,"endOffset":249334,"count":1}],"isBlockCoverage":true},{"functionName":"_MultiChannel__closure","ranges":[{"startOffset":249364,"endOffset":249477,"count":1}],"isBlockCoverage":true},{"functionName":"_MultiChannel_virtualChannel_closure","ranges":[{"startOffset":249521,"endOffset":249629,"count":1}],"isBlockCoverage":true},{"functionName":"_MultiChannel_virtualChannel_closure0","ranges":[{"startOffset":249674,"endOffset":249783,"count":1}],"isBlockCoverage":true},{"functionName":"VirtualChannel","ranges":[{"startOffset":249805,"endOffset":249952,"count":1}],"isBlockCoverage":true},{"functionName":"current","ranges":[{"startOffset":249967,"endOffset":250526,"count":0}],"isBlockCoverage":false},{"functionName":"StreamChannelMixin","ranges":[{"startOffset":250559,"endOffset":250596,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":250814,"endOffset":250880,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":250900,"endOffset":250978,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":250996,"endOffset":251098,"count":0}],"isBlockCoverage":false},{"functionName":"noSuchMethod$1","ranges":[{"startOffset":251120,"endOffset":251378,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":251425,"endOffset":251482,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":251502,"endOffset":251569,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":251625,"endOffset":251686,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":251704,"endOffset":251751,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":251771,"endOffset":251813,"count":0}],"isBlockCoverage":false},{"functionName":"noSuchMethod$1","ranges":[{"startOffset":251835,"endOffset":251986,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":252061,"endOffset":252103,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":252121,"endOffset":252178,"count":0}],"isBlockCoverage":false},{"functionName":"waitUntilDone$0","ranges":[{"startOffset":252201,"endOffset":252266,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":252411,"endOffset":252677,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":252695,"endOffset":252762,"count":0}],"isBlockCoverage":false},{"functionName":"add$1","ranges":[{"startOffset":252825,"endOffset":253058,"count":1},{"startOffset":252978,"endOffset":253024,"count":0}],"isBlockCoverage":true},{"functionName":"removeAt$1","ranges":[{"startOffset":253076,"endOffset":253376,"count":0}],"isBlockCoverage":false},{"functionName":"insert$2","ranges":[{"startOffset":253392,"endOffset":253775,"count":0}],"isBlockCoverage":false},{"functionName":"insertAll$2","ranges":[{"startOffset":253794,"endOffset":254419,"count":0}],"isBlockCoverage":false},{"functionName":"removeLast$0","ranges":[{"startOffset":254439,"endOffset":254691,"count":0}],"isBlockCoverage":false},{"functionName":"addAll$1","ranges":[{"startOffset":254707,"endOffset":255155,"count":0}],"isBlockCoverage":false},{"functionName":"forEach$1","ranges":[{"startOffset":255172,"endOffset":255530,"count":0}],"isBlockCoverage":false},{"functionName":"join$1","ranges":[{"startOffset":255544,"endOffset":255804,"count":0}],"isBlockCoverage":false},{"functionName":"join$0","ranges":[{"startOffset":255818,"endOffset":255886,"count":0}],"isBlockCoverage":false},{"functionName":"fold$1$2","ranges":[{"startOffset":255902,"endOffset":256434,"count":1},{"startOffset":256336,"endOffset":256400,"count":0}],"isBlockCoverage":true},{"functionName":"elementAt$1","ranges":[{"startOffset":256453,"endOffset":256606,"count":0}],"isBlockCoverage":false},{"functionName":"sublist$2","ranges":[{"startOffset":256623,"endOffset":257154,"count":0}],"isBlockCoverage":false},{"functionName":"get$first","ranges":[{"startOffset":257171,"endOffset":257321,"count":0}],"isBlockCoverage":false},{"functionName":"get$last","ranges":[{"startOffset":257337,"endOffset":257511,"count":0}],"isBlockCoverage":false},{"functionName":"setRange$4","ranges":[{"startOffset":257529,"endOffset":258508,"count":0}],"isBlockCoverage":false},{"functionName":"setRange$3","ranges":[{"startOffset":258526,"endOffset":258641,"count":0}],"isBlockCoverage":false},{"functionName":"get$isNotEmpty","ranges":[{"startOffset":258663,"endOffset":258725,"count":1}],"isBlockCoverage":true},{"functionName":"toString$0","ranges":[{"startOffset":258743,"endOffset":258839,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":258859,"endOffset":258990,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":259010,"endOffset":259088,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":259106,"endOffset":259162,"count":1}],"isBlockCoverage":true},{"functionName":"set$length","ranges":[{"startOffset":259180,"endOffset":259464,"count":1},{"startOffset":259255,"endOffset":259308,"count":0},{"startOffset":259342,"endOffset":259423,"count":0}],"isBlockCoverage":true},{"functionName":"$index","ranges":[{"startOffset":259478,"endOffset":259689,"count":1},{"startOffset":259592,"endOffset":259653,"count":0}],"isBlockCoverage":true},{"functionName":"$indexSet","ranges":[{"startOffset":259706,"endOffset":260245,"count":1},{"startOffset":259897,"endOffset":259951,"count":0},{"startOffset":260028,"endOffset":260089,"count":0},{"startOffset":260147,"endOffset":260208,"count":0}],"isBlockCoverage":true},{"functionName":"get$current","ranges":[{"startOffset":260411,"endOffset":260472,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":260490,"endOffset":260928,"count":0}],"isBlockCoverage":false},{"functionName":"set$__interceptors$_current","ranges":[{"startOffset":260963,"endOffset":261101,"count":0}],"isBlockCoverage":false},{"functionName":"toRadixString$1","ranges":[{"startOffset":261175,"endOffset":262041,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":262059,"endOffset":262195,"count":1},{"startOffset":262134,"endOffset":262148,"count":0}],"isBlockCoverage":true},{"functionName":"get$hashCode","ranges":[{"startOffset":262215,"endOffset":262729,"count":0}],"isBlockCoverage":false},{"functionName":"$mod","ranges":[{"startOffset":262741,"endOffset":262992,"count":0}],"isBlockCoverage":false},{"functionName":"$tdiv","ranges":[{"startOffset":263005,"endOffset":263202,"count":0}],"isBlockCoverage":false},{"functionName":"_tdivFast$1","ranges":[{"startOffset":263221,"endOffset":263355,"count":1},{"startOffset":263313,"endOffset":263348,"count":0}],"isBlockCoverage":true},{"functionName":"_tdivSlow$1","ranges":[{"startOffset":263374,"endOffset":263848,"count":0}],"isBlockCoverage":false},{"functionName":"_shrOtherPositive$1","ranges":[{"startOffset":263875,"endOffset":264112,"count":1},{"startOffset":263995,"endOffset":264089,"count":0}],"isBlockCoverage":true},{"functionName":"_shrReceiverPositive$1","ranges":[{"startOffset":264142,"endOffset":264311,"count":0}],"isBlockCoverage":false},{"functionName":"_shrBothPositive$1","ranges":[{"startOffset":264337,"endOffset":264420,"count":1},{"startOffset":264389,"endOffset":264392,"count":0}],"isBlockCoverage":true},{"functionName":"$gt","ranges":[{"startOffset":264431,"endOffset":264592,"count":0}],"isBlockCoverage":false},{"functionName":"codeUnitAt$1","ranges":[{"startOffset":264740,"endOffset":265145,"count":1},{"startOffset":264844,"endOffset":264905,"count":0},{"startOffset":264935,"endOffset":264996,"count":0},{"startOffset":265041,"endOffset":265098,"count":0}],"isBlockCoverage":true},{"functionName":"_codeUnitAt$1","ranges":[{"startOffset":265166,"endOffset":265346,"count":1},{"startOffset":265238,"endOffset":265299,"count":0}],"isBlockCoverage":true},{"functionName":"allMatches$2","ranges":[{"startOffset":265366,"endOffset":265723,"count":0}],"isBlockCoverage":false},{"functionName":"allMatches$1","ranges":[{"startOffset":265743,"endOffset":265832,"count":0}],"isBlockCoverage":false},{"functionName":"matchAsPrefix$2","ranges":[{"startOffset":265855,"endOffset":266378,"count":0}],"isBlockCoverage":false},{"functionName":"$add","ranges":[{"startOffset":266390,"endOffset":266564,"count":0}],"isBlockCoverage":false},{"functionName":"endsWith$1","ranges":[{"startOffset":266582,"endOffset":266823,"count":0}],"isBlockCoverage":false},{"functionName":"replaceFirst$2","ranges":[{"startOffset":266845,"endOffset":267026,"count":0}],"isBlockCoverage":false},{"functionName":"replaceRange$3","ranges":[{"startOffset":267048,"endOffset":267373,"count":0}],"isBlockCoverage":false},{"functionName":"startsWith$2","ranges":[{"startOffset":267393,"endOffset":268070,"count":1},{"startOffset":267526,"endOffset":267573,"count":0},{"startOffset":267619,"endOffset":267638,"count":0},{"startOffset":267695,"endOffset":267776,"count":0},{"startOffset":267911,"endOffset":267924,"count":0},{"startOffset":267996,"endOffset":268069,"count":0}],"isBlockCoverage":true},{"functionName":"startsWith$1","ranges":[{"startOffset":268090,"endOffset":268181,"count":1}],"isBlockCoverage":true},{"functionName":"substring$2","ranges":[{"startOffset":268200,"endOffset":268888,"count":1},{"startOffset":268334,"endOffset":268386,"count":0},{"startOffset":268501,"endOffset":268525,"count":0},{"startOffset":268560,"endOffset":268620,"count":0},{"startOffset":268662,"endOffset":268722,"count":0},{"startOffset":268769,"endOffset":268827,"count":0}],"isBlockCoverage":true},{"functionName":"substring$1","ranges":[{"startOffset":268907,"endOffset":269006,"count":1}],"isBlockCoverage":true},{"functionName":"trim$0","ranges":[{"startOffset":269020,"endOffset":269700,"count":0}],"isBlockCoverage":false},{"functionName":"$mul","ranges":[{"startOffset":269712,"endOffset":270191,"count":0}],"isBlockCoverage":false},{"functionName":"padRight$1","ranges":[{"startOffset":270209,"endOffset":270458,"count":0}],"isBlockCoverage":false},{"functionName":"indexOf$2","ranges":[{"startOffset":270475,"endOffset":270731,"count":1},{"startOffset":270582,"endOffset":270663,"count":0}],"isBlockCoverage":true},{"functionName":"indexOf$1","ranges":[{"startOffset":270748,"endOffset":270836,"count":1}],"isBlockCoverage":true},{"functionName":"lastIndexOf$2","ranges":[{"startOffset":270857,"endOffset":271276,"count":0}],"isBlockCoverage":false},{"functionName":"lastIndexOf$1","ranges":[{"startOffset":271297,"endOffset":271392,"count":0}],"isBlockCoverage":false},{"functionName":"contains$1","ranges":[{"startOffset":271410,"endOffset":271584,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":271602,"endOffset":271651,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":271671,"endOffset":272077,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":272095,"endOffset":272151,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":272165,"endOffset":272372,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":272459,"endOffset":272512,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":272526,"endOffset":272627,"count":0}],"isBlockCoverage":false},{"functionName":"$asEfficientLengthIterable","ranges":[{"startOffset":272661,"endOffset":272701,"count":0}],"isBlockCoverage":false},{"functionName":"$asUnmodifiableListMixin","ranges":[{"startOffset":272733,"endOffset":272773,"count":0}],"isBlockCoverage":false},{"functionName":"$asListMixin","ranges":[{"startOffset":272793,"endOffset":272833,"count":0}],"isBlockCoverage":false},{"functionName":"$asIterable","ranges":[{"startOffset":272852,"endOffset":272892,"count":0}],"isBlockCoverage":false},{"functionName":"$asList","ranges":[{"startOffset":272907,"endOffset":272947,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":273046,"endOffset":273183,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":273202,"endOffset":273263,"count":0}],"isBlockCoverage":false},{"functionName":"join$1","ranges":[{"startOffset":273277,"endOffset":274216,"count":0}],"isBlockCoverage":false},{"functionName":"join$0","ranges":[{"startOffset":274230,"endOffset":274298,"count":0}],"isBlockCoverage":false},{"functionName":"fold$1$2","ranges":[{"startOffset":274314,"endOffset":274870,"count":0}],"isBlockCoverage":false},{"functionName":"toList$1$growable","ranges":[{"startOffset":274895,"endOffset":275249,"count":0}],"isBlockCoverage":false},{"functionName":"toList$0","ranges":[{"startOffset":275265,"endOffset":275346,"count":0}],"isBlockCoverage":false},{"functionName":"get$_endIndex","ranges":[{"startOffset":275405,"endOffset":275616,"count":0}],"isBlockCoverage":false},{"functionName":"get$_startIndex","ranges":[{"startOffset":275639,"endOffset":275841,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":275859,"endOffset":276224,"count":0}],"isBlockCoverage":false},{"functionName":"elementAt$1","ranges":[{"startOffset":276243,"endOffset":276692,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":276746,"endOffset":276803,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":276821,"endOffset":277341,"count":0}],"isBlockCoverage":false},{"functionName":"set$__internal$_current","ranges":[{"startOffset":277372,"endOffset":277506,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":277583,"endOffset":277702,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":277720,"endOffset":277797,"count":0}],"isBlockCoverage":false},{"functionName":"$asIterable","ranges":[{"startOffset":277816,"endOffset":277859,"count":0}],"isBlockCoverage":false},{"functionName":"$asEfficientLengthIterable","ranges":[{"startOffset":277975,"endOffset":278018,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":278073,"endOffset":278314,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":278333,"endOffset":278390,"count":0}],"isBlockCoverage":false},{"functionName":"set$__internal$_current","ranges":[{"startOffset":278421,"endOffset":278555,"count":0}],"isBlockCoverage":false},{"functionName":"$asIterator","ranges":[{"startOffset":278574,"endOffset":278617,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":278676,"endOffset":278740,"count":0}],"isBlockCoverage":false},{"functionName":"elementAt$1","ranges":[{"startOffset":278759,"endOffset":278853,"count":0}],"isBlockCoverage":false},{"functionName":"$asEfficientLengthIterable","ranges":[{"startOffset":278887,"endOffset":278930,"count":0}],"isBlockCoverage":false},{"functionName":"$asListIterable","ranges":[{"startOffset":278953,"endOffset":278996,"count":0}],"isBlockCoverage":false},{"functionName":"$asIterable","ranges":[{"startOffset":279015,"endOffset":279058,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":279114,"endOffset":279232,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":279286,"endOffset":279470,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":279489,"endOffset":279550,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":279607,"endOffset":279745,"count":0}],"isBlockCoverage":false},{"functionName":"$asIterable","ranges":[{"startOffset":279764,"endOffset":279807,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":279863,"endOffset":279920,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":279938,"endOffset":280470,"count":0}],"isBlockCoverage":false},{"functionName":"set$_currentExpansion","ranges":[{"startOffset":280499,"endOffset":280668,"count":0}],"isBlockCoverage":false},{"functionName":"set$__internal$_current","ranges":[{"startOffset":280699,"endOffset":280833,"count":0}],"isBlockCoverage":false},{"functionName":"$asIterator","ranges":[{"startOffset":280872,"endOffset":280915,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":280975,"endOffset":281097,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":281155,"endOffset":281440,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":281459,"endOffset":281520,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":281574,"endOffset":281612,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":281631,"endOffset":281663,"count":0}],"isBlockCoverage":false},{"functionName":"$indexSet","ranges":[{"startOffset":281785,"endOffset":282038,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":282140,"endOffset":282204,"count":0}],"isBlockCoverage":false},{"functionName":"elementAt$1","ranges":[{"startOffset":282223,"endOffset":282393,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":282442,"endOffset":282661,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":282679,"endOffset":282759,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":282770,"endOffset":282934,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":283042,"endOffset":283103,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":283121,"endOffset":283182,"count":0}],"isBlockCoverage":false},{"functionName":"$indexSet","ranges":[{"startOffset":283199,"endOffset":283429,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":283502,"endOffset":283560,"count":0}],"isBlockCoverage":false},{"functionName":"containsKey$1","ranges":[{"startOffset":283581,"endOffset":283761,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":283775,"endOffset":283884,"count":0}],"isBlockCoverage":false},{"functionName":"_fetch$1","ranges":[{"startOffset":283900,"endOffset":283974,"count":0}],"isBlockCoverage":false},{"functionName":"forEach$1","ranges":[{"startOffset":283991,"endOffset":284372,"count":0}],"isBlockCoverage":false},{"functionName":"Instantiation$1","ranges":[{"startOffset":284431,"endOffset":284530,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":284548,"endOffset":284741,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":284792,"endOffset":284881,"count":0}],"isBlockCoverage":false},{"functionName":"call$4","ranges":[{"startOffset":284895,"endOffset":285000,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":285018,"endOffset":285157,"count":0}],"isBlockCoverage":false},{"functionName":"get$memberName","ranges":[{"startOffset":285220,"endOffset":285288,"count":0}],"isBlockCoverage":false},{"functionName":"get$positionalArguments","ranges":[{"startOffset":285319,"endOffset":285850,"count":0}],"isBlockCoverage":false},{"functionName":"get$namedArguments","ranges":[{"startOffset":285876,"endOffset":286722,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":286820,"endOffset":287115,"count":0}],"isBlockCoverage":false},{"functionName":"matchTypeError$1","ranges":[{"startOffset":287198,"endOffset":287850,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":287900,"endOffset":288103,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":288163,"endOffset":288563,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":288622,"endOffset":288728,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":288838,"endOffset":289012,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":289083,"endOffset":289391,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":289461,"endOffset":289555,"count":0}],"isBlockCoverage":false},{"functionName":"get$$call","ranges":[{"startOffset":289592,"endOffset":289629,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":289793,"endOffset":289982,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":290028,"endOffset":290329,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":290349,"endOffset":290718,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":290736,"endOffset":290971,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":291035,"endOffset":291081,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":291145,"endOffset":291191,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":291244,"endOffset":291314,"count":0}],"isBlockCoverage":false},{"functionName":"get$_typeName","ranges":[{"startOffset":291366,"endOffset":291542,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":291560,"endOffset":291614,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":291634,"endOffset":291830,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":291841,"endOffset":292006,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":292062,"endOffset":292120,"count":1}],"isBlockCoverage":true},{"functionName":"get$isEmpty","ranges":[{"startOffset":292139,"endOffset":292203,"count":1}],"isBlockCoverage":true},{"functionName":"get$keys","ranges":[{"startOffset":292219,"endOffset":292325,"count":0}],"isBlockCoverage":false},{"functionName":"get$values","ranges":[{"startOffset":292343,"endOffset":292585,"count":0}],"isBlockCoverage":false},{"functionName":"containsKey$1","ranges":[{"startOffset":292606,"endOffset":293097,"count":1},{"startOffset":292682,"endOffset":292834,"count":0},{"startOffset":292963,"endOffset":292976,"count":0},{"startOffset":293038,"endOffset":293091,"count":0}],"isBlockCoverage":true},{"functionName":"internalContainsKey$1","ranges":[{"startOffset":293126,"endOffset":293341,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":293355,"endOffset":293981,"count":1},{"startOffset":293518,"endOffset":293525,"count":0},{"startOffset":293603,"endOffset":293609,"count":0},{"startOffset":293790,"endOffset":293797,"count":0},{"startOffset":293872,"endOffset":293878,"count":0},{"startOffset":293930,"endOffset":293975,"count":0}],"isBlockCoverage":true},{"functionName":"internalGet$1","ranges":[{"startOffset":294002,"endOffset":294339,"count":0}],"isBlockCoverage":false},{"functionName":"$indexSet","ranges":[{"startOffset":294356,"endOffset":295711,"count":1},{"startOffset":295102,"endOffset":295705,"count":0}],"isBlockCoverage":true},{"functionName":"putIfAbsent$2","ranges":[{"startOffset":295732,"endOffset":296105,"count":1},{"startOffset":296009,"endOffset":296104,"count":0}],"isBlockCoverage":true},{"functionName":"remove$1","ranges":[{"startOffset":296121,"endOffset":296430,"count":0}],"isBlockCoverage":false},{"functionName":"internalRemove$1","ranges":[{"startOffset":296454,"endOffset":296861,"count":0}],"isBlockCoverage":false},{"functionName":"clear$0","ranges":[{"startOffset":296876,"endOffset":297150,"count":0}],"isBlockCoverage":false},{"functionName":"forEach$1","ranges":[{"startOffset":297167,"endOffset":297681,"count":1},{"startOffset":297580,"endOffset":297640,"count":0}],"isBlockCoverage":true},{"functionName":"_addHashTableEntry$3","ranges":[{"startOffset":297709,"endOffset":298113,"count":1},{"startOffset":298057,"endOffset":298107,"count":0}],"isBlockCoverage":true},{"functionName":"_removeHashTableEntry$2","ranges":[{"startOffset":298144,"endOffset":298428,"count":0}],"isBlockCoverage":false},{"functionName":"_modified$0","ranges":[{"startOffset":298447,"endOffset":298529,"count":1}],"isBlockCoverage":true},{"functionName":"_newLinkedCell$2","ranges":[{"startOffset":298553,"endOffset":299085,"count":1}],"isBlockCoverage":true},{"functionName":"_unlinkCell$1","ranges":[{"startOffset":299106,"endOffset":299471,"count":0}],"isBlockCoverage":false},{"functionName":"internalFindBucketIndex$2","ranges":[{"startOffset":299504,"endOffset":299755,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":299773,"endOffset":299834,"count":0}],"isBlockCoverage":false},{"functionName":"_getTableCell$2","ranges":[{"startOffset":299857,"endOffset":299910,"count":1}],"isBlockCoverage":true},{"functionName":"_getTableBucket$2","ranges":[{"startOffset":299935,"endOffset":299988,"count":0}],"isBlockCoverage":false},{"functionName":"_setTableEntry$3","ranges":[{"startOffset":300012,"endOffset":300073,"count":1}],"isBlockCoverage":true},{"functionName":"_deleteTableEntry$2","ranges":[{"startOffset":300100,"endOffset":300153,"count":1}],"isBlockCoverage":true},{"functionName":"_containsTableEntry$2","ranges":[{"startOffset":300182,"endOffset":300265,"count":1}],"isBlockCoverage":true},{"functionName":"_newHashTable$0","ranges":[{"startOffset":300288,"endOffset":300495,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":300587,"endOffset":300732,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":300750,"endOffset":300898,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":301001,"endOffset":301076,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":301095,"endOffset":301176,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":301196,"endOffset":301388,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":301454,"endOffset":301512,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":301530,"endOffset":302000,"count":0}],"isBlockCoverage":false},{"functionName":"set$__js_helper$_current","ranges":[{"startOffset":302032,"endOffset":302167,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":302241,"endOffset":302289,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":302363,"endOffset":302428,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":302503,"endOffset":302583,"count":1}],"isBlockCoverage":true},{"functionName":"toString$0","ranges":[{"startOffset":302658,"endOffset":302722,"count":0}],"isBlockCoverage":false},{"functionName":"get$_nativeGlobalVersion","ranges":[{"startOffset":302754,"endOffset":303029,"count":0}],"isBlockCoverage":false},{"functionName":"get$_nativeAnchoredVersion","ranges":[{"startOffset":303063,"endOffset":303350,"count":0}],"isBlockCoverage":false},{"functionName":"firstMatch$1","ranges":[{"startOffset":303370,"endOffset":303626,"count":0}],"isBlockCoverage":false},{"functionName":"allMatches$2","ranges":[{"startOffset":303646,"endOffset":303862,"count":0}],"isBlockCoverage":false},{"functionName":"allMatches$1","ranges":[{"startOffset":303882,"endOffset":303971,"count":0}],"isBlockCoverage":false},{"functionName":"_execGlobal$2","ranges":[{"startOffset":303992,"endOffset":304252,"count":0}],"isBlockCoverage":false},{"functionName":"_execAnchored$2","ranges":[{"startOffset":304275,"endOffset":304648,"count":0}],"isBlockCoverage":false},{"functionName":"matchAsPrefix$2","ranges":[{"startOffset":304671,"endOffset":304954,"count":0}],"isBlockCoverage":false},{"functionName":"get$start","ranges":[{"startOffset":305051,"endOffset":305102,"count":0}],"isBlockCoverage":false},{"functionName":"get$end","ranges":[{"startOffset":305117,"endOffset":305201,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":305215,"endOffset":305397,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":305476,"endOffset":305584,"count":0}],"isBlockCoverage":false},{"functionName":"$asIterable","ranges":[{"startOffset":305603,"endOffset":305645,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":305706,"endOffset":305764,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":305782,"endOffset":306369,"count":0}],"isBlockCoverage":false},{"functionName":"$asIterator","ranges":[{"startOffset":306408,"endOffset":306450,"count":0}],"isBlockCoverage":false},{"functionName":"get$end","ranges":[{"startOffset":306499,"endOffset":306643,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":306657,"endOffset":306806,"count":0}],"isBlockCoverage":false},{"functionName":"get$start","ranges":[{"startOffset":306840,"endOffset":306891,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":306959,"endOffset":307077,"count":0}],"isBlockCoverage":false},{"functionName":"$asIterable","ranges":[{"startOffset":307096,"endOffset":307138,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":307204,"endOffset":307851,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":307870,"endOffset":307928,"count":0}],"isBlockCoverage":false},{"functionName":"$asIterator","ranges":[{"startOffset":307967,"endOffset":308009,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":308182,"endOffset":308238,"count":0}],"isBlockCoverage":false},{"functionName":"$asJavaScriptIndexingBehavior","ranges":[{"startOffset":308313,"endOffset":308331,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":308392,"endOffset":308544,"count":0}],"isBlockCoverage":false},{"functionName":"$indexSet","ranges":[{"startOffset":308561,"endOffset":308753,"count":0}],"isBlockCoverage":false},{"functionName":"$asEfficientLengthIterable","ranges":[{"startOffset":308822,"endOffset":308865,"count":0}],"isBlockCoverage":false},{"functionName":"$asFixedLengthListMixin","ranges":[{"startOffset":308896,"endOffset":308939,"count":0}],"isBlockCoverage":false},{"functionName":"$asListMixin","ranges":[{"startOffset":308959,"endOffset":309002,"count":0}],"isBlockCoverage":false},{"functionName":"$asIterable","ranges":[{"startOffset":309041,"endOffset":309084,"count":0}],"isBlockCoverage":false},{"functionName":"$asList","ranges":[{"startOffset":309115,"endOffset":309158,"count":0}],"isBlockCoverage":false},{"functionName":"$indexSet","ranges":[{"startOffset":309219,"endOffset":309408,"count":1}],"isBlockCoverage":true},{"functionName":"$asEfficientLengthIterable","ranges":[{"startOffset":309477,"endOffset":309517,"count":0}],"isBlockCoverage":false},{"functionName":"$asFixedLengthListMixin","ranges":[{"startOffset":309548,"endOffset":309588,"count":0}],"isBlockCoverage":false},{"functionName":"$asListMixin","ranges":[{"startOffset":309608,"endOffset":309648,"count":1}],"isBlockCoverage":true},{"functionName":"$asIterable","ranges":[{"startOffset":309687,"endOffset":309727,"count":0}],"isBlockCoverage":false},{"functionName":"$asList","ranges":[{"startOffset":309758,"endOffset":309798,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":309850,"endOffset":310002,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":310054,"endOffset":310206,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":310257,"endOffset":310409,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":310462,"endOffset":310614,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":310667,"endOffset":310819,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":310882,"endOffset":310938,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":310952,"endOffset":311104,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":311160,"endOffset":311216,"count":1}],"isBlockCoverage":true},{"functionName":"$index","ranges":[{"startOffset":311230,"endOffset":311382,"count":0}],"isBlockCoverage":false},{"functionName":"sublist$2","ranges":[{"startOffset":311399,"endOffset":311541,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":312009,"endOffset":312148,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":312250,"endOffset":312486,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":312598,"endOffset":312646,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":312812,"endOffset":312860,"count":0}],"isBlockCoverage":false},{"functionName":"_TimerImpl$2","ranges":[{"startOffset":312981,"endOffset":313267,"count":0}],"isBlockCoverage":false},{"functionName":"_TimerImpl$periodic$2","ranges":[{"startOffset":313296,"endOffset":313599,"count":1},{"startOffset":313511,"endOffset":313593,"count":0}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":313680,"endOffset":313756,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":313888,"endOffset":314241,"count":0}],"isBlockCoverage":false},{"functionName":"complete$1","ranges":[{"startOffset":314370,"endOffset":314852,"count":1},{"startOffset":314559,"endOffset":314846,"count":0}],"isBlockCoverage":true},{"functionName":"completeError$2","ranges":[{"startOffset":314875,"endOffset":315072,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":315167,"endOffset":315240,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":315387,"endOffset":315467,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":315594,"endOffset":315668,"count":1}],"isBlockCoverage":true},{"functionName":"call$2","ranges":[{"startOffset":315747,"endOffset":315907,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":316044,"endOffset":316137,"count":1}],"isBlockCoverage":true},{"functionName":"completeError$2","ranges":[{"startOffset":316289,"endOffset":316893,"count":0}],"isBlockCoverage":false},{"functionName":"completeError$1","ranges":[{"startOffset":316916,"endOffset":316987,"count":0}],"isBlockCoverage":false},{"functionName":"complete$1","ranges":[{"startOffset":317064,"endOffset":317349,"count":1},{"startOffset":317244,"endOffset":317309,"count":0}],"isBlockCoverage":true},{"functionName":"complete$0","ranges":[{"startOffset":317367,"endOffset":317441,"count":1}],"isBlockCoverage":true},{"functionName":"_completeError$2","ranges":[{"startOffset":317465,"endOffset":317560,"count":0}],"isBlockCoverage":false},{"functionName":"complete$1","ranges":[{"startOffset":317615,"endOffset":317895,"count":1},{"startOffset":317795,"endOffset":317860,"count":0}],"isBlockCoverage":true},{"functionName":"complete$0","ranges":[{"startOffset":317913,"endOffset":317987,"count":0}],"isBlockCoverage":false},{"functionName":"_completeError$2","ranges":[{"startOffset":318011,"endOffset":318101,"count":0}],"isBlockCoverage":false},{"functionName":"matchesErrorTest$1","ranges":[{"startOffset":318165,"endOffset":318401,"count":0}],"isBlockCoverage":false},{"functionName":"handleError$1","ranges":[{"startOffset":318422,"endOffset":319026,"count":0}],"isBlockCoverage":false},{"functionName":"then$1$2$onError","ranges":[{"startOffset":319080,"endOffset":319598,"count":1},{"startOffset":319465,"endOffset":319521,"count":0}],"isBlockCoverage":true},{"functionName":"then$1$1","ranges":[{"startOffset":319614,"endOffset":319686,"count":1}],"isBlockCoverage":true},{"functionName":"_thenNoZoneRegistration$1$2","ranges":[{"startOffset":319721,"endOffset":320105,"count":1}],"isBlockCoverage":true},{"functionName":"whenComplete$1","ranges":[{"startOffset":320127,"endOffset":320534,"count":0}],"isBlockCoverage":false},{"functionName":"_addListener$1","ranges":[{"startOffset":320556,"endOffset":321250,"count":1},{"startOffset":320829,"endOffset":321144,"count":0}],"isBlockCoverage":true},{"functionName":"_prependListeners$1","ranges":[{"startOffset":321277,"endOffset":322404,"count":0}],"isBlockCoverage":false},{"functionName":"_removeListeners$0","ranges":[{"startOffset":322430,"endOffset":322625,"count":1}],"isBlockCoverage":true},{"functionName":"_reverseListeners$1","ranges":[{"startOffset":322652,"endOffset":322909,"count":1}],"isBlockCoverage":true},{"functionName":"_complete$1","ranges":[{"startOffset":322928,"endOffset":323583,"count":1},{"startOffset":323168,"endOffset":323336,"count":0}],"isBlockCoverage":true},{"functionName":"_completeError$2","ranges":[{"startOffset":323607,"endOffset":323915,"count":0}],"isBlockCoverage":false},{"functionName":"_completeError$1","ranges":[{"startOffset":323939,"endOffset":324011,"count":0}],"isBlockCoverage":false},{"functionName":"_asyncComplete$1","ranges":[{"startOffset":324035,"endOffset":324387,"count":1},{"startOffset":324208,"endOffset":324269,"count":0}],"isBlockCoverage":true},{"functionName":"_chainFuture$1","ranges":[{"startOffset":324409,"endOffset":324868,"count":0}],"isBlockCoverage":false},{"functionName":"_asyncCompleteError$2","ranges":[{"startOffset":324897,"endOffset":325120,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":325203,"endOffset":325287,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":325425,"endOffset":325517,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":325657,"endOffset":325758,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":325850,"endOffset":325999,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":326013,"endOffset":326075,"count":0}],"isBlockCoverage":false},{"functionName":"$defaultValues","ranges":[{"startOffset":326120,"endOffset":326159,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":326252,"endOffset":326322,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":326457,"endOffset":326765,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":326898,"endOffset":326974,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":327114,"endOffset":327196,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":327357,"endOffset":328955,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":329075,"endOffset":329128,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":329234,"endOffset":329953,"count":1},{"startOffset":329710,"endOffset":329947,"count":0}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":330050,"endOffset":330966,"count":0}],"isBlockCoverage":false},{"functionName":"pipe$1","ranges":[{"startOffset":331068,"endOffset":331333,"count":1}],"isBlockCoverage":true},{"functionName":"get$length","ranges":[{"startOffset":331351,"endOffset":331673,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":331729,"endOffset":331793,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":331871,"endOffset":332007,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":332025,"endOffset":332139,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":332198,"endOffset":332266,"count":0}],"isBlockCoverage":false},{"functionName":"get$_pendingEvents","ranges":[{"startOffset":332504,"endOffset":332877,"count":1},{"startOffset":332650,"endOffset":332876,"count":0}],"isBlockCoverage":true},{"functionName":"_ensurePendingEvents$0","ranges":[{"startOffset":332907,"endOffset":333600,"count":0}],"isBlockCoverage":false},{"functionName":"get$_subscription","ranges":[{"startOffset":333625,"endOffset":334046,"count":1},{"startOffset":333673,"endOffset":333925,"count":0}],"isBlockCoverage":true},{"functionName":"_badEventState$0","ranges":[{"startOffset":334070,"endOffset":334263,"count":0}],"isBlockCoverage":false},{"functionName":"_ensureDoneFuture$0","ranges":[{"startOffset":334290,"endOffset":334533,"count":0}],"isBlockCoverage":false},{"functionName":"add$1","ranges":[{"startOffset":334546,"endOffset":334760,"count":1},{"startOffset":334681,"endOffset":334728,"count":0}],"isBlockCoverage":true},{"functionName":"addError$2","ranges":[{"startOffset":334778,"endOffset":335358,"count":0}],"isBlockCoverage":false},{"functionName":"addError$1","ranges":[{"startOffset":335376,"endOffset":335442,"count":0}],"isBlockCoverage":false},{"functionName":"close$0","ranges":[{"startOffset":335457,"endOffset":335879,"count":0}],"isBlockCoverage":false},{"functionName":"_add$1","ranges":[{"startOffset":335893,"endOffset":336207,"count":1},{"startOffset":336085,"endOffset":336201,"count":0}],"isBlockCoverage":true},{"functionName":"_async$_addError$2","ranges":[{"startOffset":336233,"endOffset":336487,"count":0}],"isBlockCoverage":false},{"functionName":"_subscribe$4","ranges":[{"startOffset":336507,"endOffset":337709,"count":1},{"startOffset":336834,"endOffset":336911,"count":0},{"startOffset":336965,"endOffset":336968,"count":0},{"startOffset":337264,"endOffset":337491,"count":0}],"isBlockCoverage":true},{"functionName":"_recordCancel$1","ranges":[{"startOffset":337732,"endOffset":338892,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":339105,"endOffset":339165,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":339261,"endOffset":339394,"count":0}],"isBlockCoverage":false},{"functionName":"_sendData$1","ranges":[{"startOffset":339533,"endOffset":339677,"count":1}],"isBlockCoverage":true},{"functionName":"_sendError$2","ranges":[{"startOffset":339697,"endOffset":339802,"count":0}],"isBlockCoverage":false},{"functionName":"_sendDone$0","ranges":[{"startOffset":339821,"endOffset":339882,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":339984,"endOffset":340083,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":340094,"endOffset":340307,"count":0}],"isBlockCoverage":false},{"functionName":"_onCancel$0","ranges":[{"startOffset":340372,"endOffset":340443,"count":0}],"isBlockCoverage":false},{"functionName":"_onPause$0","ranges":[{"startOffset":340461,"endOffset":340868,"count":0}],"isBlockCoverage":false},{"functionName":"_onResume$0","ranges":[{"startOffset":340887,"endOffset":341296,"count":0}],"isBlockCoverage":false},{"functionName":"add$1","ranges":[{"startOffset":341350,"endOffset":341482,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":341597,"endOffset":341672,"count":0}],"isBlockCoverage":false},{"functionName":"_BufferingStreamSubscription$4","ranges":[{"startOffset":341780,"endOffset":343046,"count":1},{"startOffset":342069,"endOffset":342106,"count":0},{"startOffset":342501,"endOffset":342838,"count":0}],"isBlockCoverage":true},{"functionName":"_setPendingEvents$1","ranges":[{"startOffset":343073,"endOffset":343490,"count":1},{"startOffset":343296,"endOffset":343484,"count":0}],"isBlockCoverage":true},{"functionName":"cancel$0","ranges":[{"startOffset":343506,"endOffset":343740,"count":0}],"isBlockCoverage":false},{"functionName":"_cancel$0","ranges":[{"startOffset":343757,"endOffset":344079,"count":0}],"isBlockCoverage":false},{"functionName":"_add$1","ranges":[{"startOffset":344093,"endOffset":344445,"count":1},{"startOffset":344310,"endOffset":344317,"count":0},{"startOffset":344368,"endOffset":344439,"count":0}],"isBlockCoverage":true},{"functionName":"_async$_addError$2","ranges":[{"startOffset":344471,"endOffset":344720,"count":0}],"isBlockCoverage":false},{"functionName":"_close$0","ranges":[{"startOffset":344736,"endOffset":344979,"count":0}],"isBlockCoverage":false},{"functionName":"_onPause$0","ranges":[{"startOffset":344997,"endOffset":345015,"count":0}],"isBlockCoverage":false},{"functionName":"_onResume$0","ranges":[{"startOffset":345034,"endOffset":345052,"count":0}],"isBlockCoverage":false},{"functionName":"_onCancel$0","ranges":[{"startOffset":345071,"endOffset":345103,"count":0}],"isBlockCoverage":false},{"functionName":"_addPending$1","ranges":[{"startOffset":345124,"endOffset":345687,"count":0}],"isBlockCoverage":false},{"functionName":"_sendData$1","ranges":[{"startOffset":345706,"endOffset":346096,"count":1}],"isBlockCoverage":true},{"functionName":"_sendError$2","ranges":[{"startOffset":346116,"endOffset":346631,"count":0}],"isBlockCoverage":false},{"functionName":"_sendDone$0","ranges":[{"startOffset":346650,"endOffset":346982,"count":0}],"isBlockCoverage":false},{"functionName":"_guardCallback$1","ranges":[{"startOffset":347006,"endOffset":347285,"count":1}],"isBlockCoverage":true},{"functionName":"_checkState$1","ranges":[{"startOffset":347306,"endOffset":348403,"count":1},{"startOffset":347416,"endOffset":347457,"count":0},{"startOffset":347459,"endOffset":347850,"count":0},{"startOffset":347932,"endOffset":347996,"count":0},{"startOffset":348099,"endOffset":348318,"count":0},{"startOffset":348345,"endOffset":348356,"count":0},{"startOffset":348366,"endOffset":348397,"count":0}],"isBlockCoverage":true},{"functionName":"set$_async$_onData","ranges":[{"startOffset":348429,"endOffset":348607,"count":1}],"isBlockCoverage":true},{"functionName":"set$_onDone","ranges":[{"startOffset":348626,"endOffset":348722,"count":1}],"isBlockCoverage":true},{"functionName":"set$_pending","ranges":[{"startOffset":348742,"endOffset":348928,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":349070,"endOffset":349703,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":349855,"endOffset":350105,"count":0}],"isBlockCoverage":false},{"functionName":"listen$4$cancelOnError$onDone$onError","ranges":[{"startOffset":350252,"endOffset":350638,"count":1}],"isBlockCoverage":true},{"functionName":"listen$1","ranges":[{"startOffset":350654,"endOffset":350761,"count":1}],"isBlockCoverage":true},{"functionName":"listen$3$onDone$onError","ranges":[{"startOffset":350792,"endOffset":350921,"count":1}],"isBlockCoverage":true},{"functionName":"listen$2$onDone","ranges":[{"startOffset":350944,"endOffset":351061,"count":1}],"isBlockCoverage":true},{"functionName":"set$next","ranges":[{"startOffset":351113,"endOffset":351203,"count":0}],"isBlockCoverage":false},{"functionName":"get$next","ranges":[{"startOffset":351219,"endOffset":351261,"count":0}],"isBlockCoverage":false},{"functionName":"perform$1","ranges":[{"startOffset":351313,"endOffset":351448,"count":0}],"isBlockCoverage":false},{"functionName":"perform$1","ranges":[{"startOffset":351501,"endOffset":351585,"count":0}],"isBlockCoverage":false},{"functionName":"$as_DelayedEvent","ranges":[{"startOffset":351609,"endOffset":351627,"count":0}],"isBlockCoverage":false},{"functionName":"perform$1","ranges":[{"startOffset":351679,"endOffset":351735,"count":0}],"isBlockCoverage":false},{"functionName":"get$next","ranges":[{"startOffset":351751,"endOffset":351783,"count":0}],"isBlockCoverage":false},{"functionName":"set$next","ranges":[{"startOffset":351799,"endOffset":351889,"count":0}],"isBlockCoverage":false},{"functionName":"$as_DelayedEvent","ranges":[{"startOffset":351938,"endOffset":351956,"count":0}],"isBlockCoverage":false},{"functionName":"schedule$1","ranges":[{"startOffset":352011,"endOffset":352371,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":352439,"endOffset":352917,"count":0}],"isBlockCoverage":false},{"functionName":"add$1","ranges":[{"startOffset":353038,"endOffset":353300,"count":0}],"isBlockCoverage":false},{"functionName":"_schedule$0","ranges":[{"startOffset":353365,"endOffset":353539,"count":0}],"isBlockCoverage":false},{"functionName":"cancel$0","ranges":[{"startOffset":353555,"endOffset":353615,"count":0}],"isBlockCoverage":false},{"functionName":"_sendDone$0","ranges":[{"startOffset":353634,"endOffset":353880,"count":0}],"isBlockCoverage":false},{"functionName":"listen$4$cancelOnError$onDone$onError","ranges":[{"startOffset":354026,"endOffset":354367,"count":0}],"isBlockCoverage":false},{"functionName":"listen$1","ranges":[{"startOffset":354383,"endOffset":354490,"count":0}],"isBlockCoverage":false},{"functionName":"listen$3$onDone$onError","ranges":[{"startOffset":354521,"endOffset":354650,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":354727,"endOffset":354776,"count":0}],"isBlockCoverage":false},{"functionName":"handleUncaughtError$3","ranges":[{"startOffset":355050,"endOffset":355408,"count":0}],"isBlockCoverage":false},{"functionName":"get$_delegate","ranges":[{"startOffset":355523,"endOffset":355705,"count":0}],"isBlockCoverage":false},{"functionName":"get$errorZone","ranges":[{"startOffset":355726,"endOffset":355789,"count":1}],"isBlockCoverage":true},{"functionName":"runGuarded$1","ranges":[{"startOffset":355809,"endOffset":356114,"count":1},{"startOffset":355949,"endOffset":356108,"count":0}],"isBlockCoverage":true},{"functionName":"runUnaryGuarded$1$2","ranges":[{"startOffset":356141,"endOffset":356526,"count":1},{"startOffset":356361,"endOffset":356520,"count":0}],"isBlockCoverage":true},{"functionName":"runBinaryGuarded$2$3","ranges":[{"startOffset":356554,"endOffset":357013,"count":0}],"isBlockCoverage":false},{"functionName":"bindCallback$1$1","ranges":[{"startOffset":357037,"endOffset":357198,"count":0}],"isBlockCoverage":false},{"functionName":"bindUnaryCallback$2$1","ranges":[{"startOffset":357227,"endOffset":357422,"count":1}],"isBlockCoverage":true},{"functionName":"bindCallbackGuarded$1","ranges":[{"startOffset":357451,"endOffset":357611,"count":1}],"isBlockCoverage":true},{"functionName":"bindUnaryCallbackGuarded$1$1","ranges":[{"startOffset":357647,"endOffset":357841,"count":1}],"isBlockCoverage":true},{"functionName":"$index","ranges":[{"startOffset":357855,"endOffset":358169,"count":0}],"isBlockCoverage":false},{"functionName":"handleUncaughtError$2","ranges":[{"startOffset":358198,"endOffset":358557,"count":0}],"isBlockCoverage":false},{"functionName":"fork$2$specification$zoneValues","ranges":[{"startOffset":358596,"endOffset":358897,"count":0}],"isBlockCoverage":false},{"functionName":"run$1$1","ranges":[{"startOffset":358912,"endOffset":359343,"count":1}],"isBlockCoverage":true},{"functionName":"runUnary$2$2","ranges":[{"startOffset":359363,"endOffset":359898,"count":1}],"isBlockCoverage":true},{"functionName":"runBinary$3$3","ranges":[{"startOffset":359919,"endOffset":360544,"count":0}],"isBlockCoverage":false},{"functionName":"registerCallback$1$1","ranges":[{"startOffset":360572,"endOffset":361053,"count":1}],"isBlockCoverage":true},{"functionName":"registerUnaryCallback$2$1","ranges":[{"startOffset":361086,"endOffset":361624,"count":1}],"isBlockCoverage":true},{"functionName":"registerBinaryCallback$3$1","ranges":[{"startOffset":361658,"endOffset":362225,"count":1}],"isBlockCoverage":true},{"functionName":"errorCallback$2","ranges":[{"startOffset":362248,"endOffset":362670,"count":0}],"isBlockCoverage":false},{"functionName":"scheduleMicrotask$1","ranges":[{"startOffset":362697,"endOffset":363013,"count":1}],"isBlockCoverage":true},{"functionName":"createPeriodicTimer$2","ranges":[{"startOffset":363042,"endOffset":363397,"count":1}],"isBlockCoverage":true},{"functionName":"print$1","ranges":[{"startOffset":363412,"endOffset":363675,"count":0}],"isBlockCoverage":false},{"functionName":"set$_run","ranges":[{"startOffset":363691,"endOffset":363808,"count":1}],"isBlockCoverage":true},{"functionName":"set$_runUnary","ranges":[{"startOffset":363829,"endOffset":363961,"count":1}],"isBlockCoverage":true},{"functionName":"set$_runBinary","ranges":[{"startOffset":363983,"endOffset":364118,"count":1}],"isBlockCoverage":true},{"functionName":"set$_registerCallback","ranges":[{"startOffset":364147,"endOffset":364303,"count":1}],"isBlockCoverage":true},{"functionName":"set$_registerUnaryCallback","ranges":[{"startOffset":364337,"endOffset":364508,"count":1}],"isBlockCoverage":true},{"functionName":"set$_registerBinaryCallback","ranges":[{"startOffset":364543,"endOffset":364717,"count":1}],"isBlockCoverage":true},{"functionName":"set$_errorCallback","ranges":[{"startOffset":364743,"endOffset":364972,"count":1}],"isBlockCoverage":true},{"functionName":"set$_scheduleMicrotask","ranges":[{"startOffset":365002,"endOffset":365229,"count":1}],"isBlockCoverage":true},{"functionName":"set$_createTimer","ranges":[{"startOffset":365253,"endOffset":365479,"count":1}],"isBlockCoverage":true},{"functionName":"set$_createPeriodicTimer","ranges":[{"startOffset":365511,"endOffset":365778,"count":1}],"isBlockCoverage":true},{"functionName":"set$_print","ranges":[{"startOffset":365796,"endOffset":365977,"count":1}],"isBlockCoverage":true},{"functionName":"set$_fork","ranges":[{"startOffset":365994,"endOffset":366199,"count":1}],"isBlockCoverage":true},{"functionName":"set$_handleUncaughtError","ranges":[{"startOffset":366231,"endOffset":366468,"count":1}],"isBlockCoverage":true},{"functionName":"get$_run","ranges":[{"startOffset":366484,"endOffset":366526,"count":0}],"isBlockCoverage":false},{"functionName":"get$_runUnary","ranges":[{"startOffset":366547,"endOffset":366594,"count":0}],"isBlockCoverage":false},{"functionName":"get$_runBinary","ranges":[{"startOffset":366616,"endOffset":366664,"count":0}],"isBlockCoverage":false},{"functionName":"get$_registerCallback","ranges":[{"startOffset":366693,"endOffset":366748,"count":0}],"isBlockCoverage":false},{"functionName":"get$_registerUnaryCallback","ranges":[{"startOffset":366782,"endOffset":366842,"count":0}],"isBlockCoverage":false},{"functionName":"get$_registerBinaryCallback","ranges":[{"startOffset":366877,"endOffset":366938,"count":0}],"isBlockCoverage":false},{"functionName":"get$_errorCallback","ranges":[{"startOffset":366964,"endOffset":367016,"count":0}],"isBlockCoverage":false},{"functionName":"get$_scheduleMicrotask","ranges":[{"startOffset":367046,"endOffset":367102,"count":0}],"isBlockCoverage":false},{"functionName":"get$_createTimer","ranges":[{"startOffset":367126,"endOffset":367176,"count":0}],"isBlockCoverage":false},{"functionName":"get$_createPeriodicTimer","ranges":[{"startOffset":367208,"endOffset":367266,"count":0}],"isBlockCoverage":false},{"functionName":"get$_print","ranges":[{"startOffset":367284,"endOffset":367328,"count":0}],"isBlockCoverage":false},{"functionName":"get$_fork","ranges":[{"startOffset":367345,"endOffset":367388,"count":0}],"isBlockCoverage":false},{"functionName":"get$_handleUncaughtError","ranges":[{"startOffset":367420,"endOffset":367478,"count":0}],"isBlockCoverage":false},{"functionName":"get$parent","ranges":[{"startOffset":367496,"endOffset":367548,"count":0}],"isBlockCoverage":false},{"functionName":"get$_async$_map","ranges":[{"startOffset":367571,"endOffset":367620,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":367689,"endOffset":367765,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":367783,"endOffset":367838,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":367912,"endOffset":368062,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":368080,"endOffset":368151,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":368227,"endOffset":368300,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":368449,"endOffset":368598,"count":1}],"isBlockCoverage":true},{"functionName":"$signature","ranges":[{"startOffset":368616,"endOffset":368683,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":368752,"endOffset":369158,"count":0}],"isBlockCoverage":false},{"functionName":"get$_run","ranges":[{"startOffset":369225,"endOffset":369292,"count":1}],"isBlockCoverage":true},{"functionName":"get$_runUnary","ranges":[{"startOffset":369313,"endOffset":369385,"count":1}],"isBlockCoverage":true},{"functionName":"get$_runBinary","ranges":[{"startOffset":369407,"endOffset":369480,"count":1}],"isBlockCoverage":true},{"functionName":"get$_registerCallback","ranges":[{"startOffset":369509,"endOffset":369589,"count":1}],"isBlockCoverage":true},{"functionName":"get$_registerUnaryCallback","ranges":[{"startOffset":369623,"endOffset":369675,"count":1}],"isBlockCoverage":true},{"functionName":"get$_registerBinaryCallback","ranges":[{"startOffset":369710,"endOffset":369762,"count":1}],"isBlockCoverage":true},{"functionName":"get$_errorCallback","ranges":[{"startOffset":369788,"endOffset":369865,"count":1}],"isBlockCoverage":true},{"functionName":"get$_scheduleMicrotask","ranges":[{"startOffset":369895,"endOffset":369976,"count":1}],"isBlockCoverage":true},{"functionName":"get$_createTimer","ranges":[{"startOffset":370000,"endOffset":370075,"count":1}],"isBlockCoverage":true},{"functionName":"get$_createPeriodicTimer","ranges":[{"startOffset":370107,"endOffset":370159,"count":1}],"isBlockCoverage":true},{"functionName":"get$_print","ranges":[{"startOffset":370177,"endOffset":370246,"count":1}],"isBlockCoverage":true},{"functionName":"get$_fork","ranges":[{"startOffset":370263,"endOffset":370331,"count":1}],"isBlockCoverage":true},{"functionName":"get$_handleUncaughtError","ranges":[{"startOffset":370363,"endOffset":370415,"count":0}],"isBlockCoverage":false},{"functionName":"get$parent","ranges":[{"startOffset":370433,"endOffset":370466,"count":1}],"isBlockCoverage":true},{"functionName":"get$_async$_map","ranges":[{"startOffset":370489,"endOffset":370549,"count":1}],"isBlockCoverage":true},{"functionName":"get$_delegate","ranges":[{"startOffset":370570,"endOffset":370764,"count":0}],"isBlockCoverage":false},{"functionName":"get$errorZone","ranges":[{"startOffset":370785,"endOffset":370822,"count":1}],"isBlockCoverage":true},{"functionName":"runGuarded$1","ranges":[{"startOffset":370842,"endOffset":371321,"count":0}],"isBlockCoverage":false},{"functionName":"runUnaryGuarded$1$2","ranges":[{"startOffset":371348,"endOffset":371910,"count":0}],"isBlockCoverage":false},{"functionName":"runBinaryGuarded$2$3","ranges":[{"startOffset":371938,"endOffset":372581,"count":0}],"isBlockCoverage":false},{"functionName":"bindCallback$1$1","ranges":[{"startOffset":372605,"endOffset":372733,"count":0}],"isBlockCoverage":false},{"functionName":"bindCallbackGuarded$1","ranges":[{"startOffset":372762,"endOffset":372889,"count":0}],"isBlockCoverage":false},{"functionName":"bindUnaryCallbackGuarded$1$1","ranges":[{"startOffset":372925,"endOffset":373077,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":373091,"endOffset":373129,"count":0}],"isBlockCoverage":false},{"functionName":"handleUncaughtError$2","ranges":[{"startOffset":373158,"endOffset":373305,"count":0}],"isBlockCoverage":false},{"functionName":"fork$2$specification$zoneValues","ranges":[{"startOffset":373344,"endOffset":373458,"count":1}],"isBlockCoverage":true},{"functionName":"run$1$1","ranges":[{"startOffset":373473,"endOffset":373668,"count":0}],"isBlockCoverage":false},{"functionName":"runUnary$2$2","ranges":[{"startOffset":373688,"endOffset":373966,"count":0}],"isBlockCoverage":false},{"functionName":"runBinary$3$3","ranges":[{"startOffset":373987,"endOffset":374346,"count":0}],"isBlockCoverage":false},{"functionName":"registerCallback$1$1","ranges":[{"startOffset":374374,"endOffset":374454,"count":0}],"isBlockCoverage":false},{"functionName":"registerUnaryCallback$2$1","ranges":[{"startOffset":374487,"endOffset":374583,"count":0}],"isBlockCoverage":false},{"functionName":"registerBinaryCallback$3$1","ranges":[{"startOffset":374617,"endOffset":374721,"count":0}],"isBlockCoverage":false},{"functionName":"errorCallback$2","ranges":[{"startOffset":374744,"endOffset":374793,"count":0}],"isBlockCoverage":false},{"functionName":"scheduleMicrotask$1","ranges":[{"startOffset":374820,"endOffset":374933,"count":0}],"isBlockCoverage":false},{"functionName":"createPeriodicTimer$2","ranges":[{"startOffset":374962,"endOffset":375105,"count":0}],"isBlockCoverage":false},{"functionName":"print$1","ranges":[{"startOffset":375120,"endOffset":375172,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":375239,"endOffset":375306,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":375324,"endOffset":375379,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":375453,"endOffset":375517,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":375664,"endOffset":375804,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":375822,"endOffset":375889,"count":0}],"isBlockCoverage":false},{"functionName":"call$5","ranges":[{"startOffset":375942,"endOffset":376743,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":376812,"endOffset":376870,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":376889,"endOffset":376953,"count":0}],"isBlockCoverage":false},{"functionName":"get$keys","ranges":[{"startOffset":376969,"endOffset":377070,"count":0}],"isBlockCoverage":false},{"functionName":"containsKey$1","ranges":[{"startOffset":377091,"endOffset":377529,"count":0}],"isBlockCoverage":false},{"functionName":"_containsKey$1","ranges":[{"startOffset":377551,"endOffset":377737,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":377751,"endOffset":378258,"count":0}],"isBlockCoverage":false},{"functionName":"_get$1","ranges":[{"startOffset":378272,"endOffset":378549,"count":0}],"isBlockCoverage":false},{"functionName":"$indexSet","ranges":[{"startOffset":378566,"endOffset":379433,"count":0}],"isBlockCoverage":false},{"functionName":"_set$2","ranges":[{"startOffset":379447,"endOffset":380330,"count":0}],"isBlockCoverage":false},{"functionName":"forEach$1","ranges":[{"startOffset":380347,"endOffset":380898,"count":0}],"isBlockCoverage":false},{"functionName":"_collection$_computeKeys$0","ranges":[{"startOffset":380932,"endOffset":382221,"count":0}],"isBlockCoverage":false},{"functionName":"_collection$_addHashTableEntry$3","ranges":[{"startOffset":382261,"endOffset":382617,"count":0}],"isBlockCoverage":false},{"functionName":"_computeHashCode$1","ranges":[{"startOffset":382643,"endOffset":382712,"count":0}],"isBlockCoverage":false},{"functionName":"_getBucket$2","ranges":[{"startOffset":382732,"endOffset":382810,"count":0}],"isBlockCoverage":false},{"functionName":"_findBucketIndex$2","ranges":[{"startOffset":382836,"endOffset":383075,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":383135,"endOffset":383198,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":383217,"endOffset":383286,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":383306,"endOffset":383438,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":383499,"endOffset":383557,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":383575,"endOffset":384056,"count":0}],"isBlockCoverage":false},{"functionName":"set$_collection$_current","ranges":[{"startOffset":384088,"endOffset":384223,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":384300,"endOffset":384484,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":384502,"endOffset":384560,"count":0}],"isBlockCoverage":false},{"functionName":"contains$1","ranges":[{"startOffset":384578,"endOffset":385195,"count":1},{"startOffset":384662,"endOffset":384687,"count":0},{"startOffset":384689,"endOffset":384885,"count":0},{"startOffset":385049,"endOffset":385189,"count":0}],"isBlockCoverage":true},{"functionName":"_contains$1","ranges":[{"startOffset":385214,"endOffset":385409,"count":0}],"isBlockCoverage":false},{"functionName":"add$1","ranges":[{"startOffset":385422,"endOffset":386268,"count":0}],"isBlockCoverage":false},{"functionName":"_collection$_add$1","ranges":[{"startOffset":386294,"endOffset":386943,"count":0}],"isBlockCoverage":false},{"functionName":"remove$1","ranges":[{"startOffset":386959,"endOffset":387360,"count":1},{"startOffset":387018,"endOffset":387043,"count":0},{"startOffset":387053,"endOffset":387136,"count":0},{"startOffset":387304,"endOffset":387354,"count":0}],"isBlockCoverage":true},{"functionName":"_remove$1","ranges":[{"startOffset":387377,"endOffset":387746,"count":0}],"isBlockCoverage":false},{"functionName":"_collection$_addHashTableEntry$2","ranges":[{"startOffset":387786,"endOffset":388089,"count":0}],"isBlockCoverage":false},{"functionName":"_collection$_removeHashTableEntry$2","ranges":[{"startOffset":388132,"endOffset":388443,"count":1},{"startOffset":388221,"endOffset":388442,"count":0}],"isBlockCoverage":true},{"functionName":"_collection$_modified$0","ranges":[{"startOffset":388474,"endOffset":388582,"count":0}],"isBlockCoverage":false},{"functionName":"_collection$_newLinkedCell$1","ranges":[{"startOffset":388618,"endOffset":389176,"count":0}],"isBlockCoverage":false},{"functionName":"_collection$_unlinkCell$1","ranges":[{"startOffset":389209,"endOffset":389658,"count":0}],"isBlockCoverage":false},{"functionName":"_computeHashCode$1","ranges":[{"startOffset":389684,"endOffset":389761,"count":0}],"isBlockCoverage":false},{"functionName":"_getBucket$2","ranges":[{"startOffset":389781,"endOffset":389867,"count":0}],"isBlockCoverage":false},{"functionName":"_findBucketIndex$2","ranges":[{"startOffset":389893,"endOffset":390203,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":390306,"endOffset":390364,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":390382,"endOffset":390971,"count":0}],"isBlockCoverage":false},{"functionName":"set$_collection$_current","ranges":[{"startOffset":391003,"endOffset":391138,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":391329,"endOffset":391499,"count":0}],"isBlockCoverage":false},{"functionName":"elementAt$1","ranges":[{"startOffset":391518,"endOffset":391594,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":391613,"endOffset":391685,"count":0}],"isBlockCoverage":false},{"functionName":"get$isNotEmpty","ranges":[{"startOffset":391707,"endOffset":391775,"count":0}],"isBlockCoverage":false},{"functionName":"fillRange$3","ranges":[{"startOffset":391794,"endOffset":392116,"count":1}],"isBlockCoverage":true},{"functionName":"toString$0","ranges":[{"startOffset":392134,"endOffset":392230,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":392322,"endOffset":392591,"count":0}],"isBlockCoverage":false},{"functionName":"forEach$1","ranges":[{"startOffset":392659,"endOffset":393030,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":393048,"endOffset":393131,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":393150,"endOffset":393234,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":393252,"endOffset":393313,"count":0}],"isBlockCoverage":false},{"functionName":"$indexSet","ranges":[{"startOffset":393389,"endOffset":393708,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":393752,"endOffset":393815,"count":1}],"isBlockCoverage":true},{"functionName":"$indexSet","ranges":[{"startOffset":393832,"endOffset":394035,"count":0}],"isBlockCoverage":false},{"functionName":"forEach$1","ranges":[{"startOffset":394052,"endOffset":394236,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":394255,"endOffset":394333,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":394351,"endOffset":394428,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":394446,"endOffset":394504,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":394608,"endOffset":394693,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":394926,"endOffset":395244,"count":1},{"startOffset":395025,"endOffset":395058,"count":0},{"startOffset":395107,"endOffset":395114,"count":0},{"startOffset":395221,"endOffset":395229,"count":0}],"isBlockCoverage":true},{"functionName":"get$length","ranges":[{"startOffset":395262,"endOffset":395383,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":395402,"endOffset":395463,"count":0}],"isBlockCoverage":false},{"functionName":"get$keys","ranges":[{"startOffset":395479,"endOffset":395703,"count":0}],"isBlockCoverage":false},{"functionName":"$indexSet","ranges":[{"startOffset":395720,"endOffset":396180,"count":0}],"isBlockCoverage":false},{"functionName":"containsKey$1","ranges":[{"startOffset":396201,"endOffset":396375,"count":0}],"isBlockCoverage":false},{"functionName":"forEach$1","ranges":[{"startOffset":396392,"endOffset":397032,"count":1},{"startOffset":396553,"endOffset":396587,"count":0},{"startOffset":396958,"endOffset":397018,"count":0}],"isBlockCoverage":true},{"functionName":"_computeKeys$0","ranges":[{"startOffset":397054,"endOffset":397276,"count":1}],"isBlockCoverage":true},{"functionName":"_upgrade$0","ranges":[{"startOffset":397294,"endOffset":397882,"count":0}],"isBlockCoverage":false},{"functionName":"_process$1","ranges":[{"startOffset":397900,"endOffset":398131,"count":1},{"startOffset":398012,"endOffset":398019,"count":0}],"isBlockCoverage":true},{"functionName":"$asMapMixin","ranges":[{"startOffset":398150,"endOffset":398199,"count":0}],"isBlockCoverage":false},{"functionName":"$asMap","ranges":[{"startOffset":398213,"endOffset":398262,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":398322,"endOffset":398411,"count":0}],"isBlockCoverage":false},{"functionName":"elementAt$1","ranges":[{"startOffset":398430,"endOffset":398755,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":398775,"endOffset":399090,"count":0}],"isBlockCoverage":false},{"functionName":"$asEfficientLengthIterable","ranges":[{"startOffset":399124,"endOffset":399167,"count":0}],"isBlockCoverage":false},{"functionName":"$asListIterable","ranges":[{"startOffset":399190,"endOffset":399233,"count":0}],"isBlockCoverage":false},{"functionName":"$asIterable","ranges":[{"startOffset":399252,"endOffset":399295,"count":0}],"isBlockCoverage":false},{"functionName":"encode$1","ranges":[{"startOffset":399344,"endOffset":399419,"count":0}],"isBlockCoverage":false},{"functionName":"convert$1","ranges":[{"startOffset":399480,"endOffset":400124,"count":0}],"isBlockCoverage":false},{"functionName":"$asStreamTransformer","ranges":[{"startOffset":400152,"endOffset":400212,"count":0}],"isBlockCoverage":false},{"functionName":"$asConverter","ranges":[{"startOffset":400232,"endOffset":400292,"count":0}],"isBlockCoverage":false},{"functionName":"normalize$3","ranges":[{"startOffset":400378,"endOffset":404030,"count":0}],"isBlockCoverage":false},{"functionName":"$asCodec","ranges":[{"startOffset":404046,"endOffset":404106,"count":0}],"isBlockCoverage":false},{"functionName":"$asStreamTransformer","ranges":[{"startOffset":404170,"endOffset":404230,"count":0}],"isBlockCoverage":false},{"functionName":"$asConverter","ranges":[{"startOffset":404250,"endOffset":404310,"count":0}],"isBlockCoverage":false},{"functionName":"$asCodec","ranges":[{"startOffset":404386,"endOffset":404437,"count":0}],"isBlockCoverage":false},{"functionName":"$asCodec","ranges":[{"startOffset":404514,"endOffset":404574,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":404641,"endOffset":404894,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":404950,"endOffset":405016,"count":0}],"isBlockCoverage":false},{"functionName":"decode$2$reviver","ranges":[{"startOffset":405072,"endOffset":405191,"count":1}],"isBlockCoverage":true},{"functionName":"encode$2$toEncodable","ranges":[{"startOffset":405219,"endOffset":405389,"count":1}],"isBlockCoverage":true},{"functionName":"get$encoder","ranges":[{"startOffset":405408,"endOffset":405464,"count":1}],"isBlockCoverage":true},{"functionName":"get$decoder","ranges":[{"startOffset":405483,"endOffset":405534,"count":1}],"isBlockCoverage":true},{"functionName":"$asCodec","ranges":[{"startOffset":405550,"endOffset":405603,"count":0}],"isBlockCoverage":false},{"functionName":"$asStreamTransformer","ranges":[{"startOffset":405665,"endOffset":405718,"count":0}],"isBlockCoverage":false},{"functionName":"$asConverter","ranges":[{"startOffset":405738,"endOffset":405791,"count":0}],"isBlockCoverage":false},{"functionName":"$asStreamTransformer","ranges":[{"startOffset":405853,"endOffset":405906,"count":0}],"isBlockCoverage":false},{"functionName":"$asConverter","ranges":[{"startOffset":405926,"endOffset":405979,"count":0}],"isBlockCoverage":false},{"functionName":"writeStringContent$1","ranges":[{"startOffset":406046,"endOffset":407693,"count":1},{"startOffset":406329,"endOffset":407300,"count":0},{"startOffset":407346,"endOffset":407538,"count":0},{"startOffset":407601,"endOffset":407687,"count":0}],"isBlockCoverage":true},{"functionName":"_checkCycle$1","ranges":[{"startOffset":407714,"endOffset":408027,"count":1},{"startOffset":407871,"endOffset":407883,"count":0},{"startOffset":407911,"endOffset":407970,"count":0}],"isBlockCoverage":true},{"functionName":"writeObject$1","ranges":[{"startOffset":408048,"endOffset":408754,"count":1},{"startOffset":408163,"endOffset":408748,"count":0}],"isBlockCoverage":true},{"functionName":"writeJsonValue$1","ranges":[{"startOffset":408778,"endOffset":410030,"count":1},{"startOffset":408901,"endOffset":408914,"count":0},{"startOffset":409006,"endOffset":409072,"count":0},{"startOffset":409100,"endOffset":409167,"count":0},{"startOffset":409655,"endOffset":409678,"count":0},{"startOffset":409908,"endOffset":409931,"count":0},{"startOffset":409987,"endOffset":410016,"count":0}],"isBlockCoverage":true},{"functionName":"writeList$1","ranges":[{"startOffset":410049,"endOffset":410429,"count":1}],"isBlockCoverage":true},{"functionName":"writeMap$1","ranges":[{"startOffset":410447,"endOffset":411384,"count":1},{"startOffset":410929,"endOffset":410942,"count":0},{"startOffset":411241,"endOffset":411274,"count":0}],"isBlockCoverage":true},{"functionName":"call$2","ranges":[{"startOffset":411454,"endOffset":411738,"count":1},{"startOffset":411538,"endOffset":411572,"count":0}],"isBlockCoverage":true},{"functionName":"get$_partialResult","ranges":[{"startOffset":411829,"endOffset":411944,"count":0}],"isBlockCoverage":false},{"functionName":"writeNumber$1","ranges":[{"startOffset":411965,"endOffset":412063,"count":1}],"isBlockCoverage":true},{"functionName":"writeString$1","ranges":[{"startOffset":412084,"endOffset":412151,"count":1}],"isBlockCoverage":true},{"functionName":"writeStringSlice$3","ranges":[{"startOffset":412177,"endOffset":412285,"count":0}],"isBlockCoverage":false},{"functionName":"writeCharCode$1","ranges":[{"startOffset":412308,"endOffset":412387,"count":0}],"isBlockCoverage":false},{"functionName":"get$encoder","ranges":[{"startOffset":412438,"endOffset":412486,"count":0}],"isBlockCoverage":false},{"functionName":"convert$1","ranges":[{"startOffset":412537,"endOffset":413070,"count":0}],"isBlockCoverage":false},{"functionName":"$asStreamTransformer","ranges":[{"startOffset":413098,"endOffset":413158,"count":0}],"isBlockCoverage":false},{"functionName":"$asConverter","ranges":[{"startOffset":413178,"endOffset":413238,"count":0}],"isBlockCoverage":false},{"functionName":"_writeSurrogate$2","ranges":[{"startOffset":413298,"endOffset":414650,"count":0}],"isBlockCoverage":false},{"functionName":"_fillBuffer$3","ranges":[{"startOffset":414671,"endOffset":416478,"count":0}],"isBlockCoverage":false},{"functionName":"convert$1","ranges":[{"startOffset":416529,"endOffset":417119,"count":1},{"startOffset":416771,"endOffset":416785,"count":0},{"startOffset":417103,"endOffset":417107,"count":0}],"isBlockCoverage":true},{"functionName":"$asStreamTransformer","ranges":[{"startOffset":417147,"endOffset":417207,"count":0}],"isBlockCoverage":false},{"functionName":"$asConverter","ranges":[{"startOffset":417227,"endOffset":417287,"count":0}],"isBlockCoverage":false},{"functionName":"flush$2","ranges":[{"startOffset":417337,"endOffset":417609,"count":1},{"startOffset":417475,"endOffset":417603,"count":0}],"isBlockCoverage":true},{"functionName":"convert$3","ranges":[{"startOffset":417626,"endOffset":421538,"count":1},{"startOffset":418311,"endOffset":419809,"count":0},{"startOffset":420150,"endOffset":421331,"count":0},{"startOffset":421410,"endOffset":421532,"count":0}],"isBlockCoverage":true},{"functionName":"call$2","ranges":[{"startOffset":421610,"endOffset":421735,"count":1}],"isBlockCoverage":true},{"functionName":"call$2","ranges":[{"startOffset":421826,"endOffset":422161,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":422248,"endOffset":422415,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":422435,"endOffset":422566,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":422584,"endOffset":423195,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":423264,"endOffset":423417,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":423437,"endOffset":423515,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":423533,"endOffset":424155,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":424219,"endOffset":424494,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":424578,"endOffset":424661,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":424763,"endOffset":424813,"count":0}],"isBlockCoverage":false},{"functionName":"get$_errorName","ranges":[{"startOffset":424871,"endOffset":424955,"count":0}],"isBlockCoverage":false},{"functionName":"get$_errorExplanation","ranges":[{"startOffset":424984,"endOffset":425019,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":425037,"endOffset":425551,"count":0}],"isBlockCoverage":false},{"functionName":"get$_errorName","ranges":[{"startOffset":425606,"endOffset":425651,"count":0}],"isBlockCoverage":false},{"functionName":"get$_errorExplanation","ranges":[{"startOffset":425680,"endOffset":426274,"count":0}],"isBlockCoverage":false},{"functionName":"get$_errorName","ranges":[{"startOffset":426329,"endOffset":426374,"count":0}],"isBlockCoverage":false},{"functionName":"get$_errorExplanation","ranges":[{"startOffset":426403,"endOffset":426799,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":426817,"endOffset":426869,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":426927,"endOffset":427772,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":427829,"endOffset":427903,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":427962,"endOffset":428088,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":428139,"endOffset":428201,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":428269,"endOffset":428498,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":428555,"endOffset":428604,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":428680,"endOffset":428730,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":428813,"endOffset":429012,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":429063,"endOffset":429125,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":429181,"endOffset":431814,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":431916,"endOffset":432069,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":432088,"endOffset":432159,"count":0}],"isBlockCoverage":false},{"functionName":"skipWhile$1","ranges":[{"startOffset":432178,"endOffset":432378,"count":0}],"isBlockCoverage":false},{"functionName":"get$first","ranges":[{"startOffset":432395,"endOffset":432580,"count":0}],"isBlockCoverage":false},{"functionName":"get$last","ranges":[{"startOffset":432596,"endOffset":432864,"count":0}],"isBlockCoverage":false},{"functionName":"elementAt$1","ranges":[{"startOffset":432883,"endOffset":433294,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":433312,"endOffset":433398,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":433568,"endOffset":433650,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":433668,"endOffset":433708,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":433808,"endOffset":433863,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":433883,"endOffset":433950,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":433968,"endOffset":434059,"count":0}],"isBlockCoverage":false},{"functionName":"noSuchMethod$1","ranges":[{"startOffset":434081,"endOffset":434328,"count":0}],"isBlockCoverage":false},{"functionName":"toString","ranges":[{"startOffset":434344,"endOffset":434398,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":434513,"endOffset":434563,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":434678,"endOffset":434733,"count":0}],"isBlockCoverage":false},{"functionName":"write$1","ranges":[{"startOffset":434748,"endOffset":434803,"count":1}],"isBlockCoverage":true},{"functionName":"writeCharCode$1","ranges":[{"startOffset":434826,"endOffset":434919,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":434937,"endOffset":435033,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":435148,"endOffset":435892,"count":1},{"startOffset":435410,"endOffset":435547,"count":0}],"isBlockCoverage":true},{"functionName":"call$2","ranges":[{"startOffset":435976,"endOffset":436109,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":436192,"endOffset":436325,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":436339,"endOffset":436397,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":436483,"endOffset":436948,"count":0}],"isBlockCoverage":false},{"functionName":"get$userInfo","ranges":[{"startOffset":437015,"endOffset":437062,"count":0}],"isBlockCoverage":false},{"functionName":"get$host","ranges":[{"startOffset":437078,"endOffset":437303,"count":0}],"isBlockCoverage":false},{"functionName":"get$port","ranges":[{"startOffset":437319,"endOffset":437453,"count":0}],"isBlockCoverage":false},{"functionName":"get$query","ranges":[{"startOffset":437470,"endOffset":437551,"count":0}],"isBlockCoverage":false},{"functionName":"get$fragment","ranges":[{"startOffset":437571,"endOffset":437655,"count":0}],"isBlockCoverage":false},{"functionName":"get$pathSegments","ranges":[{"startOffset":437679,"endOffset":438447,"count":0}],"isBlockCoverage":false},{"functionName":"get$queryParameters","ranges":[{"startOffset":438474,"endOffset":438764,"count":1},{"startOffset":438691,"endOffset":438695,"count":0}],"isBlockCoverage":true},{"functionName":"_mergePaths$2","ranges":[{"startOffset":438785,"endOffset":439869,"count":0}],"isBlockCoverage":false},{"functionName":"resolve$1","ranges":[{"startOffset":439886,"endOffset":439969,"count":0}],"isBlockCoverage":false},{"functionName":"resolveUri$1","ranges":[{"startOffset":439989,"endOffset":442823,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasAuthority","ranges":[{"startOffset":442847,"endOffset":442898,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasPort","ranges":[{"startOffset":442917,"endOffset":442968,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasQuery","ranges":[{"startOffset":442988,"endOffset":443040,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasFragment","ranges":[{"startOffset":443063,"endOffset":443118,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasAbsolutePath","ranges":[{"startOffset":443145,"endOffset":443210,"count":0}],"isBlockCoverage":false},{"functionName":"toFilePath$0","ranges":[{"startOffset":443230,"endOffset":444436,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":444454,"endOffset":445288,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":445299,"endOffset":446881,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":446901,"endOffset":447105,"count":0}],"isBlockCoverage":false},{"functionName":"set$_pathSegments","ranges":[{"startOffset":447130,"endOffset":447254,"count":0}],"isBlockCoverage":false},{"functionName":"set$_queryParameters","ranges":[{"startOffset":447282,"endOffset":447436,"count":1}],"isBlockCoverage":true},{"functionName":"get$scheme","ranges":[{"startOffset":447469,"endOffset":447513,"count":0}],"isBlockCoverage":false},{"functionName":"get$path","ranges":[{"startOffset":447529,"endOffset":447579,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":447643,"endOffset":447836,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":447944,"endOffset":448269,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":448348,"endOffset":448460,"count":0}],"isBlockCoverage":false},{"functionName":"get$uri","ranges":[{"startOffset":448525,"endOffset":449212,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":449230,"endOffset":449434,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":449492,"endOffset":449544,"count":1}],"isBlockCoverage":true},{"functionName":"call$2","ranges":[{"startOffset":449620,"endOffset":449847,"count":1},{"startOffset":449723,"endOffset":449749,"count":0}],"isBlockCoverage":true},{"functionName":"call$3","ranges":[{"startOffset":449926,"endOffset":450216,"count":1},{"startOffset":450142,"endOffset":450169,"count":0}],"isBlockCoverage":true},{"functionName":"call$3","ranges":[{"startOffset":450275,"endOffset":450601,"count":1},{"startOffset":450527,"endOffset":450554,"count":0}],"isBlockCoverage":true},{"functionName":"get$hasAuthority","ranges":[{"startOffset":450658,"endOffset":450710,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasPort","ranges":[{"startOffset":450729,"endOffset":451079,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasQuery","ranges":[{"startOffset":451099,"endOffset":451337,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasFragment","ranges":[{"startOffset":451360,"endOffset":451538,"count":0}],"isBlockCoverage":false},{"functionName":"get$_isFile","ranges":[{"startOffset":451557,"endOffset":451650,"count":0}],"isBlockCoverage":false},{"functionName":"get$_isHttp","ranges":[{"startOffset":451669,"endOffset":451762,"count":0}],"isBlockCoverage":false},{"functionName":"get$_isHttps","ranges":[{"startOffset":451782,"endOffset":451876,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasAbsolutePath","ranges":[{"startOffset":451903,"endOffset":451985,"count":0}],"isBlockCoverage":false},{"functionName":"get$scheme","ranges":[{"startOffset":452003,"endOffset":452773,"count":0}],"isBlockCoverage":false},{"functionName":"get$userInfo","ranges":[{"startOffset":452793,"endOffset":453028,"count":0}],"isBlockCoverage":false},{"functionName":"get$host","ranges":[{"startOffset":453044,"endOffset":453171,"count":0}],"isBlockCoverage":false},{"functionName":"get$port","ranges":[{"startOffset":453187,"endOffset":453563,"count":0}],"isBlockCoverage":false},{"functionName":"get$path","ranges":[{"startOffset":453579,"endOffset":453674,"count":0}],"isBlockCoverage":false},{"functionName":"get$query","ranges":[{"startOffset":453691,"endOffset":453975,"count":0}],"isBlockCoverage":false},{"functionName":"get$fragment","ranges":[{"startOffset":453995,"endOffset":454227,"count":0}],"isBlockCoverage":false},{"functionName":"get$pathSegments","ranges":[{"startOffset":454251,"endOffset":455219,"count":0}],"isBlockCoverage":false},{"functionName":"get$queryParameters","ranges":[{"startOffset":455246,"endOffset":455623,"count":0}],"isBlockCoverage":false},{"functionName":"_isPort$1","ranges":[{"startOffset":455640,"endOffset":455927,"count":0}],"isBlockCoverage":false},{"functionName":"removeFragment$0","ranges":[{"startOffset":455951,"endOffset":456335,"count":0}],"isBlockCoverage":false},{"functionName":"resolve$1","ranges":[{"startOffset":456352,"endOffset":456435,"count":0}],"isBlockCoverage":false},{"functionName":"resolveUri$1","ranges":[{"startOffset":456455,"endOffset":456640,"count":0}],"isBlockCoverage":false},{"functionName":"_simpleMerge$2","ranges":[{"startOffset":456662,"endOffset":462688,"count":0}],"isBlockCoverage":false},{"functionName":"toFilePath$0","ranges":[{"startOffset":462708,"endOffset":463987,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":464007,"endOffset":464186,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":464197,"endOffset":464401,"count":0}],"isBlockCoverage":false},{"functionName":"_toNonSimple$0","ranges":[{"startOffset":464423,"endOffset":465061,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":465079,"endOffset":465122,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":465252,"endOffset":465309,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":465361,"endOffset":465418,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":465507,"endOffset":465563,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":465616,"endOffset":465673,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":465726,"endOffset":465782,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":465830,"endOffset":465889,"count":0}],"isBlockCoverage":false},{"functionName":"get$onClick","ranges":[{"startOffset":465908,"endOffset":466020,"count":0}],"isBlockCoverage":false},{"functionName":"addEventListener$3","ranges":[{"startOffset":466136,"endOffset":466350,"count":1}],"isBlockCoverage":true},{"functionName":"_addEventListener$3","ranges":[{"startOffset":466377,"endOffset":466569,"count":1}],"isBlockCoverage":true},{"functionName":"_removeEventListener$3","ranges":[{"startOffset":466599,"endOffset":466794,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":466904,"endOffset":466960,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":467015,"endOffset":467071,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":467085,"endOffset":467319,"count":0}],"isBlockCoverage":false},{"functionName":"$indexSet","ranges":[{"startOffset":467336,"endOffset":467547,"count":0}],"isBlockCoverage":false},{"functionName":"elementAt$1","ranges":[{"startOffset":467566,"endOffset":467719,"count":0}],"isBlockCoverage":false},{"functionName":"$asEfficientLengthIterable","ranges":[{"startOffset":467788,"endOffset":467829,"count":0}],"isBlockCoverage":false},{"functionName":"$asJavaScriptIndexingBehavior","ranges":[{"startOffset":467904,"endOffset":467945,"count":0}],"isBlockCoverage":false},{"functionName":"$asListMixin","ranges":[{"startOffset":467965,"endOffset":468006,"count":0}],"isBlockCoverage":false},{"functionName":"$asIterable","ranges":[{"startOffset":468045,"endOffset":468086,"count":0}],"isBlockCoverage":false},{"functionName":"$asList","ranges":[{"startOffset":468117,"endOffset":468158,"count":0}],"isBlockCoverage":false},{"functionName":"$asImmutableListMixin","ranges":[{"startOffset":468187,"endOffset":468228,"count":0}],"isBlockCoverage":false},{"functionName":"get$origin","ranges":[{"startOffset":468330,"endOffset":468485,"count":1},{"startOffset":468414,"endOffset":468484,"count":0}],"isBlockCoverage":true},{"functionName":"toString$0","ranges":[{"startOffset":468503,"endOffset":468560,"count":0}],"isBlockCoverage":false},{"functionName":"addEventListener$3","ranges":[{"startOffset":468671,"endOffset":468926,"count":1}],"isBlockCoverage":true},{"functionName":"postMessage$1","ranges":[{"startOffset":468947,"endOffset":469079,"count":1}],"isBlockCoverage":true},{"functionName":"toString$0","ranges":[{"startOffset":469194,"endOffset":469338,"count":0}],"isBlockCoverage":false},{"functionName":"_removeChild$1","ranges":[{"startOffset":469360,"endOffset":469435,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":469505,"endOffset":469561,"count":0}],"isBlockCoverage":false},{"functionName":"get$location","ranges":[{"startOffset":469638,"endOffset":469696,"count":1}],"isBlockCoverage":true},{"functionName":"postMessage$3","ranges":[{"startOffset":469717,"endOffset":469975,"count":0}],"isBlockCoverage":false},{"functionName":"_postMessage_1$3","ranges":[{"startOffset":469999,"endOffset":470177,"count":0}],"isBlockCoverage":false},{"functionName":"listen$4$cancelOnError$onDone$onError","ranges":[{"startOffset":470279,"endOffset":470605,"count":0}],"isBlockCoverage":false},{"functionName":"listen$1","ranges":[{"startOffset":470621,"endOffset":470728,"count":0}],"isBlockCoverage":false},{"functionName":"listen$3$onDone$onError","ranges":[{"startOffset":470759,"endOffset":470888,"count":0}],"isBlockCoverage":false},{"functionName":"cancel$0","ranges":[{"startOffset":470995,"endOffset":471170,"count":0}],"isBlockCoverage":false},{"functionName":"_tryResume$0","ranges":[{"startOffset":471190,"endOffset":471364,"count":1}],"isBlockCoverage":true},{"functionName":"_unlisten$0","ranges":[{"startOffset":471383,"endOffset":471696,"count":0}],"isBlockCoverage":false},{"functionName":"set$_onData","ranges":[{"startOffset":471715,"endOffset":471819,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":471888,"endOffset":471979,"count":1}],"isBlockCoverage":true},{"functionName":"get$iterator","ranges":[{"startOffset":472060,"endOffset":472239,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":472301,"endOffset":472764,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":472783,"endOffset":472829,"count":0}],"isBlockCoverage":false},{"functionName":"set$_current","ranges":[{"startOffset":472849,"endOffset":472972,"count":0}],"isBlockCoverage":false},{"functionName":"postMessage$3","ranges":[{"startOffset":473056,"endOffset":473227,"count":1}],"isBlockCoverage":true},{"functionName":"findSlot$1","ranges":[{"startOffset":473464,"endOffset":473763,"count":1},{"startOffset":473634,"endOffset":473643,"count":0}],"isBlockCoverage":true},{"functionName":"walk$1","ranges":[{"startOffset":473777,"endOffset":475247,"count":1},{"startOffset":474098,"endOffset":474130,"count":0},{"startOffset":474165,"endOffset":474240,"count":0},{"startOffset":474273,"endOffset":474282,"count":0},{"startOffset":474315,"endOffset":474324,"count":0},{"startOffset":474419,"endOffset":474428,"count":0},{"startOffset":474556,"endOffset":474581,"count":0},{"startOffset":474667,"endOffset":474679,"count":0},{"startOffset":475007,"endOffset":475032,"count":0},{"startOffset":475094,"endOffset":475106,"count":0},{"startOffset":475155,"endOffset":475246,"count":0}],"isBlockCoverage":true},{"functionName":"copyList$2","ranges":[{"startOffset":475265,"endOffset":475616,"count":1}],"isBlockCoverage":true},{"functionName":"call$2","ranges":[{"startOffset":475682,"endOffset":475766,"count":1}],"isBlockCoverage":true},{"functionName":"findSlot$1","ranges":[{"startOffset":475849,"endOffset":476208,"count":1},{"startOffset":476029,"endOffset":476044,"count":0},{"startOffset":476071,"endOffset":476080,"count":0}],"isBlockCoverage":true},{"functionName":"walk$1","ranges":[{"startOffset":476222,"endOffset":478314,"count":1},{"startOffset":476555,"endOffset":476884,"count":0},{"startOffset":476924,"endOffset":476999,"count":0},{"startOffset":477073,"endOffset":477118,"count":0},{"startOffset":477319,"endOffset":477344,"count":0},{"startOffset":477434,"endOffset":477446,"count":0},{"startOffset":477849,"endOffset":477874,"count":0},{"startOffset":477936,"endOffset":477948,"count":0},{"startOffset":478073,"endOffset":478076,"count":0},{"startOffset":478292,"endOffset":478313,"count":0}],"isBlockCoverage":true},{"functionName":"convertNativeToDart_AcceptStructuredClone$2$mustCopy","ranges":[{"startOffset":478374,"endOffset":478470,"count":1}],"isBlockCoverage":true},{"functionName":"call$2","ranges":[{"startOffset":478542,"endOffset":478706,"count":1}],"isBlockCoverage":true},{"functionName":"forEachJsField$2","ranges":[{"startOffset":478846,"endOffset":479184,"count":1},{"startOffset":479052,"endOffset":479098,"count":0}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":479261,"endOffset":479336,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":479433,"endOffset":479510,"count":0}],"isBlockCoverage":false},{"functionName":"get$onClick","ranges":[{"startOffset":479581,"endOffset":479693,"count":1}],"isBlockCoverage":true},{"functionName":"$asEfficientLengthIterable","ranges":[{"startOffset":479789,"endOffset":479829,"count":0}],"isBlockCoverage":false},{"functionName":"$asIterable","ranges":[{"startOffset":479868,"endOffset":479908,"count":0}],"isBlockCoverage":false},{"functionName":"$asList","ranges":[{"startOffset":479939,"endOffset":479979,"count":0}],"isBlockCoverage":false},{"functionName":"addStream$1","ranges":[{"startOffset":480035,"endOffset":480478,"count":0}],"isBlockCoverage":false},{"functionName":"_checkEventAllowed$0","ranges":[{"startOffset":480506,"endOffset":480767,"count":0}],"isBlockCoverage":false},{"functionName":"close$0","ranges":[{"startOffset":480782,"endOffset":480870,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":480987,"endOffset":481045,"count":0}],"isBlockCoverage":false},{"functionName":"absolute$7","ranges":[{"startOffset":481161,"endOffset":481639,"count":0}],"isBlockCoverage":false},{"functionName":"absolute$1","ranges":[{"startOffset":481657,"endOffset":481775,"count":0}],"isBlockCoverage":false},{"functionName":"join$8","ranges":[{"startOffset":481789,"endOffset":482229,"count":0}],"isBlockCoverage":false},{"functionName":"join$2","ranges":[{"startOffset":482243,"endOffset":482371,"count":0}],"isBlockCoverage":false},{"functionName":"joinAll$1","ranges":[{"startOffset":482388,"endOffset":483822,"count":0}],"isBlockCoverage":false},{"functionName":"split$1","ranges":[{"startOffset":483837,"endOffset":484322,"count":0}],"isBlockCoverage":false},{"functionName":"normalize$1","ranges":[{"startOffset":484341,"endOffset":484574,"count":0}],"isBlockCoverage":false},{"functionName":"_needsNormalization$1","ranges":[{"startOffset":484603,"endOffset":486114,"count":0}],"isBlockCoverage":false},{"functionName":"relative$1","ranges":[{"startOffset":486132,"endOffset":488870,"count":0}],"isBlockCoverage":false},{"functionName":"toUri$1","ranges":[{"startOffset":488885,"endOffset":489181,"count":0}],"isBlockCoverage":false},{"functionName":"prettyUri$1","ranges":[{"startOffset":489200,"endOffset":489763,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":489820,"endOffset":489888,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":489967,"endOffset":490034,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":490111,"endOffset":490184,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":490264,"endOffset":490368,"count":0}],"isBlockCoverage":false},{"functionName":"getRoot$1","ranges":[{"startOffset":490441,"endOffset":490777,"count":0}],"isBlockCoverage":false},{"functionName":"relativePathToUri$1","ranges":[{"startOffset":490804,"endOffset":491061,"count":0}],"isBlockCoverage":false},{"functionName":"pathsEqual$2","ranges":[{"startOffset":491081,"endOffset":491140,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasTrailingSeparator","ranges":[{"startOffset":491205,"endOffset":491442,"count":0}],"isBlockCoverage":false},{"functionName":"removeTrailingSeparators$0","ranges":[{"startOffset":491476,"endOffset":491891,"count":0}],"isBlockCoverage":false},{"functionName":"normalize$0","ranges":[{"startOffset":491910,"endOffset":493391,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":493409,"endOffset":493905,"count":0}],"isBlockCoverage":false},{"functionName":"set$parts","ranges":[{"startOffset":493922,"endOffset":494022,"count":0}],"isBlockCoverage":false},{"functionName":"set$separators","ranges":[{"startOffset":494044,"endOffset":494159,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":494224,"endOffset":494290,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":494364,"endOffset":494430,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":494476,"endOffset":494529,"count":0}],"isBlockCoverage":false},{"functionName":"containsSeparator$1","ranges":[{"startOffset":494589,"endOffset":494666,"count":0}],"isBlockCoverage":false},{"functionName":"isSeparator$1","ranges":[{"startOffset":494687,"endOffset":494743,"count":0}],"isBlockCoverage":false},{"functionName":"needsSeparator$1","ranges":[{"startOffset":494767,"endOffset":494881,"count":0}],"isBlockCoverage":false},{"functionName":"rootLength$2$withDrive","ranges":[{"startOffset":494911,"endOffset":495044,"count":0}],"isBlockCoverage":false},{"functionName":"rootLength$1","ranges":[{"startOffset":495064,"endOffset":495141,"count":0}],"isBlockCoverage":false},{"functionName":"isRootRelative$1","ranges":[{"startOffset":495165,"endOffset":495207,"count":0}],"isBlockCoverage":false},{"functionName":"pathFromUri$1","ranges":[{"startOffset":495228,"endOffset":495555,"count":0}],"isBlockCoverage":false},{"functionName":"absolutePathToUri$1","ranges":[{"startOffset":495582,"endOffset":495981,"count":0}],"isBlockCoverage":false},{"functionName":"get$name","ranges":[{"startOffset":495997,"endOffset":496047,"count":0}],"isBlockCoverage":false},{"functionName":"get$separator","ranges":[{"startOffset":496068,"endOffset":496115,"count":0}],"isBlockCoverage":false},{"functionName":"containsSeparator$1","ranges":[{"startOffset":496173,"endOffset":496250,"count":0}],"isBlockCoverage":false},{"functionName":"isSeparator$1","ranges":[{"startOffset":496271,"endOffset":496327,"count":0}],"isBlockCoverage":false},{"functionName":"needsSeparator$1","ranges":[{"startOffset":496351,"endOffset":496625,"count":0}],"isBlockCoverage":false},{"functionName":"rootLength$2$withDrive","ranges":[{"startOffset":496655,"endOffset":497605,"count":0}],"isBlockCoverage":false},{"functionName":"rootLength$1","ranges":[{"startOffset":497625,"endOffset":497702,"count":0}],"isBlockCoverage":false},{"functionName":"isRootRelative$1","ranges":[{"startOffset":497726,"endOffset":497817,"count":0}],"isBlockCoverage":false},{"functionName":"pathFromUri$1","ranges":[{"startOffset":497838,"endOffset":497892,"count":0}],"isBlockCoverage":false},{"functionName":"relativePathToUri$1","ranges":[{"startOffset":497919,"endOffset":497973,"count":0}],"isBlockCoverage":false},{"functionName":"absolutePathToUri$1","ranges":[{"startOffset":498000,"endOffset":498054,"count":0}],"isBlockCoverage":false},{"functionName":"get$name","ranges":[{"startOffset":498070,"endOffset":498120,"count":0}],"isBlockCoverage":false},{"functionName":"get$separator","ranges":[{"startOffset":498141,"endOffset":498188,"count":0}],"isBlockCoverage":false},{"functionName":"containsSeparator$1","ranges":[{"startOffset":498250,"endOffset":498327,"count":0}],"isBlockCoverage":false},{"functionName":"isSeparator$1","ranges":[{"startOffset":498348,"endOffset":498423,"count":0}],"isBlockCoverage":false},{"functionName":"needsSeparator$1","ranges":[{"startOffset":498447,"endOffset":498622,"count":0}],"isBlockCoverage":false},{"functionName":"rootLength$2$withDrive","ranges":[{"startOffset":498652,"endOffset":499519,"count":0}],"isBlockCoverage":false},{"functionName":"rootLength$1","ranges":[{"startOffset":499539,"endOffset":499616,"count":0}],"isBlockCoverage":false},{"functionName":"isRootRelative$1","ranges":[{"startOffset":499640,"endOffset":499706,"count":0}],"isBlockCoverage":false},{"functionName":"pathFromUri$1","ranges":[{"startOffset":499727,"endOffset":500380,"count":0}],"isBlockCoverage":false},{"functionName":"absolutePathToUri$1","ranges":[{"startOffset":500407,"endOffset":501556,"count":0}],"isBlockCoverage":false},{"functionName":"codeUnitsEqual$2","ranges":[{"startOffset":501580,"endOffset":501969,"count":0}],"isBlockCoverage":false},{"functionName":"pathsEqual$2","ranges":[{"startOffset":501989,"endOffset":502379,"count":0}],"isBlockCoverage":false},{"functionName":"get$name","ranges":[{"startOffset":502395,"endOffset":502445,"count":0}],"isBlockCoverage":false},{"functionName":"get$separator","ranges":[{"startOffset":502466,"endOffset":502513,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":502588,"endOffset":502655,"count":0}],"isBlockCoverage":false},{"functionName":"toTrace$0","ranges":[{"startOffset":502719,"endOffset":503068,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":503086,"endOffset":503628,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":503712,"endOffset":503885,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":503968,"endOffset":504053,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":504131,"endOffset":504223,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":504303,"endOffset":504679,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":504760,"endOffset":504879,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":504958,"endOffset":505296,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":505376,"endOffset":505558,"count":0}],"isBlockCoverage":false},{"functionName":"get$isCore","ranges":[{"startOffset":505624,"endOffset":505689,"count":0}],"isBlockCoverage":false},{"functionName":"get$library","ranges":[{"startOffset":505708,"endOffset":505863,"count":0}],"isBlockCoverage":false},{"functionName":"get$$package","ranges":[{"startOffset":505883,"endOffset":506053,"count":0}],"isBlockCoverage":false},{"functionName":"get$location","ranges":[{"startOffset":506073,"endOffset":506361,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":506379,"endOffset":506469,"count":0}],"isBlockCoverage":false},{"functionName":"get$uri","ranges":[{"startOffset":506484,"endOffset":506525,"count":0}],"isBlockCoverage":false},{"functionName":"get$line","ranges":[{"startOffset":506541,"endOffset":506583,"count":0}],"isBlockCoverage":false},{"functionName":"get$column","ranges":[{"startOffset":506601,"endOffset":506645,"count":0}],"isBlockCoverage":false},{"functionName":"get$member","ranges":[{"startOffset":506663,"endOffset":506707,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":506771,"endOffset":507825,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":507908,"endOffset":508742,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":508839,"endOffset":509859,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":509948,"endOffset":511172,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":511261,"endOffset":512805,"count":0}],"isBlockCoverage":false},{"functionName":"get$_trace","ranges":[{"startOffset":512874,"endOffset":513090,"count":0}],"isBlockCoverage":false},{"functionName":"get$frames","ranges":[{"startOffset":513108,"endOffset":513171,"count":0}],"isBlockCoverage":false},{"functionName":"get$terse","ranges":[{"startOffset":513188,"endOffset":513273,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":513291,"endOffset":513357,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":513456,"endOffset":513524,"count":0}],"isBlockCoverage":false},{"functionName":"get$terse","ranges":[{"startOffset":513589,"endOffset":513680,"count":0}],"isBlockCoverage":false},{"functionName":"foldFrames$2$terse","ranges":[{"startOffset":513706,"endOffset":515185,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":515203,"endOffset":515689,"count":0}],"isBlockCoverage":false},{"functionName":"get$frames","ranges":[{"startOffset":515729,"endOffset":515773,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":515834,"endOffset":515912,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":515991,"endOffset":516074,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":516151,"endOffset":516253,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":516331,"endOffset":516414,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":516495,"endOffset":516567,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":516649,"endOffset":516732,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":516814,"endOffset":516927,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":517010,"endOffset":517098,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":517181,"endOffset":517269,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":517353,"endOffset":517442,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":517517,"endOffset":517556,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":517637,"endOffset":517967,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":518049,"endOffset":518442,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":518522,"endOffset":518641,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":518720,"endOffset":518989,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":519063,"endOffset":519108,"count":0}],"isBlockCoverage":false},{"functionName":"get$uri","ranges":[{"startOffset":519140,"endOffset":519181,"count":0}],"isBlockCoverage":false},{"functionName":"get$line","ranges":[{"startOffset":519197,"endOffset":519239,"count":0}],"isBlockCoverage":false},{"functionName":"get$column","ranges":[{"startOffset":519257,"endOffset":519301,"count":0}],"isBlockCoverage":false},{"functionName":"get$isCore","ranges":[{"startOffset":519319,"endOffset":519363,"count":0}],"isBlockCoverage":false},{"functionName":"get$library","ranges":[{"startOffset":519382,"endOffset":519427,"count":0}],"isBlockCoverage":false},{"functionName":"get$$package","ranges":[{"startOffset":519447,"endOffset":519493,"count":0}],"isBlockCoverage":false},{"functionName":"get$location","ranges":[{"startOffset":519513,"endOffset":519567,"count":0}],"isBlockCoverage":false},{"functionName":"get$member","ranges":[{"startOffset":519585,"endOffset":519629,"count":0}],"isBlockCoverage":false},{"functionName":"GuaranteeChannel$3$allowSinkErrors","ranges":[{"startOffset":519710,"endOffset":520046,"count":1}],"isBlockCoverage":true},{"functionName":"_onSinkDisconnected$0","ranges":[{"startOffset":520075,"endOffset":520266,"count":0}],"isBlockCoverage":false},{"functionName":"set$_sink","ranges":[{"startOffset":520283,"endOffset":520401,"count":1}],"isBlockCoverage":true},{"functionName":"set$_streamController","ranges":[{"startOffset":520430,"endOffset":520588,"count":1}],"isBlockCoverage":true},{"functionName":"set$_guarantee_channel$_subscription","ranges":[{"startOffset":520632,"endOffset":520801,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":520862,"endOffset":521185,"count":1},{"startOffset":520956,"endOffset":520963,"count":0}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":521266,"endOffset":521392,"count":0}],"isBlockCoverage":false},{"functionName":"add$1","ranges":[{"startOffset":521510,"endOffset":522038,"count":1},{"startOffset":521653,"endOffset":521725,"count":0},{"startOffset":521781,"endOffset":521859,"count":0},{"startOffset":521898,"endOffset":521905,"count":0}],"isBlockCoverage":true},{"functionName":"addError$2","ranges":[{"startOffset":522056,"endOffset":522478,"count":0}],"isBlockCoverage":false},{"functionName":"addError$1","ranges":[{"startOffset":522496,"endOffset":522562,"count":0}],"isBlockCoverage":false},{"functionName":"_addError$2","ranges":[{"startOffset":522581,"endOffset":522735,"count":0}],"isBlockCoverage":false},{"functionName":"_addError$1","ranges":[{"startOffset":522754,"endOffset":522821,"count":0}],"isBlockCoverage":false},{"functionName":"addStream$1","ranges":[{"startOffset":522840,"endOffset":523722,"count":1},{"startOffset":522976,"endOffset":523049,"count":0},{"startOffset":523105,"endOffset":523184,"count":0},{"startOffset":523215,"endOffset":523334,"count":0}],"isBlockCoverage":true},{"functionName":"close$0","ranges":[{"startOffset":523737,"endOffset":524196,"count":0}],"isBlockCoverage":false},{"functionName":"_onStreamDisconnected$0","ranges":[{"startOffset":524227,"endOffset":524597,"count":0}],"isBlockCoverage":false},{"functionName":"set$_addStreamSubscription","ranges":[{"startOffset":524631,"endOffset":524808,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":524925,"endOffset":525051,"count":0}],"isBlockCoverage":false},{"functionName":"_MultiChannel$1","ranges":[{"startOffset":525129,"endOffset":525778,"count":1}],"isBlockCoverage":true},{"functionName":"virtualChannel$1","ranges":[{"startOffset":525802,"endOffset":527448,"count":1},{"startOffset":526029,"endOffset":526206,"count":0},{"startOffset":526253,"endOffset":526477,"count":0},{"startOffset":526530,"endOffset":526575,"count":0},{"startOffset":526702,"endOffset":526803,"count":0}],"isBlockCoverage":true},{"functionName":"_closeChannel$2","ranges":[{"startOffset":527471,"endOffset":527872,"count":0}],"isBlockCoverage":false},{"functionName":"_closeInnerChannel$0","ranges":[{"startOffset":527900,"endOffset":528350,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":528432,"endOffset":528620,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":528638,"endOffset":528705,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":528764,"endOffset":528829,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":528956,"endOffset":529518,"count":1},{"startOffset":529164,"endOffset":529171,"count":0},{"startOffset":529457,"endOffset":529512,"count":0}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":529596,"endOffset":529733,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":529751,"endOffset":529835,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":529908,"endOffset":530159,"count":1}],"isBlockCoverage":true},{"functionName":"$signature","ranges":[{"startOffset":530177,"endOffset":530277,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":530351,"endOffset":530463,"count":0}],"isBlockCoverage":false},{"functionName":"get$local","ranges":[{"startOffset":530647,"endOffset":530691,"count":0}],"isBlockCoverage":false},{"functionName":"set$_local","ranges":[{"startOffset":530709,"endOffset":530828,"count":1}],"isBlockCoverage":true},{"functionName":"set$_foreign","ranges":[{"startOffset":530848,"endOffset":530973,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":531139,"endOffset":532002,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":532120,"endOffset":533385,"count":1},{"startOffset":532816,"endOffset":533379,"count":0}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":533455,"endOffset":533696,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":533767,"endOffset":534167,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":534238,"endOffset":534587,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":534706,"endOffset":534887,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":535005,"endOffset":535323,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":535453,"endOffset":535766,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":535848,"endOffset":535966,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":536046,"endOffset":537326,"count":1},{"startOffset":536265,"endOffset":536272,"count":0},{"startOffset":536472,"endOffset":536479,"count":0},{"startOffset":536965,"endOffset":537320,"count":0}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":537408,"endOffset":537676,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":537758,"endOffset":538685,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":537952,"endOffset":538612,"count":1},{"startOffset":538042,"endOffset":538098,"count":0}],"isBlockCoverage":true},{"functionName":"aliases","ranges":[{"startOffset":538714,"endOffset":539149,"count":1}],"isBlockCoverage":true},{"functionName":"installTearOffs","ranges":[{"startOffset":539157,"endOffset":544148,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":540050,"endOffset":540089,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":540135,"endOffset":540205,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":540496,"endOffset":540593,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":540702,"endOffset":540820,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":540931,"endOffset":541070,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":541195,"endOffset":541305,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":541440,"endOffset":541561,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":541698,"endOffset":541826,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":542583,"endOffset":542622,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":542757,"endOffset":542796,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":542921,"endOffset":542960,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":543161,"endOffset":543200,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":543660,"endOffset":543699,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":543800,"endOffset":543839,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":544079,"endOffset":544134,"count":0}],"isBlockCoverage":false},{"functionName":"inheritance","ranges":[{"startOffset":544156,"endOffset":556574,"count":1}],"isBlockCoverage":true},{"functionName":"constants","ranges":[{"startOffset":556582,"endOffset":566012,"count":1}],"isBlockCoverage":true},{"functionName":"getTagFallback","ranges":[{"startOffset":557622,"endOffset":557736,"count":0}],"isBlockCoverage":false},{"functionName":"C.C_JS_CONST0","ranges":[{"startOffset":557758,"endOffset":558873,"count":1},{"startOffset":558781,"endOffset":558796,"count":0}],"isBlockCoverage":true},{"functionName":"getTag","ranges":[{"startOffset":557825,"endOffset":557928,"count":0}],"isBlockCoverage":false},{"functionName":"getUnknownTag","ranges":[{"startOffset":557931,"endOffset":558148,"count":0}],"isBlockCoverage":false},{"functionName":"getUnknownTagGenericBrowser","ranges":[{"startOffset":558151,"endOffset":558326,"count":0}],"isBlockCoverage":false},{"functionName":"prototypeForTag","ranges":[{"startOffset":558329,"endOffset":558595,"count":1},{"startOffset":558399,"endOffset":558411,"count":0},{"startOffset":558545,"endOffset":558557,"count":0}],"isBlockCoverage":true},{"functionName":"discriminator","ranges":[{"startOffset":558598,"endOffset":558642,"count":0}],"isBlockCoverage":false},{"functionName":"C.C_JS_CONST6","ranges":[{"startOffset":558895,"endOffset":559359,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":558931,"endOffset":559356,"count":1},{"startOffset":558987,"endOffset":559000,"count":0},{"startOffset":559078,"endOffset":559091,"count":0},{"startOffset":559317,"endOffset":559355,"count":0}],"isBlockCoverage":true},{"functionName":"confirm","ranges":[{"startOffset":559135,"endOffset":559242,"count":1}],"isBlockCoverage":true},{"functionName":"C.C_JS_CONST1","ranges":[{"startOffset":559381,"endOffset":559530,"count":1},{"startOffset":559468,"endOffset":559529,"count":0}],"isBlockCoverage":true},{"functionName":"C.C_JS_CONST2","ranges":[{"startOffset":559552,"endOffset":560025,"count":1}],"isBlockCoverage":true},{"functionName":"getTagFixed","ranges":[{"startOffset":559648,"endOffset":559829,"count":0}],"isBlockCoverage":false},{"functionName":"prototypeForTagFixed","ranges":[{"startOffset":559832,"endOffset":559945,"count":1}],"isBlockCoverage":true},{"functionName":"C.C_JS_CONST5","ranges":[{"startOffset":560047,"endOffset":560577,"count":1},{"startOffset":560134,"endOffset":560138,"count":0},{"startOffset":560195,"endOffset":560576,"count":0}],"isBlockCoverage":true},{"functionName":"getTagFirefox","ranges":[{"startOffset":560454,"endOffset":560543,"count":0}],"isBlockCoverage":false},{"functionName":"C.C_JS_CONST4","ranges":[{"startOffset":560599,"endOffset":561481,"count":1},{"startOffset":560686,"endOffset":560690,"count":0},{"startOffset":560748,"endOffset":561480,"count":0}],"isBlockCoverage":true},{"functionName":"getTagIE","ranges":[{"startOffset":561013,"endOffset":561256,"count":0}],"isBlockCoverage":false},{"functionName":"prototypeForTagIE","ranges":[{"startOffset":561259,"endOffset":561407,"count":0}],"isBlockCoverage":false},{"functionName":"C.C_JS_CONST3","ranges":[{"startOffset":561503,"endOffset":561536,"count":1}],"isBlockCoverage":true},{"functionName":"staticFields","ranges":[{"startOffset":566020,"endOffset":566720,"count":1}],"isBlockCoverage":true},{"functionName":"lazyInitializers","ranges":[{"startOffset":566728,"endOffset":575683,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":566870,"endOffset":566948,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":567029,"endOffset":567098,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":567199,"endOffset":567387,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":567484,"endOffset":567687,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":567780,"endOffset":567891,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":567998,"endOffset":568249,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":568352,"endOffset":568465,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":568582,"endOffset":568837,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":568938,"endOffset":569053,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":569168,"endOffset":569357,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":569468,"endOffset":569585,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":569710,"endOffset":569903,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":570002,"endOffset":570077,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":570142,"endOffset":570223,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":570288,"endOffset":570350,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":570413,"endOffset":570448,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":570517,"endOffset":570578,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":570669,"endOffset":571283,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":571354,"endOffset":571512,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":571583,"endOffset":571664,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":571721,"endOffset":571771,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":571814,"endOffset":571888,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":571931,"endOffset":572008,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":572059,"endOffset":572220,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":572275,"endOffset":572548,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":572595,"endOffset":572849,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":572906,"endOffset":572966,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":573011,"endOffset":573116,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":573161,"endOffset":573279,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":573336,"endOffset":573422,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":573481,"endOffset":573591,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":573658,"endOffset":573797,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":573854,"endOffset":573959,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":574008,"endOffset":574107,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":574158,"endOffset":574221,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":574282,"endOffset":574368,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":574437,"endOffset":574524,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":574577,"endOffset":574658,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":574703,"endOffset":574773,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":574826,"endOffset":574893,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":574960,"endOffset":575064,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":575121,"endOffset":575225,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":575270,"endOffset":575364,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":575421,"endOffset":575534,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":575585,"endOffset":575677,"count":1}],"isBlockCoverage":true},{"functionName":"nativeSupport","ranges":[{"startOffset":579591,"endOffset":596530,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":579623,"endOffset":580408,"count":1},{"startOffset":580311,"endOffset":580407,"count":0}],"isBlockCoverage":true},{"functionName":"intern","ranges":[{"startOffset":579655,"endOffset":579781,"count":1}],"isBlockCoverage":true},{"functionName":"init.getIsolateTag","ranges":[{"startOffset":579810,"endOffset":579894,"count":1}],"isBlockCoverage":true},{"functionName":"Function.call$0","ranges":[{"startOffset":596565,"endOffset":596600,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$1","ranges":[{"startOffset":596632,"endOffset":596669,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$2","ranges":[{"startOffset":596701,"endOffset":596744,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$3","ranges":[{"startOffset":596776,"endOffset":596825,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$4","ranges":[{"startOffset":596857,"endOffset":596912,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$1$1","ranges":[{"startOffset":596946,"endOffset":596983,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$3$1","ranges":[{"startOffset":597017,"endOffset":597054,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$3$3","ranges":[{"startOffset":597088,"endOffset":597137,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$2$2","ranges":[{"startOffset":597171,"endOffset":597214,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$2$1","ranges":[{"startOffset":597248,"endOffset":597285,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$2$3","ranges":[{"startOffset":597319,"endOffset":597368,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$1$2","ranges":[{"startOffset":597402,"endOffset":597445,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$5","ranges":[{"startOffset":597477,"endOffset":597538,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$3$4","ranges":[{"startOffset":597572,"endOffset":597627,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$2$4","ranges":[{"startOffset":597661,"endOffset":597716,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$1$4","ranges":[{"startOffset":597750,"endOffset":597805,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$3$6","ranges":[{"startOffset":597839,"endOffset":597906,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$2$5","ranges":[{"startOffset":597940,"endOffset":598001,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":598067,"endOffset":598606,"count":1},{"startOffset":598129,"endOffset":598227,"count":0},{"startOffset":598282,"endOffset":598605,"count":0}],"isBlockCoverage":true},{"functionName":"onLoad","ranges":[{"startOffset":598329,"endOffset":598499,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":598608,"endOffset":598784,"count":1},{"startOffset":598726,"endOffset":598753,"count":0}],"isBlockCoverage":true}]},{"scriptId":"6","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":276,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":275,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_completeError$20","ranges":[{"startOffset":82,"endOffset":273,"count":0}],"isBlockCoverage":false}]},{"scriptId":"7","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":282,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":281,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_complete$11","ranges":[{"startOffset":82,"endOffset":279,"count":1}],"isBlockCoverage":true}]},{"scriptId":"8","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":277,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":276,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__completeError$22","ranges":[{"startOffset":82,"endOffset":274,"count":0}],"isBlockCoverage":false}]},{"scriptId":"9","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":277,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":276,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_add$13","ranges":[{"startOffset":82,"endOffset":274,"count":1}],"isBlockCoverage":true}]},{"scriptId":"10","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":271,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":270,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_addError$24","ranges":[{"startOffset":82,"endOffset":268,"count":1}],"isBlockCoverage":true}]},{"scriptId":"11","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":277,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":276,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_add$15","ranges":[{"startOffset":82,"endOffset":274,"count":1}],"isBlockCoverage":true}]},{"scriptId":"12","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":272,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":271,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__sendDone$06","ranges":[{"startOffset":82,"endOffset":269,"count":0}],"isBlockCoverage":false}]},{"scriptId":"13","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":271,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":270,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_addError$27","ranges":[{"startOffset":82,"endOffset":268,"count":1}],"isBlockCoverage":true}]},{"scriptId":"14","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":272,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":271,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__addError$28","ranges":[{"startOffset":82,"endOffset":269,"count":1}],"isBlockCoverage":true}]},{"scriptId":"15","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":281,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":280,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__closeInnerChannel$09","ranges":[{"startOffset":82,"endOffset":278,"count":1}],"isBlockCoverage":true}]},{"scriptId":"16","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":62,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":61,"count":1}],"isBlockCoverage":true}]},{"scriptId":"17","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":92,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":91,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":89,"count":1},{"startOffset":87,"endOffset":88,"count":0}],"isBlockCoverage":true}]},{"scriptId":"18","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":62,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":61,"count":1}],"isBlockCoverage":true}]},{"scriptId":"19","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":86,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":85,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":83,"count":0}],"isBlockCoverage":false}]},{"scriptId":"20","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":62,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":61,"count":1}],"isBlockCoverage":true}]},{"scriptId":"21","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":106,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":105,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":103,"count":0}],"isBlockCoverage":false}]},{"scriptId":"22","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":62,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":61,"count":1}],"isBlockCoverage":true}]},{"scriptId":"23","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":86,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":85,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":83,"count":0}],"isBlockCoverage":false}]},{"scriptId":"24","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":62,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":61,"count":1}],"isBlockCoverage":true}]},{"scriptId":"25","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":92,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":91,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":89,"count":1},{"startOffset":87,"endOffset":88,"count":0}],"isBlockCoverage":true}]},{"scriptId":"26","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":64,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":63,"count":1}],"isBlockCoverage":true}]},{"scriptId":"27","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":98,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":97,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":95,"count":0}],"isBlockCoverage":false}]},{"scriptId":"28","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":64,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":63,"count":1}],"isBlockCoverage":true}]},{"scriptId":"29","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":89,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":88,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":86,"count":0}],"isBlockCoverage":false}]},{"scriptId":"30","url":"http://localhost:33587/JvrQonmMf3ATS3rRCO76ZTlBfGvy%2Fj69/test/packages/test/dart.js","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":2011,"count":1}],"isBlockCoverage":true},{"functionName":"window.onload","ranges":[{"startOffset":384,"endOffset":2009,"count":1},{"startOffset":1295,"endOffset":1442,"count":0},{"startOffset":1491,"endOffset":1629,"count":0}],"isBlockCoverage":true},{"functionName":"sendLoadException","ranges":[{"startOffset":560,"endOffset":762,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":875,"endOffset":921,"count":0}],"isBlockCoverage":false},{"functionName":"script.onerror","ranges":[{"startOffset":1747,"endOffset":1907,"count":0}],"isBlockCoverage":false}]},{"scriptId":"31","url":"http://localhost:33587/JvrQonmMf3ATS3rRCO76ZTlBfGvy%2Fj69/test/main_test.dart.browser_test.dart.js","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":1081547,"count":1}],"isBlockCoverage":true},{"functionName":"dartProgram","ranges":[{"startOffset":1051,"endOffset":1081480,"count":1}],"isBlockCoverage":true},{"functionName":"copyProperties","ranges":[{"startOffset":1078,"endOffset":1253,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1288,"endOffset":1858,"count":1},{"startOffset":1469,"endOffset":1482,"count":0},{"startOffset":1645,"endOffset":1707,"count":0},{"startOffset":1709,"endOffset":1812,"count":0},{"startOffset":1818,"endOffset":1857,"count":0}],"isBlockCoverage":true},{"functionName":"cls","ranges":[{"startOffset":1315,"endOffset":1333,"count":1}],"isBlockCoverage":true},{"functionName":"setFunctionNamesIfNecessary","ranges":[{"startOffset":1864,"endOffset":2287,"count":1},{"startOffset":1991,"endOffset":2283,"count":0}],"isBlockCoverage":true},{"functionName":"t","ranges":[{"startOffset":1916,"endOffset":1936,"count":0}],"isBlockCoverage":false},{"functionName":"inherit","ranges":[{"startOffset":2290,"endOffset":2685,"count":1},{"startOffset":2533,"endOffset":2681,"count":0}],"isBlockCoverage":true},{"functionName":"inheritMany","ranges":[{"startOffset":2688,"endOffset":2805,"count":1}],"isBlockCoverage":true},{"functionName":"mixin","ranges":[{"startOffset":2808,"endOffset":2929,"count":1}],"isBlockCoverage":true},{"functionName":"lazy","ranges":[{"startOffset":2932,"endOffset":3681,"count":1}],"isBlockCoverage":true},{"functionName":"holder.<computed>","ranges":[{"startOffset":3094,"endOffset":3676,"count":1},{"startOffset":3429,"endOffset":3467,"count":0},{"startOffset":3539,"endOffset":3559,"count":0}],"isBlockCoverage":true},{"functionName":"holder.<computed>","ranges":[{"startOffset":3134,"endOffset":3187,"count":0}],"isBlockCoverage":false},{"functionName":"holder.<computed>","ranges":[{"startOffset":3589,"endOffset":3640,"count":1}],"isBlockCoverage":true},{"functionName":"makeConstList","ranges":[{"startOffset":3684,"endOffset":3799,"count":1}],"isBlockCoverage":true},{"functionName":"convertToFastObject","ranges":[{"startOffset":3802,"endOffset":3939,"count":1}],"isBlockCoverage":true},{"functionName":"t","ranges":[{"startOffset":3849,"endOffset":3869,"count":1}],"isBlockCoverage":true},{"functionName":"convertAllToFastObject","ranges":[{"startOffset":3942,"endOffset":4093,"count":1}],"isBlockCoverage":true},{"functionName":"tearOffGetter","ranges":[{"startOffset":4123,"endOffset":5038,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff","ranges":[{"startOffset":5041,"endOffset":5449,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":5180,"endOffset":5362,"count":1}],"isBlockCoverage":true},{"functionName":"installTearOff","ranges":[{"startOffset":5475,"endOffset":6389,"count":1}],"isBlockCoverage":true},{"functionName":"installStaticTearOff","ranges":[{"startOffset":6392,"endOffset":6715,"count":1}],"isBlockCoverage":true},{"functionName":"installInstanceTearOff","ranges":[{"startOffset":6718,"endOffset":7067,"count":1}],"isBlockCoverage":true},{"functionName":"setOrUpdateInterceptorsByTag","ranges":[{"startOffset":7070,"endOffset":7273,"count":1},{"startOffset":7234,"endOffset":7272,"count":0}],"isBlockCoverage":true},{"functionName":"setOrUpdateLeafTags","ranges":[{"startOffset":7276,"endOffset":7452,"count":1},{"startOffset":7413,"endOffset":7451,"count":0}],"isBlockCoverage":true},{"functionName":"updateTypes","ranges":[{"startOffset":7455,"endOffset":7608,"count":0}],"isBlockCoverage":false},{"functionName":"updateHolder","ranges":[{"startOffset":7611,"endOffset":7715,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":7736,"endOffset":9400,"count":1}],"isBlockCoverage":true},{"functionName":"mkInstance","ranges":[{"startOffset":7770,"endOffset":8132,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":7890,"endOffset":8123,"count":1}],"isBlockCoverage":true},{"functionName":"mkStatic","ranges":[{"startOffset":8151,"endOffset":8481,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":8256,"endOffset":8472,"count":1}],"isBlockCoverage":true},{"functionName":"initializeDeferredHunk","ranges":[{"startOffset":9406,"endOffset":9527,"count":0}],"isBlockCoverage":false},{"functionName":"getGlobalFromName","ranges":[{"startOffset":9530,"endOffset":9727,"count":0}],"isBlockCoverage":false},{"functionName":"JS_CONST","ranges":[{"startOffset":9759,"endOffset":9786,"count":0}],"isBlockCoverage":false},{"functionName":"CastIterable_CastIterable","ranges":[{"startOffset":9819,"endOffset":10153,"count":1},{"startOffset":10045,"endOffset":10152,"count":0}],"isBlockCoverage":true},{"functionName":"hexDigitValue","ranges":[{"startOffset":10174,"endOffset":10439,"count":0}],"isBlockCoverage":false},{"functionName":"SubListIterable$","ranges":[{"startOffset":10463,"endOffset":10899,"count":0}],"isBlockCoverage":false},{"functionName":"MappedIterable_MappedIterable","ranges":[{"startOffset":10936,"endOffset":11314,"count":0}],"isBlockCoverage":false},{"functionName":"IterableElementError_noElement","ranges":[{"startOffset":11352,"endOffset":11415,"count":0}],"isBlockCoverage":false},{"functionName":"IterableElementError_tooMany","ranges":[{"startOffset":11451,"endOffset":11521,"count":0}],"isBlockCoverage":false},{"functionName":"IterableElementError_tooFew","ranges":[{"startOffset":11556,"endOffset":11625,"count":0}],"isBlockCoverage":false},{"functionName":"_CastIterableBase","ranges":[{"startOffset":11650,"endOffset":11686,"count":0}],"isBlockCoverage":false},{"functionName":"CastIterator","ranges":[{"startOffset":11706,"endOffset":11789,"count":1}],"isBlockCoverage":true},{"functionName":"CastIterable","ranges":[{"startOffset":11809,"endOffset":11892,"count":0}],"isBlockCoverage":false},{"functionName":"_EfficientLengthCastIterable","ranges":[{"startOffset":11928,"endOffset":12027,"count":1}],"isBlockCoverage":true},{"functionName":"CastMap","ranges":[{"startOffset":12042,"endOffset":12120,"count":1}],"isBlockCoverage":true},{"functionName":"CastMap_forEach_closure","ranges":[{"startOffset":12151,"endOffset":12241,"count":0}],"isBlockCoverage":false},{"functionName":"CodeUnits","ranges":[{"startOffset":12258,"endOffset":12313,"count":0}],"isBlockCoverage":false},{"functionName":"EfficientLengthIterable","ranges":[{"startOffset":12344,"endOffset":12386,"count":0}],"isBlockCoverage":false},{"functionName":"ListIterable","ranges":[{"startOffset":12406,"endOffset":12437,"count":0}],"isBlockCoverage":false},{"functionName":"SubListIterable","ranges":[{"startOffset":12460,"endOffset":12640,"count":0}],"isBlockCoverage":false},{"functionName":"ListIterator","ranges":[{"startOffset":12660,"endOffset":12874,"count":1}],"isBlockCoverage":true},{"functionName":"MappedIterable","ranges":[{"startOffset":12896,"endOffset":13018,"count":1}],"isBlockCoverage":true},{"functionName":"EfficientLengthMappedIterable","ranges":[{"startOffset":13055,"endOffset":13192,"count":0}],"isBlockCoverage":false},{"functionName":"MappedIterator","ranges":[{"startOffset":13214,"endOffset":13372,"count":1}],"isBlockCoverage":true},{"functionName":"MappedListIterable","ranges":[{"startOffset":13398,"endOffset":13511,"count":1}],"isBlockCoverage":true},{"functionName":"WhereIterable","ranges":[{"startOffset":13532,"endOffset":13653,"count":1}],"isBlockCoverage":true},{"functionName":"WhereIterator","ranges":[{"startOffset":13674,"endOffset":13784,"count":1}],"isBlockCoverage":true},{"functionName":"ExpandIterable","ranges":[{"startOffset":13806,"endOffset":13928,"count":0}],"isBlockCoverage":false},{"functionName":"ExpandIterator","ranges":[{"startOffset":13950,"endOffset":14144,"count":0}],"isBlockCoverage":false},{"functionName":"SkipWhileIterable","ranges":[{"startOffset":14169,"endOffset":14294,"count":0}],"isBlockCoverage":false},{"functionName":"SkipWhileIterator","ranges":[{"startOffset":14319,"endOffset":14473,"count":0}],"isBlockCoverage":false},{"functionName":"EmptyIterator","ranges":[{"startOffset":14494,"endOffset":14549,"count":1}],"isBlockCoverage":true},{"functionName":"FixedLengthListMixin","ranges":[{"startOffset":14577,"endOffset":14616,"count":0}],"isBlockCoverage":false},{"functionName":"UnmodifiableListMixin","ranges":[{"startOffset":14645,"endOffset":14685,"count":0}],"isBlockCoverage":false},{"functionName":"UnmodifiableListBase","ranges":[{"startOffset":14713,"endOffset":14752,"count":0}],"isBlockCoverage":false},{"functionName":"ReversedListIterable","ranges":[{"startOffset":14780,"endOffset":14871,"count":1}],"isBlockCoverage":true},{"functionName":"Symbol","ranges":[{"startOffset":14885,"endOffset":14946,"count":1}],"isBlockCoverage":true},{"functionName":"ConstantMap__throwUnmodifiable","ranges":[{"startOffset":14984,"endOffset":15086,"count":0}],"isBlockCoverage":false},{"functionName":"instantiate1","ranges":[{"startOffset":15106,"endOffset":15248,"count":0}],"isBlockCoverage":false},{"functionName":"unminifyOrTag","ranges":[{"startOffset":15269,"endOffset":15468,"count":0}],"isBlockCoverage":false},{"functionName":"isJsIndexable","ranges":[{"startOffset":15489,"endOffset":15722,"count":0}],"isBlockCoverage":false},{"functionName":"S","ranges":[{"startOffset":15731,"endOffset":16230,"count":1},{"startOffset":15821,"endOffset":16229,"count":0}],"isBlockCoverage":true},{"functionName":"Primitives_objectHashCode","ranges":[{"startOffset":16263,"endOffset":16463,"count":1}],"isBlockCoverage":true},{"functionName":"Primitives_parseInt","ranges":[{"startOffset":16490,"endOffset":17741,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_objectTypeName","ranges":[{"startOffset":17774,"endOffset":17874,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives__objectTypeNameNewRti","ranges":[{"startOffset":17914,"endOffset":18695,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives__saneNativeClassName","ranges":[{"startOffset":18734,"endOffset":18825,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_dateNow","ranges":[{"startOffset":18851,"endOffset":18894,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_initTicker","ranges":[{"startOffset":18923,"endOffset":19555,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_currentUri","ranges":[{"startOffset":19584,"endOffset":19683,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives__fromCharCodeApply","ranges":[{"startOffset":19720,"endOffset":20112,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_stringFromCodePoints","ranges":[{"startOffset":20151,"endOffset":20858,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_stringFromCharCodes","ranges":[{"startOffset":20896,"endOffset":21417,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_stringFromNativeUint8List","ranges":[{"startOffset":21461,"endOffset":21888,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_stringFromCharCode","ranges":[{"startOffset":21925,"endOffset":22438,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_lazyAsJsDate","ranges":[{"startOffset":22469,"endOffset":22610,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_getYear","ranges":[{"startOffset":22636,"endOffset":22752,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_getMonth","ranges":[{"startOffset":22779,"endOffset":22892,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_getDay","ranges":[{"startOffset":22917,"endOffset":23029,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_getHours","ranges":[{"startOffset":23056,"endOffset":23169,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_getMinutes","ranges":[{"startOffset":23198,"endOffset":23313,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_getSeconds","ranges":[{"startOffset":23342,"endOffset":23457,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_getMilliseconds","ranges":[{"startOffset":23491,"endOffset":23611,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_getProperty","ranges":[{"startOffset":23641,"endOffset":23862,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_setProperty","ranges":[{"startOffset":23892,"endOffset":24121,"count":0}],"isBlockCoverage":false},{"functionName":"iae","ranges":[{"startOffset":24132,"endOffset":24219,"count":0}],"isBlockCoverage":false},{"functionName":"ioore","ranges":[{"startOffset":24232,"endOffset":24397,"count":0}],"isBlockCoverage":false},{"functionName":"diagnoseIndexError","ranges":[{"startOffset":24423,"endOffset":24943,"count":0}],"isBlockCoverage":false},{"functionName":"diagnoseRangeError","ranges":[{"startOffset":24969,"endOffset":25354,"count":0}],"isBlockCoverage":false},{"functionName":"argumentErrorValue","ranges":[{"startOffset":25380,"endOffset":25464,"count":0}],"isBlockCoverage":false},{"functionName":"checkNum","ranges":[{"startOffset":25480,"endOffset":25619,"count":0}],"isBlockCoverage":false},{"functionName":"wrapException","ranges":[{"startOffset":25640,"endOffset":26027,"count":0}],"isBlockCoverage":false},{"functionName":"toStringWrapper","ranges":[{"startOffset":26050,"endOffset":26116,"count":0}],"isBlockCoverage":false},{"functionName":"throwExpression","ranges":[{"startOffset":26139,"endOffset":26192,"count":0}],"isBlockCoverage":false},{"functionName":"throwConcurrentModificationError","ranges":[{"startOffset":26232,"endOffset":26333,"count":0}],"isBlockCoverage":false},{"functionName":"TypeErrorDecoder_extractPattern","ranges":[{"startOffset":26372,"endOffset":27376,"count":0}],"isBlockCoverage":false},{"functionName":"TypeErrorDecoder_provokeCallErrorOn","ranges":[{"startOffset":27419,"endOffset":27663,"count":0}],"isBlockCoverage":false},{"functionName":"TypeErrorDecoder_provokePropertyErrorOn","ranges":[{"startOffset":27710,"endOffset":27892,"count":0}],"isBlockCoverage":false},{"functionName":"NullError$","ranges":[{"startOffset":27910,"endOffset":28020,"count":0}],"isBlockCoverage":false},{"functionName":"JsNoSuchMethodError$","ranges":[{"startOffset":28048,"endOffset":28232,"count":0}],"isBlockCoverage":false},{"functionName":"unwrapException","ranges":[{"startOffset":28255,"endOffset":32748,"count":0}],"isBlockCoverage":false},{"functionName":"getTraceFromException","ranges":[{"startOffset":32777,"endOffset":33142,"count":1},{"startOffset":32881,"endOffset":32909,"count":0},{"startOffset":32947,"endOffset":32983,"count":0},{"startOffset":33055,"endOffset":33068,"count":0}],"isBlockCoverage":true},{"functionName":"objectHashCode","ranges":[{"startOffset":33164,"endOffset":33346,"count":1}],"isBlockCoverage":true},{"functionName":"fillLiteralMap","ranges":[{"startOffset":33368,"endOffset":33829,"count":1}],"isBlockCoverage":true},{"functionName":"fillLiteralSet","ranges":[{"startOffset":33851,"endOffset":34149,"count":1}],"isBlockCoverage":true},{"functionName":"invokeClosure","ranges":[{"startOffset":34170,"endOffset":34749,"count":1},{"startOffset":34441,"endOffset":34493,"count":0},{"startOffset":34502,"endOffset":34560,"count":0},{"startOffset":34569,"endOffset":34633,"count":0},{"startOffset":34641,"endOffset":34748,"count":0}],"isBlockCoverage":true},{"functionName":"convertDartClosureToJS","ranges":[{"startOffset":34779,"endOffset":35232,"count":1},{"startOffset":34862,"endOffset":34874,"count":0}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":34979,"endOffset":35131,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":35029,"endOffset":35122,"count":1}],"isBlockCoverage":true},{"functionName":"Closure_fromTearOff","ranges":[{"startOffset":35259,"endOffset":37399,"count":1},{"startOffset":36000,"endOffset":36017,"count":0},{"startOffset":37093,"endOffset":37187,"count":0}],"isBlockCoverage":true},{"functionName":"static_tear_off","ranges":[{"startOffset":35831,"endOffset":35899,"count":0}],"isBlockCoverage":false},{"functionName":"Closure__computeSignatureFunctionNewRti","ranges":[{"startOffset":37446,"endOffset":38243,"count":1},{"startOffset":37726,"endOffset":38242,"count":0}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":37580,"endOffset":37686,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":37620,"endOffset":37675,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":37997,"endOffset":38133,"count":0}],"isBlockCoverage":false},{"functionName":"Closure_cspForwardCall","ranges":[{"startOffset":38273,"endOffset":39658,"count":1},{"startOffset":38399,"endOffset":38406,"count":0},{"startOffset":38418,"endOffset":38573,"count":0},{"startOffset":38582,"endOffset":38739,"count":0},{"startOffset":38748,"endOffset":38911,"count":0},{"startOffset":38920,"endOffset":39089,"count":0},{"startOffset":39098,"endOffset":39273,"count":0},{"startOffset":39282,"endOffset":39463,"count":0}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":38443,"endOffset":38553,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":38607,"endOffset":38719,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":38773,"endOffset":38891,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":38945,"endOffset":39069,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":39123,"endOffset":39253,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":39307,"endOffset":39443,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":39498,"endOffset":39623,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":39534,"endOffset":39610,"count":0}],"isBlockCoverage":false},{"functionName":"Closure_forwardCallTo","ranges":[{"startOffset":39687,"endOffset":41342,"count":1},{"startOffset":40050,"endOffset":40076,"count":0},{"startOffset":40341,"endOffset":40358,"count":0},{"startOffset":40594,"endOffset":40672,"count":0},{"startOffset":40960,"endOffset":40977,"count":0},{"startOffset":41199,"endOffset":41277,"count":0}],"isBlockCoverage":true},{"functionName":"Closure_cspForwardInterceptedCall","ranges":[{"startOffset":41383,"endOffset":43149,"count":0}],"isBlockCoverage":false},{"functionName":"Closure_forwardInterceptedCallTo","ranges":[{"startOffset":43189,"endOffset":44760,"count":1},{"startOffset":43766,"endOffset":43792,"count":0},{"startOffset":43880,"endOffset":43956,"count":0},{"startOffset":44175,"endOffset":44192,"count":0},{"startOffset":44651,"endOffset":44668,"count":0}],"isBlockCoverage":true},{"functionName":"closureFromTearOff","ranges":[{"startOffset":44786,"endOffset":45024,"count":1}],"isBlockCoverage":true},{"functionName":"BoundClosure_evalRecipe","ranges":[{"startOffset":45055,"endOffset":45190,"count":0}],"isBlockCoverage":false},{"functionName":"BoundClosure_evalRecipeIntercepted","ranges":[{"startOffset":45232,"endOffset":45371,"count":0}],"isBlockCoverage":false},{"functionName":"BoundClosure_selfOf","ranges":[{"startOffset":45398,"endOffset":45451,"count":0}],"isBlockCoverage":false},{"functionName":"BoundClosure_receiverOf","ranges":[{"startOffset":45482,"endOffset":45539,"count":0}],"isBlockCoverage":false},{"functionName":"BoundClosure_computeFieldNamed","ranges":[{"startOffset":45577,"endOffset":45937,"count":1}],"isBlockCoverage":true},{"functionName":"boolConversionCheck","ranges":[{"startOffset":45964,"endOffset":46094,"count":1},{"startOffset":46015,"endOffset":46068,"count":0}],"isBlockCoverage":true},{"functionName":"extractFunctionTypeObjectFromInternal","ranges":[{"startOffset":46139,"endOffset":46420,"count":0}],"isBlockCoverage":false},{"functionName":"TypeErrorImplementation$","ranges":[{"startOffset":46452,"endOffset":46662,"count":0}],"isBlockCoverage":false},{"functionName":"_typeDescription","ranges":[{"startOffset":46686,"endOffset":47058,"count":0}],"isBlockCoverage":false},{"functionName":"assertTest","ranges":[{"startOffset":47076,"endOffset":47290,"count":1},{"startOffset":47149,"endOffset":47289,"count":0}],"isBlockCoverage":true},{"functionName":"assertThrow","ranges":[{"startOffset":47309,"endOffset":47395,"count":0}],"isBlockCoverage":false},{"functionName":"assertHelper","ranges":[{"startOffset":47415,"endOffset":47533,"count":1},{"startOffset":47480,"endOffset":47527,"count":0}],"isBlockCoverage":true},{"functionName":"throwCyclicInit","ranges":[{"startOffset":47556,"endOffset":47658,"count":0}],"isBlockCoverage":false},{"functionName":"RuntimeError$","ranges":[{"startOffset":47679,"endOffset":47746,"count":0}],"isBlockCoverage":false},{"functionName":"getIsolateAffinityTag","ranges":[{"startOffset":47775,"endOffset":47838,"count":0}],"isBlockCoverage":false},{"functionName":"setRuntimeTypeInfo","ranges":[{"startOffset":47864,"endOffset":47973,"count":1}],"isBlockCoverage":true},{"functionName":"getRuntimeTypeInfo","ranges":[{"startOffset":47999,"endOffset":48095,"count":0}],"isBlockCoverage":false},{"functionName":"getRuntimeTypeArguments","ranges":[{"startOffset":48126,"endOffset":48282,"count":0}],"isBlockCoverage":false},{"functionName":"runtimeTypeToString","ranges":[{"startOffset":48309,"endOffset":48378,"count":0}],"isBlockCoverage":false},{"functionName":"_runtimeTypeToString","ranges":[{"startOffset":48406,"endOffset":49897,"count":0}],"isBlockCoverage":false},{"functionName":"_functionRtiToString0","ranges":[{"startOffset":49926,"endOffset":52750,"count":0}],"isBlockCoverage":false},{"functionName":"_joinArguments","ranges":[{"startOffset":52772,"endOffset":53457,"count":0}],"isBlockCoverage":false},{"functionName":"getRuntimeType","ranges":[{"startOffset":53479,"endOffset":53665,"count":0}],"isBlockCoverage":false},{"functionName":"substitute","ranges":[{"startOffset":53683,"endOffset":54227,"count":0}],"isBlockCoverage":false},{"functionName":"computeSignature","ranges":[{"startOffset":54251,"endOffset":54444,"count":0}],"isBlockCoverage":false},{"functionName":"invokeOn","ranges":[{"startOffset":54460,"endOffset":54686,"count":0}],"isBlockCoverage":false},{"functionName":"defineProperty","ranges":[{"startOffset":54708,"endOffset":54861,"count":0}],"isBlockCoverage":false},{"functionName":"lookupAndCacheInterceptor","ranges":[{"startOffset":54894,"endOffset":57451,"count":0}],"isBlockCoverage":false},{"functionName":"patchInteriorProto","ranges":[{"startOffset":57477,"endOffset":57764,"count":0}],"isBlockCoverage":false},{"functionName":"makeLeafDispatchRecord","ranges":[{"startOffset":57794,"endOffset":57929,"count":1}],"isBlockCoverage":true},{"functionName":"makeDefaultDispatchRecord","ranges":[{"startOffset":57962,"endOffset":58233,"count":1}],"isBlockCoverage":true},{"functionName":"initNativeDispatch","ranges":[{"startOffset":58259,"endOffset":58415,"count":1},{"startOffset":58325,"endOffset":58332,"count":0}],"isBlockCoverage":true},{"functionName":"initNativeDispatchContinue","ranges":[{"startOffset":58449,"endOffset":59729,"count":1}],"isBlockCoverage":true},{"functionName":"fun","ranges":[{"startOffset":58828,"endOffset":58850,"count":0}],"isBlockCoverage":false},{"functionName":"initHooks","ranges":[{"startOffset":59746,"endOffset":61000,"count":1},{"startOffset":60255,"endOffset":60668,"count":0}],"isBlockCoverage":true},{"functionName":"applyHooksTransformer","ranges":[{"startOffset":61029,"endOffset":61107,"count":1}],"isBlockCoverage":true},{"functionName":"JSSyntaxRegExp_makeNative","ranges":[{"startOffset":61140,"endOffset":61765,"count":0}],"isBlockCoverage":false},{"functionName":"_MatchImplementation$","ranges":[{"startOffset":61794,"endOffset":61977,"count":0}],"isBlockCoverage":false},{"functionName":"stringContainsUnchecked","ranges":[{"startOffset":62008,"endOffset":62496,"count":0}],"isBlockCoverage":false},{"functionName":"escapeReplacement","ranges":[{"startOffset":62521,"endOffset":62671,"count":0}],"isBlockCoverage":false},{"functionName":"stringReplaceFirstRE","ranges":[{"startOffset":62699,"endOffset":62974,"count":0}],"isBlockCoverage":false},{"functionName":"quoteStringForRegExp","ranges":[{"startOffset":63002,"endOffset":63154,"count":0}],"isBlockCoverage":false},{"functionName":"stringReplaceAllUnchecked","ranges":[{"startOffset":63187,"endOffset":63770,"count":0}],"isBlockCoverage":false},{"functionName":"stringReplaceAllUncheckedString","ranges":[{"startOffset":63809,"endOffset":64503,"count":0}],"isBlockCoverage":false},{"functionName":"_stringIdentity","ranges":[{"startOffset":64526,"endOffset":64571,"count":0}],"isBlockCoverage":false},{"functionName":"stringReplaceAllFuncUnchecked","ranges":[{"startOffset":64608,"endOffset":65417,"count":0}],"isBlockCoverage":false},{"functionName":"stringReplaceFirstUnchecked","ranges":[{"startOffset":65452,"endOffset":66440,"count":0}],"isBlockCoverage":false},{"functionName":"stringReplaceRangeUnchecked","ranges":[{"startOffset":66475,"endOffset":66661,"count":0}],"isBlockCoverage":false},{"functionName":"ConstantMap","ranges":[{"startOffset":66680,"endOffset":66710,"count":0}],"isBlockCoverage":false},{"functionName":"ConstantMap_map_closure","ranges":[{"startOffset":66741,"endOffset":66867,"count":0}],"isBlockCoverage":false},{"functionName":"ConstantStringMap","ranges":[{"startOffset":66892,"endOffset":67070,"count":1}],"isBlockCoverage":true},{"functionName":"_ConstantMapKeyIterable","ranges":[{"startOffset":67101,"endOffset":67204,"count":0}],"isBlockCoverage":false},{"functionName":"Instantiation","ranges":[{"startOffset":67225,"endOffset":67257,"count":0}],"isBlockCoverage":false},{"functionName":"Instantiation1","ranges":[{"startOffset":67279,"endOffset":67372,"count":0}],"isBlockCoverage":false},{"functionName":"Primitives_initTicker_closure","ranges":[{"startOffset":67409,"endOffset":67488,"count":0}],"isBlockCoverage":false},{"functionName":"TypeErrorDecoder","ranges":[{"startOffset":67512,"endOffset":67732,"count":0}],"isBlockCoverage":false},{"functionName":"NullError","ranges":[{"startOffset":67749,"endOffset":67846,"count":0}],"isBlockCoverage":false},{"functionName":"JsNoSuchMethodError","ranges":[{"startOffset":67873,"endOffset":68011,"count":0}],"isBlockCoverage":false},{"functionName":"UnknownJsTypeError","ranges":[{"startOffset":68037,"endOffset":68114,"count":0}],"isBlockCoverage":false},{"functionName":"ExceptionAndStackTrace","ranges":[{"startOffset":68144,"endOffset":68250,"count":0}],"isBlockCoverage":true},{"functionName":"unwrapException_saveStackTrace","ranges":[{"startOffset":68288,"endOffset":68359,"count":0}],"isBlockCoverage":false},{"functionName":"_StackTrace","ranges":[{"startOffset":68378,"endOffset":68464,"count":1}],"isBlockCoverage":true},{"functionName":"Closure","ranges":[{"startOffset":68479,"endOffset":68505,"count":0}],"isBlockCoverage":true},{"functionName":"TearOffClosure","ranges":[{"startOffset":68527,"endOffset":68560,"count":0}],"isBlockCoverage":false},{"functionName":"StaticClosure","ranges":[{"startOffset":68581,"endOffset":68613,"count":1}],"isBlockCoverage":true},{"functionName":"BoundClosure","ranges":[{"startOffset":68633,"endOffset":68784,"count":1}],"isBlockCoverage":true},{"functionName":"TypeErrorImplementation","ranges":[{"startOffset":68815,"endOffset":68884,"count":0}],"isBlockCoverage":false},{"functionName":"RuntimeError","ranges":[{"startOffset":68904,"endOffset":68962,"count":0}],"isBlockCoverage":false},{"functionName":"_AssertionError","ranges":[{"startOffset":68985,"endOffset":69046,"count":0}],"isBlockCoverage":false},{"functionName":"JsLinkedHashMap","ranges":[{"startOffset":69069,"endOffset":69306,"count":1}],"isBlockCoverage":true},{"functionName":"JsLinkedHashMap_values_closure","ranges":[{"startOffset":69344,"endOffset":69418,"count":0}],"isBlockCoverage":false},{"functionName":"JsLinkedHashMap_addAll_closure","ranges":[{"startOffset":69456,"endOffset":69530,"count":0}],"isBlockCoverage":false},{"functionName":"LinkedHashMapCell","ranges":[{"startOffset":69555,"endOffset":69713,"count":1}],"isBlockCoverage":true},{"functionName":"LinkedHashMapKeyIterable","ranges":[{"startOffset":69745,"endOffset":69849,"count":1}],"isBlockCoverage":true},{"functionName":"LinkedHashMapKeyIterator","ranges":[{"startOffset":69881,"endOffset":70079,"count":1}],"isBlockCoverage":true},{"functionName":"initHooks_closure","ranges":[{"startOffset":70104,"endOffset":70166,"count":1}],"isBlockCoverage":true},{"functionName":"initHooks_closure0","ranges":[{"startOffset":70192,"endOffset":70262,"count":1}],"isBlockCoverage":true},{"functionName":"initHooks_closure1","ranges":[{"startOffset":70288,"endOffset":70360,"count":1}],"isBlockCoverage":true},{"functionName":"JSSyntaxRegExp","ranges":[{"startOffset":70382,"endOffset":70553,"count":0}],"isBlockCoverage":false},{"functionName":"_MatchImplementation","ranges":[{"startOffset":70581,"endOffset":70646,"count":0}],"isBlockCoverage":false},{"functionName":"_AllMatchesIterable","ranges":[{"startOffset":70673,"endOffset":70803,"count":0}],"isBlockCoverage":false},{"functionName":"_AllMatchesIterator","ranges":[{"startOffset":70830,"endOffset":71016,"count":0}],"isBlockCoverage":false},{"functionName":"StringMatch","ranges":[{"startOffset":71035,"endOffset":71119,"count":0}],"isBlockCoverage":false},{"functionName":"_StringAllMatchesIterable","ranges":[{"startOffset":71152,"endOffset":71292,"count":0}],"isBlockCoverage":false},{"functionName":"_StringAllMatchesIterator","ranges":[{"startOffset":71325,"endOffset":71513,"count":0}],"isBlockCoverage":false},{"functionName":"_ensureNativeList","ranges":[{"startOffset":71538,"endOffset":71579,"count":0}],"isBlockCoverage":false},{"functionName":"NativeInt8List__create1","ranges":[{"startOffset":71610,"endOffset":71664,"count":0}],"isBlockCoverage":false},{"functionName":"_checkValidIndex","ranges":[{"startOffset":71688,"endOffset":71845,"count":1},{"startOffset":71782,"endOffset":71839,"count":0}],"isBlockCoverage":true},{"functionName":"_checkValidRange","ranges":[{"startOffset":71869,"endOffset":72275,"count":0}],"isBlockCoverage":false},{"functionName":"NativeByteBuffer","ranges":[{"startOffset":72299,"endOffset":72334,"count":0}],"isBlockCoverage":false},{"functionName":"NativeTypedData","ranges":[{"startOffset":72357,"endOffset":72391,"count":0}],"isBlockCoverage":false},{"functionName":"NativeByteData","ranges":[{"startOffset":72413,"endOffset":72446,"count":0}],"isBlockCoverage":false},{"functionName":"NativeTypedArray","ranges":[{"startOffset":72470,"endOffset":72505,"count":0}],"isBlockCoverage":false},{"functionName":"NativeTypedArrayOfDouble","ranges":[{"startOffset":72537,"endOffset":72580,"count":0}],"isBlockCoverage":false},{"functionName":"NativeTypedArrayOfInt","ranges":[{"startOffset":72609,"endOffset":72649,"count":0}],"isBlockCoverage":false},{"functionName":"NativeFloat32List","ranges":[{"startOffset":72674,"endOffset":72710,"count":0}],"isBlockCoverage":false},{"functionName":"NativeFloat64List","ranges":[{"startOffset":72735,"endOffset":72771,"count":0}],"isBlockCoverage":false},{"functionName":"NativeInt16List","ranges":[{"startOffset":72794,"endOffset":72828,"count":0}],"isBlockCoverage":false},{"functionName":"NativeInt32List","ranges":[{"startOffset":72851,"endOffset":72885,"count":0}],"isBlockCoverage":false},{"functionName":"NativeInt8List","ranges":[{"startOffset":72907,"endOffset":72940,"count":0}],"isBlockCoverage":false},{"functionName":"NativeUint16List","ranges":[{"startOffset":72964,"endOffset":72999,"count":0}],"isBlockCoverage":false},{"functionName":"NativeUint32List","ranges":[{"startOffset":73023,"endOffset":73058,"count":0}],"isBlockCoverage":false},{"functionName":"NativeUint8ClampedList","ranges":[{"startOffset":73088,"endOffset":73129,"count":0}],"isBlockCoverage":false},{"functionName":"NativeUint8List","ranges":[{"startOffset":73152,"endOffset":73186,"count":0}],"isBlockCoverage":false},{"functionName":"_NativeTypedArrayOfDouble_NativeTypedArray_ListMixin","ranges":[{"startOffset":73246,"endOffset":73317,"count":0}],"isBlockCoverage":false},{"functionName":"_NativeTypedArrayOfDouble_NativeTypedArray_ListMixin_FixedLengthListMixin","ranges":[{"startOffset":73398,"endOffset":73490,"count":0}],"isBlockCoverage":false},{"functionName":"_NativeTypedArrayOfInt_NativeTypedArray_ListMixin","ranges":[{"startOffset":73547,"endOffset":73615,"count":0}],"isBlockCoverage":false},{"functionName":"_NativeTypedArrayOfInt_NativeTypedArray_ListMixin_FixedLengthListMixin","ranges":[{"startOffset":73693,"endOffset":73782,"count":0}],"isBlockCoverage":false},{"functionName":"Rti__getFutureFromFutureOr","ranges":[{"startOffset":73816,"endOffset":74142,"count":0}],"isBlockCoverage":false},{"functionName":"Rti__isUnionOfFunctionType","ranges":[{"startOffset":74176,"endOffset":74375,"count":1}],"isBlockCoverage":true},{"functionName":"Rti__getInterfaceTypeArguments","ranges":[{"startOffset":74413,"endOffset":74497,"count":1}],"isBlockCoverage":true},{"functionName":"Rti__getBindingArguments","ranges":[{"startOffset":74529,"endOffset":74614,"count":1}],"isBlockCoverage":true},{"functionName":"Rti__getFunctionParameters","ranges":[{"startOffset":74648,"endOffset":74733,"count":1}],"isBlockCoverage":true},{"functionName":"Rti__getGenericFunctionBounds","ranges":[{"startOffset":74770,"endOffset":74855,"count":1}],"isBlockCoverage":true},{"functionName":"Rti__getCanonicalRecipe","ranges":[{"startOffset":74886,"endOffset":75056,"count":0}],"isBlockCoverage":false},{"functionName":"findType","ranges":[{"startOffset":75072,"endOffset":75154,"count":1}],"isBlockCoverage":true},{"functionName":"instantiatedGenericFunctionType","ranges":[{"startOffset":75193,"endOffset":76127,"count":0}],"isBlockCoverage":false},{"functionName":"_instantiate","ranges":[{"startOffset":76147,"endOffset":80529,"count":0}],"isBlockCoverage":false},{"functionName":"_instantiateArray","ranges":[{"startOffset":80554,"endOffset":81024,"count":0}],"isBlockCoverage":false},{"functionName":"_instantiateNamed","ranges":[{"startOffset":81049,"endOffset":81640,"count":0}],"isBlockCoverage":false},{"functionName":"_instantiateFunctionParameters","ranges":[{"startOffset":81678,"endOffset":82753,"count":0}],"isBlockCoverage":false},{"functionName":"closureFunctionType","ranges":[{"startOffset":82780,"endOffset":83037,"count":1},{"startOffset":83012,"endOffset":83036,"count":0}],"isBlockCoverage":true},{"functionName":"instanceOrFunctionType","ranges":[{"startOffset":83067,"endOffset":83352,"count":1}],"isBlockCoverage":true},{"functionName":"instanceType","ranges":[{"startOffset":83372,"endOffset":83710,"count":1},{"startOffset":83505,"endOffset":83545,"count":0}],"isBlockCoverage":true},{"functionName":"_arrayInstanceType","ranges":[{"startOffset":83736,"endOffset":83981,"count":1},{"startOffset":83939,"endOffset":83957,"count":0}],"isBlockCoverage":true},{"functionName":"_instanceType","ranges":[{"startOffset":84002,"endOffset":84127,"count":1},{"startOffset":84080,"endOffset":84120,"count":0}],"isBlockCoverage":true},{"functionName":"_instanceTypeFromConstructor","ranges":[{"startOffset":84163,"endOffset":84394,"count":1}],"isBlockCoverage":true},{"functionName":"_instanceTypeFromConstructorMiss","ranges":[{"startOffset":84434,"endOffset":84736,"count":1},{"startOffset":84532,"endOffset":84574,"count":0}],"isBlockCoverage":true},{"functionName":"getTypeFromTypesTable","ranges":[{"startOffset":84765,"endOffset":85054,"count":1}],"isBlockCoverage":true},{"functionName":"createRuntimeType","ranges":[{"startOffset":85079,"endOffset":85242,"count":1},{"startOffset":85168,"endOffset":85180,"count":0}],"isBlockCoverage":true},{"functionName":"typeLiteral","ranges":[{"startOffset":85261,"endOffset":85364,"count":1}],"isBlockCoverage":true},{"functionName":"_installSpecializedIsTest","ranges":[{"startOffset":85397,"endOffset":86499,"count":1},{"startOffset":85764,"endOffset":85806,"count":0},{"startOffset":85923,"endOffset":85939,"count":0}],"isBlockCoverage":true},{"functionName":"_generalIsTestImplementation","ranges":[{"startOffset":86535,"endOffset":86701,"count":1}],"isBlockCoverage":true},{"functionName":"_isTestViaProperty","ranges":[{"startOffset":86727,"endOffset":86913,"count":1}],"isBlockCoverage":true},{"functionName":"_generalAsCheckImplementation","ranges":[{"startOffset":86950,"endOffset":87273,"count":1},{"startOffset":87022,"endOffset":87036,"count":0},{"startOffset":87112,"endOffset":87272,"count":0}],"isBlockCoverage":true},{"functionName":"_generalTypeCheckImplementation","ranges":[{"startOffset":87312,"endOffset":87635,"count":1},{"startOffset":87474,"endOffset":87634,"count":0}],"isBlockCoverage":true},{"functionName":"checkTypeBound","ranges":[{"startOffset":87657,"endOffset":88102,"count":0}],"isBlockCoverage":false},{"functionName":"_Error_compose","ranges":[{"startOffset":88124,"endOffset":88496,"count":0}],"isBlockCoverage":false},{"functionName":"_CastError$fromMessage","ranges":[{"startOffset":88526,"endOffset":88607,"count":0}],"isBlockCoverage":false},{"functionName":"_CastError__CastError$forType","ranges":[{"startOffset":88644,"endOffset":88759,"count":0}],"isBlockCoverage":false},{"functionName":"_TypeError$fromMessage","ranges":[{"startOffset":88789,"endOffset":88870,"count":0}],"isBlockCoverage":false},{"functionName":"_TypeError__TypeError$forType","ranges":[{"startOffset":88907,"endOffset":89022,"count":0}],"isBlockCoverage":false},{"functionName":"_isTop","ranges":[{"startOffset":89036,"endOffset":89079,"count":1}],"isBlockCoverage":true},{"functionName":"_asTop","ranges":[{"startOffset":89093,"endOffset":89138,"count":1}],"isBlockCoverage":true},{"functionName":"_isBool","ranges":[{"startOffset":89153,"endOffset":89227,"count":1}],"isBlockCoverage":true},{"functionName":"_asBoolNullable","ranges":[{"startOffset":89250,"endOffset":89471,"count":1},{"startOffset":89387,"endOffset":89470,"count":0}],"isBlockCoverage":true},{"functionName":"_checkBoolNullable","ranges":[{"startOffset":89497,"endOffset":89718,"count":1},{"startOffset":89634,"endOffset":89717,"count":0}],"isBlockCoverage":true},{"functionName":"_asDoubleNullable","ranges":[{"startOffset":89743,"endOffset":89956,"count":0}],"isBlockCoverage":false},{"functionName":"_checkDoubleNullable","ranges":[{"startOffset":89984,"endOffset":90197,"count":0}],"isBlockCoverage":false},{"functionName":"_isInt","ranges":[{"startOffset":90211,"endOffset":90308,"count":1}],"isBlockCoverage":true},{"functionName":"_asIntNullable","ranges":[{"startOffset":90330,"endOffset":90573,"count":1},{"startOffset":90490,"endOffset":90572,"count":0}],"isBlockCoverage":true},{"functionName":"_checkIntNullable","ranges":[{"startOffset":90598,"endOffset":90841,"count":1},{"startOffset":90709,"endOffset":90840,"count":0}],"isBlockCoverage":true},{"functionName":"_isNum","ranges":[{"startOffset":90855,"endOffset":90919,"count":1}],"isBlockCoverage":true},{"functionName":"_asNumNullable","ranges":[{"startOffset":90941,"endOffset":91151,"count":1},{"startOffset":91019,"endOffset":91150,"count":0}],"isBlockCoverage":true},{"functionName":"_checkNumNullable","ranges":[{"startOffset":91176,"endOffset":91386,"count":0}],"isBlockCoverage":false},{"functionName":"_isString","ranges":[{"startOffset":91403,"endOffset":91467,"count":1}],"isBlockCoverage":true},{"functionName":"_asStringNullable","ranges":[{"startOffset":91492,"endOffset":91705,"count":1},{"startOffset":91619,"endOffset":91704,"count":0}],"isBlockCoverage":true},{"functionName":"_checkStringNullable","ranges":[{"startOffset":91733,"endOffset":91946,"count":1},{"startOffset":91811,"endOffset":91945,"count":0}],"isBlockCoverage":true},{"functionName":"_rtiArrayToString","ranges":[{"startOffset":91971,"endOffset":92203,"count":0}],"isBlockCoverage":false},{"functionName":"_functionRtiToString","ranges":[{"startOffset":92231,"endOffset":95348,"count":0}],"isBlockCoverage":false},{"functionName":"_rtiToString","ranges":[{"startOffset":95368,"endOffset":96985,"count":0}],"isBlockCoverage":false},{"functionName":"_unminifyOrTag","ranges":[{"startOffset":97007,"endOffset":97195,"count":0}],"isBlockCoverage":false},{"functionName":"_Universe_findRule","ranges":[{"startOffset":97221,"endOffset":97393,"count":1},{"startOffset":97343,"endOffset":97368,"count":0}],"isBlockCoverage":true},{"functionName":"_Universe_findErasedType","ranges":[{"startOffset":97425,"endOffset":98058,"count":1},{"startOffset":97640,"endOffset":98052,"count":0}],"isBlockCoverage":true},{"functionName":"_Universe_addRules","ranges":[{"startOffset":98084,"endOffset":98173,"count":1}],"isBlockCoverage":true},{"functionName":"_Universe_addErasedTypes","ranges":[{"startOffset":98205,"endOffset":98294,"count":1}],"isBlockCoverage":true},{"functionName":"_Universe_eval","ranges":[{"startOffset":98316,"endOffset":98586,"count":1}],"isBlockCoverage":true},{"functionName":"_Universe_evalInEnvironment","ranges":[{"startOffset":98621,"endOffset":99004,"count":1}],"isBlockCoverage":true},{"functionName":"_Universe_bind","ranges":[{"startOffset":99026,"endOffset":99702,"count":1},{"startOffset":99328,"endOffset":99370,"count":0},{"startOffset":99578,"endOffset":99620,"count":0}],"isBlockCoverage":true},{"functionName":"_Universe__parseRecipe","ranges":[{"startOffset":99732,"endOffset":99879,"count":1}],"isBlockCoverage":true},{"functionName":"_Universe__finishRti","ranges":[{"startOffset":99907,"endOffset":100268,"count":1},{"startOffset":100023,"endOffset":100065,"count":0}],"isBlockCoverage":true},{"functionName":"_Universe__lookupTerminalRti","ranges":[{"startOffset":100304,"endOffset":100628,"count":1}],"isBlockCoverage":true},{"functionName":"_Universe__lookupUnaryRti","ranges":[{"startOffset":100661,"endOffset":101026,"count":1}],"isBlockCoverage":true},{"functionName":"_Universe__lookupGenericFunctionParameterRti","ranges":[{"startOffset":101078,"endOffset":101456,"count":1}],"isBlockCoverage":true},{"functionName":"_Universe__canonicalRecipeJoin","ranges":[{"startOffset":101494,"endOffset":101845,"count":1},{"startOffset":101750,"endOffset":101792,"count":0}],"isBlockCoverage":true},{"functionName":"_Universe__canonicalRecipeJoinNamed","ranges":[{"startOffset":101888,"endOffset":102332,"count":0}],"isBlockCoverage":false},{"functionName":"_Universe__lookupInterfaceRti","ranges":[{"startOffset":102369,"endOffset":102971,"count":1}],"isBlockCoverage":true},{"functionName":"_Universe__lookupBindingRti","ranges":[{"startOffset":103006,"endOffset":103877,"count":1},{"startOffset":103457,"endOffset":103499,"count":0}],"isBlockCoverage":true},{"functionName":"_Universe__lookupFunctionRti","ranges":[{"startOffset":103913,"endOffset":105417,"count":1},{"startOffset":104216,"endOffset":104258,"count":0},{"startOffset":104965,"endOffset":105084,"count":0}],"isBlockCoverage":true},{"functionName":"_Universe__lookupGenericFunctionRti","ranges":[{"startOffset":105460,"endOffset":106050,"count":1},{"startOffset":105635,"endOffset":105677,"count":0},{"startOffset":105817,"endOffset":105830,"count":0}],"isBlockCoverage":true},{"functionName":"_Parser_create","ranges":[{"startOffset":106072,"endOffset":106187,"count":1}],"isBlockCoverage":true},{"functionName":"_Parser_parse","ranges":[{"startOffset":106208,"endOffset":111999,"count":1},{"startOffset":106817,"endOffset":106880,"count":0},{"startOffset":106989,"endOffset":107018,"count":0},{"startOffset":107031,"endOffset":107137,"count":0},{"startOffset":107388,"endOffset":107493,"count":0},{"startOffset":108690,"endOffset":108784,"count":0},{"startOffset":108797,"endOffset":109122,"count":0},{"startOffset":109135,"endOffset":109460,"count":0},{"startOffset":109682,"endOffset":109703,"count":0},{"startOffset":110356,"endOffset":110440,"count":0},{"startOffset":111456,"endOffset":111561,"count":0},{"startOffset":111574,"endOffset":111816,"count":0},{"startOffset":111829,"endOffset":111880,"count":0}],"isBlockCoverage":true},{"functionName":"_Parser_handleDigit","ranges":[{"startOffset":112026,"endOffset":112337,"count":1},{"startOffset":112242,"endOffset":112290,"count":0}],"isBlockCoverage":true},{"functionName":"_Parser_handleIdentifier","ranges":[{"startOffset":112369,"endOffset":113633,"count":1},{"startOffset":112644,"endOffset":112650,"count":0},{"startOffset":113401,"endOffset":113494,"count":0}],"isBlockCoverage":true},{"functionName":"_Parser_handleExtendedOperations","ranges":[{"startOffset":113673,"endOffset":114066,"count":0}],"isBlockCoverage":false},{"functionName":"_Parser_toType","ranges":[{"startOffset":114088,"endOffset":114385,"count":1}],"isBlockCoverage":true},{"functionName":"_Parser_toTypes","ranges":[{"startOffset":114408,"endOffset":114605,"count":1}],"isBlockCoverage":true},{"functionName":"_Parser_toTypesNamed","ranges":[{"startOffset":114633,"endOffset":114876,"count":0}],"isBlockCoverage":false},{"functionName":"_Parser_indexToType","ranges":[{"startOffset":114903,"endOffset":115904,"count":1},{"startOffset":115075,"endOffset":115162,"count":0},{"startOffset":115556,"endOffset":115639,"count":0},{"startOffset":115790,"endOffset":115903,"count":0}],"isBlockCoverage":true},{"functionName":"_isSubtype","ranges":[{"startOffset":115922,"endOffset":118887,"count":1},{"startOffset":116182,"endOffset":116194,"count":0},{"startOffset":116235,"endOffset":116248,"count":0},{"startOffset":116365,"endOffset":116512,"count":0},{"startOffset":116574,"endOffset":116694,"count":0},{"startOffset":116718,"endOffset":116850,"count":0},{"startOffset":116874,"endOffset":117119,"count":0},{"startOffset":117143,"endOffset":117280,"count":0},{"startOffset":117431,"endOffset":117542,"count":0},{"startOffset":117566,"endOffset":117698,"count":0},{"startOffset":117735,"endOffset":117748,"count":0},{"startOffset":117932,"endOffset":117944,"count":0},{"startOffset":117981,"endOffset":117994,"count":0},{"startOffset":118164,"endOffset":118177,"count":0},{"startOffset":118216,"endOffset":118238,"count":0},{"startOffset":118278,"endOffset":118300,"count":0},{"startOffset":118576,"endOffset":118588,"count":0},{"startOffset":118615,"endOffset":118628,"count":0},{"startOffset":118768,"endOffset":118781,"count":0},{"startOffset":118861,"endOffset":118886,"count":0}],"isBlockCoverage":true},{"functionName":"_isFunctionSubtype","ranges":[{"startOffset":118913,"endOffset":121867,"count":1},{"startOffset":119567,"endOffset":119580,"count":0},{"startOffset":120006,"endOffset":120019,"count":0},{"startOffset":120482,"endOffset":120495,"count":0},{"startOffset":120682,"endOffset":120695,"count":0},{"startOffset":120916,"endOffset":120929,"count":0},{"startOffset":120992,"endOffset":121171,"count":0},{"startOffset":121437,"endOffset":121842,"count":0}],"isBlockCoverage":true},{"functionName":"_isInterfaceSubtype","ranges":[{"startOffset":121894,"endOffset":123121,"count":1},{"startOffset":122175,"endOffset":122584,"count":0},{"startOffset":122669,"endOffset":122682,"count":0},{"startOffset":123083,"endOffset":123096,"count":0}],"isBlockCoverage":true},{"functionName":"typeEqual","ranges":[{"startOffset":123138,"endOffset":124947,"count":1},{"startOffset":123229,"endOffset":123426,"count":0},{"startOffset":123435,"endOffset":123442,"count":0},{"startOffset":123451,"endOffset":123518,"count":0},{"startOffset":123527,"endOffset":123808,"count":0},{"startOffset":123817,"endOffset":124067,"count":0},{"startOffset":124076,"endOffset":124623,"count":0},{"startOffset":124632,"endOffset":124892,"count":0},{"startOffset":124901,"endOffset":124933,"count":0}],"isBlockCoverage":true},{"functionName":"typesEqual","ranges":[{"startOffset":124965,"endOffset":125245,"count":1},{"startOffset":125093,"endOffset":125106,"count":0},{"startOffset":125207,"endOffset":125220,"count":0}],"isBlockCoverage":true},{"functionName":"namedTypesEqual","ranges":[{"startOffset":125268,"endOffset":125761,"count":0}],"isBlockCoverage":false},{"functionName":"isLegacyTopType","ranges":[{"startOffset":125784,"endOffset":125838,"count":1}],"isBlockCoverage":true},{"functionName":"isTopType","ranges":[{"startOffset":125855,"endOffset":126428,"count":1},{"startOffset":126261,"endOffset":126341,"count":0}],"isBlockCoverage":true},{"functionName":"_Utils_objectAssign","ranges":[{"startOffset":126455,"endOffset":126663,"count":1}],"isBlockCoverage":true},{"functionName":"Rti","ranges":[{"startOffset":126674,"endOffset":126970,"count":1}],"isBlockCoverage":true},{"functionName":"_FunctionParameters","ranges":[{"startOffset":126997,"endOffset":127123,"count":1}],"isBlockCoverage":true},{"functionName":"_Type","ranges":[{"startOffset":127136,"endOffset":127213,"count":1}],"isBlockCoverage":true},{"functionName":"_Error","ranges":[{"startOffset":127227,"endOffset":127252,"count":0}],"isBlockCoverage":false},{"functionName":"_CastError","ranges":[{"startOffset":127270,"endOffset":127327,"count":0}],"isBlockCoverage":false},{"functionName":"_TypeError","ranges":[{"startOffset":127345,"endOffset":127402,"count":0}],"isBlockCoverage":false},{"functionName":"extractKeys","ranges":[{"startOffset":127421,"endOffset":127537,"count":0}],"isBlockCoverage":false},{"functionName":"unmangleGlobalNameIfPreservedAnyways","ranges":[{"startOffset":127581,"endOffset":127649,"count":0}],"isBlockCoverage":false},{"functionName":"printString","ranges":[{"startOffset":127668,"endOffset":128115,"count":0}],"isBlockCoverage":false},{"functionName":"makeDispatchRecord","ranges":[{"startOffset":128153,"endOffset":128286,"count":1}],"isBlockCoverage":true},{"functionName":"getNativeInterceptor","ranges":[{"startOffset":128314,"endOffset":129994,"count":1},{"startOffset":128762,"endOffset":128776,"count":0},{"startOffset":128891,"endOffset":129041,"count":0},{"startOffset":129049,"endOffset":129138,"count":0},{"startOffset":129139,"endOffset":129190,"count":0},{"startOffset":129231,"endOffset":129993,"count":0}],"isBlockCoverage":true},{"functionName":"JSArray_JSArray$fixed","ranges":[{"startOffset":130023,"endOffset":130380,"count":0}],"isBlockCoverage":false},{"functionName":"JSArray_JSArray$markFixed","ranges":[{"startOffset":130413,"endOffset":130543,"count":0}],"isBlockCoverage":false},{"functionName":"JSArray_markFixedList","ranges":[{"startOffset":130572,"endOffset":130646,"count":1}],"isBlockCoverage":true},{"functionName":"JSString__isWhitespace","ranges":[{"startOffset":130676,"endOffset":131431,"count":0}],"isBlockCoverage":false},{"functionName":"JSString__skipLeadingWhitespace","ranges":[{"startOffset":131470,"endOffset":131788,"count":0}],"isBlockCoverage":false},{"functionName":"JSString__skipTrailingWhitespace","ranges":[{"startOffset":131828,"endOffset":132157,"count":0}],"isBlockCoverage":false},{"functionName":"getInterceptor$","ranges":[{"startOffset":132180,"endOffset":132943,"count":1},{"startOffset":132240,"endOffset":132368,"count":0},{"startOffset":132699,"endOffset":132825,"count":0}],"isBlockCoverage":true},{"functionName":"getInterceptor$ansx","ranges":[{"startOffset":132970,"endOffset":133556,"count":0}],"isBlockCoverage":false},{"functionName":"getInterceptor$asx","ranges":[{"startOffset":133582,"endOffset":134092,"count":1},{"startOffset":133715,"endOffset":133731,"count":0},{"startOffset":133848,"endOffset":133974,"count":0},{"startOffset":134039,"endOffset":134091,"count":0}],"isBlockCoverage":true},{"functionName":"getInterceptor$ax","ranges":[{"startOffset":134117,"endOffset":134551,"count":1},{"startOffset":134174,"endOffset":134190,"count":0},{"startOffset":134307,"endOffset":134433,"count":0}],"isBlockCoverage":true},{"functionName":"getInterceptor$n","ranges":[{"startOffset":134575,"endOffset":134848,"count":0}],"isBlockCoverage":false},{"functionName":"getInterceptor$s","ranges":[{"startOffset":134872,"endOffset":135145,"count":1},{"startOffset":134968,"endOffset":135144,"count":0}],"isBlockCoverage":true},{"functionName":"getInterceptor$x","ranges":[{"startOffset":135169,"endOffset":135526,"count":1},{"startOffset":135226,"endOffset":135242,"count":0},{"startOffset":135282,"endOffset":135408,"count":0},{"startOffset":135457,"endOffset":135473,"count":0}],"isBlockCoverage":true},{"functionName":"get$first$ax","ranges":[{"startOffset":135546,"endOffset":135636,"count":1}],"isBlockCoverage":true},{"functionName":"get$hashCode$","ranges":[{"startOffset":135657,"endOffset":135748,"count":1}],"isBlockCoverage":true},{"functionName":"get$isEmpty$asx","ranges":[{"startOffset":135771,"endOffset":135864,"count":1}],"isBlockCoverage":true},{"functionName":"get$iterator$ax","ranges":[{"startOffset":135887,"endOffset":135980,"count":1}],"isBlockCoverage":true},{"functionName":"get$last$ax","ranges":[{"startOffset":135999,"endOffset":136088,"count":0}],"isBlockCoverage":false},{"functionName":"get$length$asx","ranges":[{"startOffset":136110,"endOffset":136202,"count":1}],"isBlockCoverage":true},{"functionName":"get$message$x","ranges":[{"startOffset":136223,"endOffset":136314,"count":0}],"isBlockCoverage":false},{"functionName":"get$runtimeType$","ranges":[{"startOffset":136338,"endOffset":136432,"count":0}],"isBlockCoverage":false},{"functionName":"get$startsWith$s","ranges":[{"startOffset":136456,"endOffset":136550,"count":0}],"isBlockCoverage":false},{"functionName":"$add$ansx","ranges":[{"startOffset":136567,"endOffset":136756,"count":0}],"isBlockCoverage":false},{"functionName":"$eq$","ranges":[{"startOffset":136768,"endOffset":136998,"count":1}],"isBlockCoverage":true},{"functionName":"$index$asx","ranges":[{"startOffset":137016,"endOffset":137374,"count":0}],"isBlockCoverage":false},{"functionName":"$indexSet$ax","ranges":[{"startOffset":137394,"endOffset":137500,"count":1}],"isBlockCoverage":true},{"functionName":"_codeUnitAt$1$s","ranges":[{"startOffset":137523,"endOffset":137624,"count":1}],"isBlockCoverage":true},{"functionName":"_removeEventListener$3$x","ranges":[{"startOffset":137656,"endOffset":137782,"count":1}],"isBlockCoverage":true},{"functionName":"addEventListener$3$x","ranges":[{"startOffset":137810,"endOffset":137932,"count":1}],"isBlockCoverage":true},{"functionName":"allMatches$1$s","ranges":[{"startOffset":137954,"endOffset":138054,"count":0}],"isBlockCoverage":false},{"functionName":"allMatches$2$s","ranges":[{"startOffset":138076,"endOffset":138184,"count":0}],"isBlockCoverage":false},{"functionName":"codeUnitAt$1$s","ranges":[{"startOffset":138206,"endOffset":138306,"count":0}],"isBlockCoverage":false},{"functionName":"contains$1$asx","ranges":[{"startOffset":138328,"endOffset":138428,"count":0}],"isBlockCoverage":false},{"functionName":"elementAt$1$ax","ranges":[{"startOffset":138450,"endOffset":138550,"count":1}],"isBlockCoverage":true},{"functionName":"endsWith$1$s","ranges":[{"startOffset":138570,"endOffset":138668,"count":0}],"isBlockCoverage":false},{"functionName":"fillRange$3$ax","ranges":[{"startOffset":138690,"endOffset":138806,"count":1}],"isBlockCoverage":true},{"functionName":"map$1$1$ax","ranges":[{"startOffset":138824,"endOffset":138930,"count":0}],"isBlockCoverage":false},{"functionName":"matchAsPrefix$2$s","ranges":[{"startOffset":138955,"endOffset":139066,"count":0}],"isBlockCoverage":false},{"functionName":"padRight$1$s","ranges":[{"startOffset":139086,"endOffset":139184,"count":0}],"isBlockCoverage":false},{"functionName":"replaceRange$3$asx","ranges":[{"startOffset":139210,"endOffset":139330,"count":0}],"isBlockCoverage":false},{"functionName":"startsWith$1$s","ranges":[{"startOffset":139352,"endOffset":139452,"count":0}],"isBlockCoverage":false},{"functionName":"startsWith$2$s","ranges":[{"startOffset":139474,"endOffset":139582,"count":1}],"isBlockCoverage":true},{"functionName":"substring$1$s","ranges":[{"startOffset":139603,"endOffset":139702,"count":0}],"isBlockCoverage":false},{"functionName":"substring$2$s","ranges":[{"startOffset":139723,"endOffset":139830,"count":0}],"isBlockCoverage":false},{"functionName":"toRadixString$1$n","ranges":[{"startOffset":139855,"endOffset":139958,"count":0}],"isBlockCoverage":false},{"functionName":"toSet$0$ax","ranges":[{"startOffset":139976,"endOffset":140064,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0$","ranges":[{"startOffset":140083,"endOffset":140172,"count":0}],"isBlockCoverage":false},{"functionName":"trim$0$s","ranges":[{"startOffset":140188,"endOffset":140274,"count":0}],"isBlockCoverage":false},{"functionName":"Interceptor","ranges":[{"startOffset":140293,"endOffset":140323,"count":0}],"isBlockCoverage":false},{"functionName":"JSBool","ranges":[{"startOffset":140337,"endOffset":140362,"count":0}],"isBlockCoverage":false},{"functionName":"JSNull","ranges":[{"startOffset":140376,"endOffset":140401,"count":0}],"isBlockCoverage":false},{"functionName":"JSObject","ranges":[{"startOffset":140417,"endOffset":140444,"count":0}],"isBlockCoverage":false},{"functionName":"JavaScriptObject","ranges":[{"startOffset":140468,"endOffset":140503,"count":0}],"isBlockCoverage":false},{"functionName":"PlainJavaScriptObject","ranges":[{"startOffset":140532,"endOffset":140572,"count":0}],"isBlockCoverage":false},{"functionName":"UnknownJavaScriptObject","ranges":[{"startOffset":140603,"endOffset":140645,"count":0}],"isBlockCoverage":false},{"functionName":"JavaScriptFunction","ranges":[{"startOffset":140671,"endOffset":140708,"count":0}],"isBlockCoverage":false},{"functionName":"JSArray","ranges":[{"startOffset":140723,"endOffset":140772,"count":0}],"isBlockCoverage":true},{"functionName":"JSUnmodifiableArray","ranges":[{"startOffset":140799,"endOffset":140860,"count":0}],"isBlockCoverage":false},{"functionName":"ArrayIterator","ranges":[{"startOffset":140881,"endOffset":141052,"count":1}],"isBlockCoverage":true},{"functionName":"JSNumber","ranges":[{"startOffset":141068,"endOffset":141095,"count":0}],"isBlockCoverage":false},{"functionName":"JSInt","ranges":[{"startOffset":141108,"endOffset":141132,"count":0}],"isBlockCoverage":false},{"functionName":"JSDouble","ranges":[{"startOffset":141148,"endOffset":141175,"count":0}],"isBlockCoverage":false},{"functionName":"JSString","ranges":[{"startOffset":141191,"endOffset":141218,"count":0}],"isBlockCoverage":true},{"functionName":"_AsyncRun__initializeScheduleImmediate","ranges":[{"startOffset":141276,"endOffset":142083,"count":1},{"startOffset":141369,"endOffset":141433,"count":0},{"startOffset":141892,"endOffset":142082,"count":0}],"isBlockCoverage":true},{"functionName":"_AsyncRun__scheduleImmediateJsOverride","ranges":[{"startOffset":142129,"endOffset":142315,"count":0}],"isBlockCoverage":false},{"functionName":"_AsyncRun__scheduleImmediateWithSetImmediate","ranges":[{"startOffset":142367,"endOffset":142554,"count":0}],"isBlockCoverage":false},{"functionName":"_AsyncRun__scheduleImmediateWithTimer","ranges":[{"startOffset":142599,"endOffset":142705,"count":0}],"isBlockCoverage":false},{"functionName":"Timer__createTimer","ranges":[{"startOffset":142731,"endOffset":142922,"count":1},{"startOffset":142886,"endOffset":142889,"count":0}],"isBlockCoverage":true},{"functionName":"_TimerImpl$","ranges":[{"startOffset":142941,"endOffset":143084,"count":1}],"isBlockCoverage":true},{"functionName":"_TimerImpl$periodic","ranges":[{"startOffset":143111,"endOffset":143264,"count":0}],"isBlockCoverage":false},{"functionName":"_makeAsyncAwaitCompleter","ranges":[{"startOffset":143296,"endOffset":143454,"count":1}],"isBlockCoverage":true},{"functionName":"_asyncStartSync","ranges":[{"startOffset":143477,"endOffset":143617,"count":1}],"isBlockCoverage":true},{"functionName":"_asyncAwait","ranges":[{"startOffset":143636,"endOffset":143720,"count":1}],"isBlockCoverage":true},{"functionName":"_asyncReturn","ranges":[{"startOffset":143740,"endOffset":143811,"count":1}],"isBlockCoverage":true},{"functionName":"_asyncRethrow","ranges":[{"startOffset":143832,"endOffset":143960,"count":0}],"isBlockCoverage":false},{"functionName":"_awaitOnObject","ranges":[{"startOffset":143982,"endOffset":144686,"count":1},{"startOffset":144384,"endOffset":144441,"count":0}],"isBlockCoverage":true},{"functionName":"_wrapJsFunctionForAsync","ranges":[{"startOffset":144717,"endOffset":145220,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":144762,"endOffset":145053,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":144799,"endOffset":145044,"count":1},{"startOffset":144941,"endOffset":145034,"count":0}],"isBlockCoverage":true},{"functionName":"Future_Future","ranges":[{"startOffset":145241,"endOffset":145457,"count":1}],"isBlockCoverage":true},{"functionName":"Future_Future$microtask","ranges":[{"startOffset":145488,"endOffset":145706,"count":0}],"isBlockCoverage":false},{"functionName":"Future_Future$sync","ranges":[{"startOffset":145732,"endOffset":146777,"count":1},{"startOffset":145947,"endOffset":145961,"count":0},{"startOffset":146185,"endOffset":146771,"count":0}],"isBlockCoverage":true},{"functionName":"Future_Future$error","ranges":[{"startOffset":146804,"endOffset":147339,"count":0}],"isBlockCoverage":false},{"functionName":"Future_wait","ranges":[{"startOffset":147358,"endOffset":148702,"count":0}],"isBlockCoverage":false},{"functionName":"Future_forEach","ranges":[{"startOffset":148724,"endOffset":148925,"count":1}],"isBlockCoverage":true},{"functionName":"Future__kTrue","ranges":[{"startOffset":148946,"endOffset":148984,"count":0}],"isBlockCoverage":false},{"functionName":"Future_doWhile","ranges":[{"startOffset":149006,"endOffset":149408,"count":1}],"isBlockCoverage":true},{"functionName":"_completeWithErrorCallback","ranges":[{"startOffset":149442,"endOffset":149802,"count":0}],"isBlockCoverage":false},{"functionName":"_Future$zoneValue","ranges":[{"startOffset":149827,"endOffset":150023,"count":1}],"isBlockCoverage":true},{"functionName":"_Future__chainForeignFuture","ranges":[{"startOffset":150058,"endOffset":150653,"count":0}],"isBlockCoverage":false},{"functionName":"_Future__chainCoreFuture","ranges":[{"startOffset":150685,"endOffset":151411,"count":1},{"startOffset":150866,"endOffset":150958,"count":0},{"startOffset":150978,"endOffset":151135,"count":0}],"isBlockCoverage":true},{"functionName":"_Future__propagateToListeners","ranges":[{"startOffset":151448,"endOffset":155442,"count":1},{"startOffset":151952,"endOffset":152109,"count":0},{"startOffset":152235,"endOffset":152357,"count":0},{"startOffset":152661,"endOffset":152687,"count":0},{"startOffset":152790,"endOffset":152910,"count":0},{"startOffset":152958,"endOffset":153223,"count":0},{"startOffset":153845,"endOffset":153967,"count":0},{"startOffset":154108,"endOffset":154697,"count":0},{"startOffset":155231,"endOffset":155375,"count":0}],"isBlockCoverage":true},{"functionName":"_registerErrorHandler","ranges":[{"startOffset":155471,"endOffset":156025,"count":0}],"isBlockCoverage":false},{"functionName":"_microtaskLoop","ranges":[{"startOffset":156047,"endOffset":156321,"count":1}],"isBlockCoverage":true},{"functionName":"_startMicrotaskLoop","ranges":[{"startOffset":156348,"endOffset":156683,"count":1},{"startOffset":156577,"endOffset":156669,"count":0}],"isBlockCoverage":true},{"functionName":"_scheduleAsyncCallback","ranges":[{"startOffset":156713,"endOffset":157097,"count":1}],"isBlockCoverage":true},{"functionName":"_schedulePriorityAsyncCallback","ranges":[{"startOffset":157135,"endOffset":157721,"count":0}],"isBlockCoverage":false},{"functionName":"scheduleMicrotask","ranges":[{"startOffset":157746,"endOffset":158408,"count":1},{"startOffset":157973,"endOffset":158407,"count":0}],"isBlockCoverage":true},{"functionName":"Stream_Stream$fromFuture","ranges":[{"startOffset":158440,"endOffset":158865,"count":0}],"isBlockCoverage":false},{"functionName":"Stream_Stream$fromIterable","ranges":[{"startOffset":158899,"endOffset":159065,"count":1}],"isBlockCoverage":true},{"functionName":"StreamIterator_StreamIterator","ranges":[{"startOffset":159102,"endOffset":159288,"count":0}],"isBlockCoverage":false},{"functionName":"StreamController_StreamController","ranges":[{"startOffset":159329,"endOffset":159628,"count":1},{"startOffset":159516,"endOffset":159621,"count":0}],"isBlockCoverage":true},{"functionName":"_runGuarded","ranges":[{"startOffset":159647,"endOffset":159995,"count":1},{"startOffset":159819,"endOffset":159989,"count":0}],"isBlockCoverage":true},{"functionName":"_AddStreamState_makeErrorHandler","ranges":[{"startOffset":160035,"endOffset":160136,"count":0}],"isBlockCoverage":false},{"functionName":"_BufferingStreamSubscription$","ranges":[{"startOffset":160173,"endOffset":160505,"count":1},{"startOffset":160287,"endOffset":160290,"count":0}],"isBlockCoverage":true},{"functionName":"_nullDataHandler","ranges":[{"startOffset":160529,"endOffset":160552,"count":0}],"isBlockCoverage":false},{"functionName":"_nullErrorHandler","ranges":[{"startOffset":160577,"endOffset":160719,"count":0}],"isBlockCoverage":false},{"functionName":"_nullDoneHandler","ranges":[{"startOffset":160743,"endOffset":160761,"count":0}],"isBlockCoverage":false},{"functionName":"_runUserCode","ranges":[{"startOffset":160781,"endOffset":161431,"count":1},{"startOffset":160958,"endOffset":161425,"count":0}],"isBlockCoverage":true},{"functionName":"_cancelAndError","ranges":[{"startOffset":161454,"endOffset":161799,"count":0}],"isBlockCoverage":false},{"functionName":"_cancelAndErrorClosure","ranges":[{"startOffset":161829,"endOffset":161940,"count":1}],"isBlockCoverage":true},{"functionName":"_cancelAndValue","ranges":[{"startOffset":161963,"endOffset":162267,"count":1}],"isBlockCoverage":true},{"functionName":"Timer_Timer","ranges":[{"startOffset":162286,"endOffset":162516,"count":1},{"startOffset":162389,"endOffset":162433,"count":0}],"isBlockCoverage":true},{"functionName":"_ZoneSpecification$","ranges":[{"startOffset":162543,"endOffset":162986,"count":1}],"isBlockCoverage":true},{"functionName":"Zone__enter","ranges":[{"startOffset":163005,"endOffset":163218,"count":1}],"isBlockCoverage":true},{"functionName":"_parentDelegate","ranges":[{"startOffset":163241,"endOffset":163377,"count":1}],"isBlockCoverage":true},{"functionName":"_rootHandleUncaughtError","ranges":[{"startOffset":163409,"endOffset":163630,"count":0}],"isBlockCoverage":false},{"functionName":"_rootRun","ranges":[{"startOffset":163646,"endOffset":164117,"count":1},{"startOffset":164009,"endOffset":164010,"count":0}],"isBlockCoverage":true},{"functionName":"_rootRunUnary","ranges":[{"startOffset":164138,"endOffset":164675,"count":1},{"startOffset":164567,"endOffset":164568,"count":0}],"isBlockCoverage":true},{"functionName":"_rootRunBinary","ranges":[{"startOffset":164697,"endOffset":165297,"count":0}],"isBlockCoverage":false},{"functionName":"_rootRegisterCallback","ranges":[{"startOffset":165326,"endOffset":165413,"count":1}],"isBlockCoverage":true},{"functionName":"_rootRegisterUnaryCallback","ranges":[{"startOffset":165447,"endOffset":165567,"count":1}],"isBlockCoverage":true},{"functionName":"_rootRegisterBinaryCallback","ranges":[{"startOffset":165602,"endOffset":165740,"count":1}],"isBlockCoverage":true},{"functionName":"_rootErrorCallback","ranges":[{"startOffset":165766,"endOffset":165885,"count":0}],"isBlockCoverage":false},{"functionName":"_rootScheduleMicrotask","ranges":[{"startOffset":165915,"endOffset":166240,"count":1},{"startOffset":166160,"endOffset":166198,"count":0}],"isBlockCoverage":true},{"functionName":"_rootCreateTimer","ranges":[{"startOffset":166264,"endOffset":166506,"count":1}],"isBlockCoverage":true},{"functionName":"_rootCreatePeriodicTimer","ranges":[{"startOffset":166538,"endOffset":166935,"count":0}],"isBlockCoverage":false},{"functionName":"_rootPrint","ranges":[{"startOffset":166953,"endOffset":167048,"count":0}],"isBlockCoverage":false},{"functionName":"_printToZone","ranges":[{"startOffset":167068,"endOffset":167130,"count":0}],"isBlockCoverage":false},{"functionName":"_rootFork","ranges":[{"startOffset":167147,"endOffset":169398,"count":1}],"isBlockCoverage":true},{"functionName":"runZoned","ranges":[{"startOffset":169414,"endOffset":171320,"count":1},{"startOffset":169842,"endOffset":170101,"count":0},{"startOffset":170196,"endOffset":170336,"count":0},{"startOffset":170963,"endOffset":171319,"count":0}],"isBlockCoverage":true},{"functionName":"_runZoned","ranges":[{"startOffset":171337,"endOffset":171497,"count":1}],"isBlockCoverage":true},{"functionName":"_AsyncRun__initializeScheduleImmediate_internalCallback","ranges":[{"startOffset":171560,"endOffset":171660,"count":1}],"isBlockCoverage":true},{"functionName":"_AsyncRun__initializeScheduleImmediate_closure","ranges":[{"startOffset":171714,"endOffset":171856,"count":1}],"isBlockCoverage":true},{"functionName":"_AsyncRun__scheduleImmediateJsOverride_internalCallback","ranges":[{"startOffset":171919,"endOffset":172021,"count":0}],"isBlockCoverage":false},{"functionName":"_AsyncRun__scheduleImmediateWithSetImmediate_internalCallback","ranges":[{"startOffset":172090,"endOffset":172198,"count":0}],"isBlockCoverage":false},{"functionName":"_TimerImpl","ranges":[{"startOffset":172216,"endOffset":172319,"count":1}],"isBlockCoverage":true},{"functionName":"_TimerImpl_internalCallback","ranges":[{"startOffset":172354,"endOffset":172455,"count":1}],"isBlockCoverage":true},{"functionName":"_TimerImpl$periodic_closure","ranges":[{"startOffset":172490,"endOffset":172660,"count":0}],"isBlockCoverage":false},{"functionName":"_AsyncAwaitCompleter","ranges":[{"startOffset":172688,"endOffset":172806,"count":1}],"isBlockCoverage":true},{"functionName":"_awaitOnObject_closure","ranges":[{"startOffset":172836,"endOffset":172909,"count":1}],"isBlockCoverage":true},{"functionName":"_awaitOnObject_closure0","ranges":[{"startOffset":172940,"endOffset":173014,"count":1}],"isBlockCoverage":true},{"functionName":"_wrapJsFunctionForAsync_closure","ranges":[{"startOffset":173053,"endOffset":173133,"count":1}],"isBlockCoverage":true},{"functionName":"_BroadcastStream","ranges":[{"startOffset":173157,"endOffset":173248,"count":1}],"isBlockCoverage":true},{"functionName":"_BroadcastSubscription","ranges":[{"startOffset":173278,"endOffset":173605,"count":1}],"isBlockCoverage":true},{"functionName":"_BroadcastStreamController","ranges":[{"startOffset":173639,"endOffset":173684,"count":0}],"isBlockCoverage":false},{"functionName":"_SyncBroadcastStreamController","ranges":[{"startOffset":173722,"endOffset":173978,"count":1}],"isBlockCoverage":true},{"functionName":"_SyncBroadcastStreamController__sendData_closure","ranges":[{"startOffset":174034,"endOffset":174152,"count":0}],"isBlockCoverage":false},{"functionName":"_SyncBroadcastStreamController__sendError_closure","ranges":[{"startOffset":174209,"endOffset":174361,"count":0}],"isBlockCoverage":false},{"functionName":"_SyncBroadcastStreamController__sendDone_closure","ranges":[{"startOffset":174417,"endOffset":174509,"count":0}],"isBlockCoverage":false},{"functionName":"_AsyncBroadcastStreamController","ranges":[{"startOffset":174548,"endOffset":174805,"count":0}],"isBlockCoverage":false},{"functionName":"Future","ranges":[{"startOffset":174819,"endOffset":174844,"count":0}],"isBlockCoverage":false},{"functionName":"Future_Future_closure","ranges":[{"startOffset":174873,"endOffset":174972,"count":1}],"isBlockCoverage":true},{"functionName":"Future_Future$microtask_closure","ranges":[{"startOffset":175011,"endOffset":175120,"count":0}],"isBlockCoverage":false},{"functionName":"Future_wait_handleError","ranges":[{"startOffset":175151,"endOffset":175316,"count":0}],"isBlockCoverage":false},{"functionName":"Future_wait_closure","ranges":[{"startOffset":175343,"endOffset":175546,"count":0}],"isBlockCoverage":false},{"functionName":"Future_forEach_closure","ranges":[{"startOffset":175576,"endOffset":175673,"count":1}],"isBlockCoverage":true},{"functionName":"Future_doWhile_closure","ranges":[{"startOffset":175703,"endOffset":175830,"count":1}],"isBlockCoverage":true},{"functionName":"TimeoutException","ranges":[{"startOffset":175854,"endOffset":175946,"count":0}],"isBlockCoverage":false},{"functionName":"Completer","ranges":[{"startOffset":175963,"endOffset":175991,"count":0}],"isBlockCoverage":false},{"functionName":"_Completer","ranges":[{"startOffset":176009,"endOffset":176038,"count":0}],"isBlockCoverage":false},{"functionName":"_AsyncCompleter","ranges":[{"startOffset":176061,"endOffset":176146,"count":1}],"isBlockCoverage":true},{"functionName":"_SyncCompleter","ranges":[{"startOffset":176168,"endOffset":176252,"count":1}],"isBlockCoverage":true},{"functionName":"_FutureListener","ranges":[{"startOffset":176275,"endOffset":176487,"count":1}],"isBlockCoverage":true},{"functionName":"_Future","ranges":[{"startOffset":176502,"endOffset":176647,"count":1}],"isBlockCoverage":true},{"functionName":"_Future__addListener_closure","ranges":[{"startOffset":176683,"endOffset":176785,"count":1}],"isBlockCoverage":true},{"functionName":"_Future__prependListeners_closure","ranges":[{"startOffset":176826,"endOffset":176931,"count":0}],"isBlockCoverage":false},{"functionName":"_Future__chainForeignFuture_closure","ranges":[{"startOffset":176974,"endOffset":177054,"count":0}],"isBlockCoverage":false},{"functionName":"_Future__chainForeignFuture_closure0","ranges":[{"startOffset":177098,"endOffset":177179,"count":0}],"isBlockCoverage":false},{"functionName":"_Future__chainForeignFuture_closure1","ranges":[{"startOffset":177223,"endOffset":177350,"count":0}],"isBlockCoverage":false},{"functionName":"_Future__asyncComplete_closure","ranges":[{"startOffset":177388,"endOffset":177489,"count":1}],"isBlockCoverage":true},{"functionName":"_Future__chainFuture_closure","ranges":[{"startOffset":177525,"endOffset":177624,"count":0}],"isBlockCoverage":false},{"functionName":"_Future__asyncCompleteError_closure","ranges":[{"startOffset":177667,"endOffset":177805,"count":0}],"isBlockCoverage":false},{"functionName":"_Future__propagateToListeners_handleWhenCompleteCallback","ranges":[{"startOffset":177869,"endOffset":178066,"count":1}],"isBlockCoverage":true},{"functionName":"_Future__propagateToListeners_handleWhenCompleteCallback_closure","ranges":[{"startOffset":178138,"endOffset":178255,"count":0}],"isBlockCoverage":false},{"functionName":"_Future__propagateToListeners_handleValueCallback","ranges":[{"startOffset":178312,"endOffset":178470,"count":1}],"isBlockCoverage":true},{"functionName":"_Future__propagateToListeners_handleError","ranges":[{"startOffset":178519,"endOffset":178663,"count":0}],"isBlockCoverage":false},{"functionName":"_AsyncCallbackEntry","ranges":[{"startOffset":178690,"endOffset":178780,"count":1}],"isBlockCoverage":true},{"functionName":"Stream","ranges":[{"startOffset":178794,"endOffset":178819,"count":0}],"isBlockCoverage":false},{"functionName":"Stream_Stream$fromFuture_closure","ranges":[{"startOffset":178859,"endOffset":178963,"count":0}],"isBlockCoverage":false},{"functionName":"Stream_Stream$fromFuture_closure0","ranges":[{"startOffset":179004,"endOffset":179086,"count":0}],"isBlockCoverage":false},{"functionName":"Stream_Stream$fromIterable_closure","ranges":[{"startOffset":179128,"endOffset":179232,"count":1}],"isBlockCoverage":true},{"functionName":"Stream_pipe_closure","ranges":[{"startOffset":179259,"endOffset":179331,"count":1}],"isBlockCoverage":true},{"functionName":"Stream_length_closure","ranges":[{"startOffset":179360,"endOffset":179453,"count":0}],"isBlockCoverage":false},{"functionName":"Stream_length_closure0","ranges":[{"startOffset":179483,"endOffset":179578,"count":0}],"isBlockCoverage":false},{"functionName":"Stream_first_closure","ranges":[{"startOffset":179606,"endOffset":179726,"count":1}],"isBlockCoverage":true},{"functionName":"Stream_first_closure0","ranges":[{"startOffset":179755,"endOffset":179821,"count":1}],"isBlockCoverage":true},{"functionName":"Stream_last_closure","ranges":[{"startOffset":179848,"endOffset":179939,"count":0}],"isBlockCoverage":false},{"functionName":"Stream_last_closure0","ranges":[{"startOffset":179967,"endOffset":180060,"count":0}],"isBlockCoverage":false},{"functionName":"Stream_firstWhere_closure","ranges":[{"startOffset":180093,"endOffset":180252,"count":1}],"isBlockCoverage":true},{"functionName":"Stream_firstWhere__closure","ranges":[{"startOffset":180286,"endOffset":180382,"count":1}],"isBlockCoverage":true},{"functionName":"Stream_firstWhere__closure0","ranges":[{"startOffset":180417,"endOffset":180544,"count":1}],"isBlockCoverage":true},{"functionName":"Stream_firstWhere_closure0","ranges":[{"startOffset":180578,"endOffset":180704,"count":1}],"isBlockCoverage":true},{"functionName":"StreamSubscription","ranges":[{"startOffset":180730,"endOffset":180767,"count":0}],"isBlockCoverage":false},{"functionName":"StreamTransformerBase","ranges":[{"startOffset":180796,"endOffset":180836,"count":0}],"isBlockCoverage":false},{"functionName":"_StreamController","ranges":[{"startOffset":180861,"endOffset":180897,"count":0}],"isBlockCoverage":false},{"functionName":"_StreamController__subscribe_closure","ranges":[{"startOffset":180941,"endOffset":181021,"count":1}],"isBlockCoverage":true},{"functionName":"_StreamController__recordCancel_complete","ranges":[{"startOffset":181069,"endOffset":181153,"count":1}],"isBlockCoverage":true},{"functionName":"_SyncStreamControllerDispatch","ranges":[{"startOffset":181190,"endOffset":181238,"count":0}],"isBlockCoverage":false},{"functionName":"_AsyncStreamControllerDispatch","ranges":[{"startOffset":181276,"endOffset":181325,"count":0}],"isBlockCoverage":false},{"functionName":"_AsyncStreamController","ranges":[{"startOffset":181355,"endOffset":181616,"count":0}],"isBlockCoverage":false},{"functionName":"_SyncStreamController","ranges":[{"startOffset":181645,"endOffset":181905,"count":1}],"isBlockCoverage":true},{"functionName":"_ControllerStream","ranges":[{"startOffset":181930,"endOffset":182022,"count":1}],"isBlockCoverage":true},{"functionName":"_ControllerSubscription","ranges":[{"startOffset":182053,"endOffset":182306,"count":1}],"isBlockCoverage":true},{"functionName":"_StreamSinkWrapper","ranges":[{"startOffset":182332,"endOffset":182428,"count":1}],"isBlockCoverage":true},{"functionName":"_AddStreamState","ranges":[{"startOffset":182451,"endOffset":182485,"count":0}],"isBlockCoverage":false},{"functionName":"_AddStreamState_makeErrorHandler_closure","ranges":[{"startOffset":182533,"endOffset":182622,"count":0}],"isBlockCoverage":false},{"functionName":"_AddStreamState_cancel_closure","ranges":[{"startOffset":182660,"endOffset":182734,"count":1}],"isBlockCoverage":true},{"functionName":"_StreamControllerAddStreamState","ranges":[{"startOffset":182773,"endOffset":182957,"count":1}],"isBlockCoverage":true},{"functionName":"_BufferingStreamSubscription","ranges":[{"startOffset":182993,"endOffset":183221,"count":1}],"isBlockCoverage":true},{"functionName":"_BufferingStreamSubscription__sendError_sendError","ranges":[{"startOffset":183278,"endOffset":183430,"count":0}],"isBlockCoverage":false},{"functionName":"_BufferingStreamSubscription__sendDone_sendDone","ranges":[{"startOffset":183485,"endOffset":183576,"count":0}],"isBlockCoverage":false},{"functionName":"_StreamImpl","ranges":[{"startOffset":183595,"endOffset":183625,"count":0}],"isBlockCoverage":false},{"functionName":"_GeneratedStreamImpl","ranges":[{"startOffset":183653,"endOffset":183773,"count":1}],"isBlockCoverage":true},{"functionName":"_IterablePendingEvents","ranges":[{"startOffset":183803,"endOffset":183928,"count":1}],"isBlockCoverage":true},{"functionName":"_DelayedEvent","ranges":[{"startOffset":183949,"endOffset":183981,"count":0}],"isBlockCoverage":false},{"functionName":"_DelayedData","ranges":[{"startOffset":184001,"endOffset":184106,"count":0}],"isBlockCoverage":false},{"functionName":"_DelayedError","ranges":[{"startOffset":184127,"endOffset":184240,"count":0}],"isBlockCoverage":false},{"functionName":"_DelayedDone","ranges":[{"startOffset":184260,"endOffset":184291,"count":1}],"isBlockCoverage":true},{"functionName":"_PendingEvents","ranges":[{"startOffset":184313,"endOffset":184346,"count":0}],"isBlockCoverage":false},{"functionName":"_PendingEvents_schedule_closure","ranges":[{"startOffset":184385,"endOffset":184490,"count":1}],"isBlockCoverage":true},{"functionName":"_StreamImplEvents","ranges":[{"startOffset":184515,"endOffset":184666,"count":0}],"isBlockCoverage":false},{"functionName":"_DoneStreamSubscription","ranges":[{"startOffset":184697,"endOffset":184849,"count":0}],"isBlockCoverage":false},{"functionName":"_StreamIterator","ranges":[{"startOffset":184872,"endOffset":184929,"count":0}],"isBlockCoverage":false},{"functionName":"_EmptyStream","ranges":[{"startOffset":184949,"endOffset":185003,"count":0}],"isBlockCoverage":false},{"functionName":"_cancelAndError_closure","ranges":[{"startOffset":185034,"endOffset":185161,"count":0}],"isBlockCoverage":false},{"functionName":"_cancelAndErrorClosure_closure","ranges":[{"startOffset":185199,"endOffset":185308,"count":1}],"isBlockCoverage":true},{"functionName":"_cancelAndValue_closure","ranges":[{"startOffset":185339,"endOffset":185434,"count":1}],"isBlockCoverage":true},{"functionName":"Timer","ranges":[{"startOffset":185447,"endOffset":185471,"count":0}],"isBlockCoverage":false},{"functionName":"AsyncError","ranges":[{"startOffset":185489,"endOffset":185575,"count":0}],"isBlockCoverage":false},{"functionName":"_ZoneFunction","ranges":[{"startOffset":185596,"endOffset":185708,"count":1}],"isBlockCoverage":true},{"functionName":"ZoneSpecification","ranges":[{"startOffset":185733,"endOffset":185769,"count":0}],"isBlockCoverage":false},{"functionName":"_ZoneSpecification","ranges":[{"startOffset":185795,"endOffset":186270,"count":1}],"isBlockCoverage":true},{"functionName":"ZoneDelegate","ranges":[{"startOffset":186290,"endOffset":186321,"count":0}],"isBlockCoverage":false},{"functionName":"Zone","ranges":[{"startOffset":186333,"endOffset":186356,"count":0}],"isBlockCoverage":false},{"functionName":"_ZoneDelegate","ranges":[{"startOffset":186377,"endOffset":186446,"count":1}],"isBlockCoverage":true},{"functionName":"_Zone","ranges":[{"startOffset":186459,"endOffset":186483,"count":0}],"isBlockCoverage":false},{"functionName":"_CustomZone","ranges":[{"startOffset":186502,"endOffset":186881,"count":1}],"isBlockCoverage":true},{"functionName":"_CustomZone_bindCallback_closure","ranges":[{"startOffset":186921,"endOffset":187052,"count":1}],"isBlockCoverage":true},{"functionName":"_CustomZone_bindUnaryCallback_closure","ranges":[{"startOffset":187097,"endOffset":187264,"count":0}],"isBlockCoverage":false},{"functionName":"_CustomZone_bindCallbackGuarded_closure","ranges":[{"startOffset":187311,"endOffset":187426,"count":1}],"isBlockCoverage":true},{"functionName":"_CustomZone_bindUnaryCallbackGuarded_closure","ranges":[{"startOffset":187478,"endOffset":187621,"count":1}],"isBlockCoverage":true},{"functionName":"_rootHandleUncaughtError_closure","ranges":[{"startOffset":187661,"endOffset":187770,"count":0}],"isBlockCoverage":false},{"functionName":"_RootZone","ranges":[{"startOffset":187787,"endOffset":187815,"count":1}],"isBlockCoverage":true},{"functionName":"_RootZone_bindCallback_closure","ranges":[{"startOffset":187853,"endOffset":187973,"count":0}],"isBlockCoverage":false},{"functionName":"_RootZone_bindCallbackGuarded_closure","ranges":[{"startOffset":188018,"endOffset":188122,"count":0}],"isBlockCoverage":false},{"functionName":"_RootZone_bindUnaryCallbackGuarded_closure","ranges":[{"startOffset":188172,"endOffset":188304,"count":0}],"isBlockCoverage":false},{"functionName":"runZoned_closure","ranges":[{"startOffset":188328,"endOffset":188389,"count":1}],"isBlockCoverage":true},{"functionName":"HashMap_HashMap","ranges":[{"startOffset":188412,"endOffset":188522,"count":1}],"isBlockCoverage":true},{"functionName":"_HashMap__getTableEntry","ranges":[{"startOffset":188553,"endOffset":188656,"count":0}],"isBlockCoverage":false},{"functionName":"_HashMap__setTableEntry","ranges":[{"startOffset":188687,"endOffset":188814,"count":1},{"startOffset":188750,"endOffset":188769,"count":0}],"isBlockCoverage":true},{"functionName":"_HashMap__newHashTable","ranges":[{"startOffset":188844,"endOffset":189036,"count":1}],"isBlockCoverage":true},{"functionName":"LinkedHashMap_LinkedHashMap","ranges":[{"startOffset":189071,"endOffset":189195,"count":1}],"isBlockCoverage":true},{"functionName":"LinkedHashMap_LinkedHashMap$_literal","ranges":[{"startOffset":189239,"endOffset":189480,"count":1}],"isBlockCoverage":true},{"functionName":"LinkedHashMap_LinkedHashMap$_empty","ranges":[{"startOffset":189522,"endOffset":189646,"count":1}],"isBlockCoverage":true},{"functionName":"LinkedHashSet_LinkedHashSet","ranges":[{"startOffset":189681,"endOffset":189769,"count":1}],"isBlockCoverage":true},{"functionName":"LinkedHashSet_LinkedHashSet$_empty","ranges":[{"startOffset":189811,"endOffset":189899,"count":1}],"isBlockCoverage":true},{"functionName":"LinkedHashSet_LinkedHashSet$_literal","ranges":[{"startOffset":189943,"endOffset":190104,"count":1}],"isBlockCoverage":true},{"functionName":"_LinkedHashSet__newHashTable","ranges":[{"startOffset":190140,"endOffset":190343,"count":1}],"isBlockCoverage":true},{"functionName":"_LinkedHashSetIterator$","ranges":[{"startOffset":190374,"endOffset":190595,"count":1}],"isBlockCoverage":true},{"functionName":"HashMap_HashMap$from","ranges":[{"startOffset":190623,"endOffset":190799,"count":1}],"isBlockCoverage":true},{"functionName":"IterableBase_iterableToShortString","ranges":[{"startOffset":190841,"endOffset":191704,"count":0}],"isBlockCoverage":false},{"functionName":"IterableBase_iterableToFullString","ranges":[{"startOffset":191745,"endOffset":192506,"count":0}],"isBlockCoverage":false},{"functionName":"_isToStringVisiting","ranges":[{"startOffset":192533,"endOffset":192718,"count":0}],"isBlockCoverage":false},{"functionName":"_iterablePartsToStrings","ranges":[{"startOffset":192749,"endOffset":195409,"count":0}],"isBlockCoverage":false},{"functionName":"LinkedHashMap_LinkedHashMap$from","ranges":[{"startOffset":195449,"endOffset":195649,"count":1}],"isBlockCoverage":true},{"functionName":"LinkedHashSet_LinkedHashSet$from","ranges":[{"startOffset":195689,"endOffset":195923,"count":1}],"isBlockCoverage":true},{"functionName":"MapBase_mapToString","ranges":[{"startOffset":195950,"endOffset":196637,"count":0}],"isBlockCoverage":false},{"functionName":"ListQueue$","ranges":[{"startOffset":196655,"endOffset":196883,"count":1}],"isBlockCoverage":true},{"functionName":"_ListQueueIterator$","ranges":[{"startOffset":196910,"endOffset":197072,"count":0}],"isBlockCoverage":false},{"functionName":"_HashMap","ranges":[{"startOffset":197088,"endOffset":197255,"count":1}],"isBlockCoverage":true},{"functionName":"_IdentityHashMap","ranges":[{"startOffset":197279,"endOffset":197454,"count":1}],"isBlockCoverage":true},{"functionName":"_HashMapKeyIterable","ranges":[{"startOffset":197481,"endOffset":197568,"count":0}],"isBlockCoverage":false},{"functionName":"_HashMapKeyIterator","ranges":[{"startOffset":197595,"endOffset":197778,"count":0}],"isBlockCoverage":false},{"functionName":"_LinkedHashSet","ranges":[{"startOffset":197800,"endOffset":198048,"count":1}],"isBlockCoverage":true},{"functionName":"_LinkedHashSetCell","ranges":[{"startOffset":198074,"endOffset":198205,"count":1}],"isBlockCoverage":true},{"functionName":"_LinkedHashSetIterator","ranges":[{"startOffset":198235,"endOffset":198443,"count":1}],"isBlockCoverage":true},{"functionName":"UnmodifiableListView","ranges":[{"startOffset":198471,"endOffset":198574,"count":0}],"isBlockCoverage":false},{"functionName":"HashMap_HashMap$from_closure","ranges":[{"startOffset":198610,"endOffset":198729,"count":1}],"isBlockCoverage":true},{"functionName":"IterableBase","ranges":[{"startOffset":198749,"endOffset":198780,"count":0}],"isBlockCoverage":false},{"functionName":"LinkedHashMap_LinkedHashMap$from_closure","ranges":[{"startOffset":198828,"endOffset":198959,"count":1}],"isBlockCoverage":true},{"functionName":"ListBase","ranges":[{"startOffset":198975,"endOffset":199002,"count":0}],"isBlockCoverage":false},{"functionName":"ListMixin","ranges":[{"startOffset":199019,"endOffset":199047,"count":0}],"isBlockCoverage":false},{"functionName":"MapBase","ranges":[{"startOffset":199062,"endOffset":199088,"count":0}],"isBlockCoverage":false},{"functionName":"MapBase_mapToString_closure","ranges":[{"startOffset":199123,"endOffset":199223,"count":0}],"isBlockCoverage":false},{"functionName":"MapMixin","ranges":[{"startOffset":199239,"endOffset":199266,"count":0}],"isBlockCoverage":false},{"functionName":"_UnmodifiableMapMixin","ranges":[{"startOffset":199295,"endOffset":199335,"count":0}],"isBlockCoverage":false},{"functionName":"MapView","ranges":[{"startOffset":199350,"endOffset":199376,"count":0}],"isBlockCoverage":false},{"functionName":"UnmodifiableMapView","ranges":[{"startOffset":199403,"endOffset":199490,"count":1}],"isBlockCoverage":true},{"functionName":"ListQueue","ranges":[{"startOffset":199507,"endOffset":199650,"count":1}],"isBlockCoverage":true},{"functionName":"_ListQueueIterator","ranges":[{"startOffset":199676,"endOffset":199903,"count":0}],"isBlockCoverage":false},{"functionName":"SetMixin","ranges":[{"startOffset":199919,"endOffset":199946,"count":0}],"isBlockCoverage":false},{"functionName":"SetBase","ranges":[{"startOffset":199961,"endOffset":199987,"count":0}],"isBlockCoverage":false},{"functionName":"_SetBase","ranges":[{"startOffset":200003,"endOffset":200030,"count":0}],"isBlockCoverage":false},{"functionName":"_ListBase_Object_ListMixin","ranges":[{"startOffset":200064,"endOffset":200109,"count":0}],"isBlockCoverage":false},{"functionName":"_SetBase_Object_SetMixin","ranges":[{"startOffset":200141,"endOffset":200184,"count":0}],"isBlockCoverage":false},{"functionName":"_UnmodifiableMapView_MapView__UnmodifiableMapMixin","ranges":[{"startOffset":200242,"endOffset":200311,"count":0}],"isBlockCoverage":false},{"functionName":"_parseJson","ranges":[{"startOffset":200329,"endOffset":200797,"count":0}],"isBlockCoverage":false},{"functionName":"_convertJsonToDartLazy","ranges":[{"startOffset":200827,"endOffset":201212,"count":0}],"isBlockCoverage":false},{"functionName":"Utf8Decoder__convertIntercepted","ranges":[{"startOffset":201251,"endOffset":201457,"count":0}],"isBlockCoverage":false},{"functionName":"Utf8Decoder__convertInterceptedUint8List","ranges":[{"startOffset":201505,"endOffset":202094,"count":0}],"isBlockCoverage":false},{"functionName":"Utf8Decoder__useTextDecoderChecked","ranges":[{"startOffset":202136,"endOffset":202310,"count":0}],"isBlockCoverage":false},{"functionName":"Utf8Decoder__useTextDecoderUnchecked","ranges":[{"startOffset":202354,"endOffset":202579,"count":0}],"isBlockCoverage":false},{"functionName":"Utf8Decoder__unsafe","ranges":[{"startOffset":202606,"endOffset":202845,"count":0}],"isBlockCoverage":false},{"functionName":"Utf8Decoder__makeDecoder","ranges":[{"startOffset":202877,"endOffset":203098,"count":0}],"isBlockCoverage":false},{"functionName":"_scanOneByteCharacters","ranges":[{"startOffset":203128,"endOffset":203470,"count":0}],"isBlockCoverage":false},{"functionName":"Base64Codec__checkPadding","ranges":[{"startOffset":203503,"endOffset":204114,"count":0}],"isBlockCoverage":false},{"functionName":"_JsonMap","ranges":[{"startOffset":204130,"endOffset":204243,"count":0}],"isBlockCoverage":false},{"functionName":"_JsonMapKeyIterable","ranges":[{"startOffset":204270,"endOffset":204335,"count":0}],"isBlockCoverage":false},{"functionName":"AsciiCodec","ranges":[{"startOffset":204353,"endOffset":204382,"count":1}],"isBlockCoverage":true},{"functionName":"_UnicodeSubsetEncoder","ranges":[{"startOffset":204411,"endOffset":204451,"count":0}],"isBlockCoverage":false},{"functionName":"AsciiEncoder","ranges":[{"startOffset":204471,"endOffset":204533,"count":1}],"isBlockCoverage":true},{"functionName":"Base64Codec","ranges":[{"startOffset":204552,"endOffset":204582,"count":1}],"isBlockCoverage":true},{"functionName":"Base64Encoder","ranges":[{"startOffset":204603,"endOffset":204635,"count":1}],"isBlockCoverage":true},{"functionName":"Codec","ranges":[{"startOffset":204648,"endOffset":204672,"count":0}],"isBlockCoverage":false},{"functionName":"_FusedCodec","ranges":[{"startOffset":204691,"endOffset":204810,"count":0}],"isBlockCoverage":false},{"functionName":"Converter","ranges":[{"startOffset":204827,"endOffset":204855,"count":0}],"isBlockCoverage":false},{"functionName":"Encoding","ranges":[{"startOffset":204871,"endOffset":204898,"count":0}],"isBlockCoverage":false},{"functionName":"JsonCodec","ranges":[{"startOffset":204915,"endOffset":204943,"count":1}],"isBlockCoverage":true},{"functionName":"JsonDecoder","ranges":[{"startOffset":204962,"endOffset":205020,"count":1}],"isBlockCoverage":true},{"functionName":"Utf8Codec","ranges":[{"startOffset":205037,"endOffset":205065,"count":1}],"isBlockCoverage":true},{"functionName":"Utf8Encoder","ranges":[{"startOffset":205084,"endOffset":205114,"count":1}],"isBlockCoverage":true},{"functionName":"_Utf8Encoder","ranges":[{"startOffset":205134,"endOffset":205235,"count":0}],"isBlockCoverage":false},{"functionName":"Utf8Decoder","ranges":[{"startOffset":205254,"endOffset":205319,"count":0}],"isBlockCoverage":false},{"functionName":"_Utf8Decoder","ranges":[{"startOffset":205339,"endOffset":205550,"count":0}],"isBlockCoverage":false},{"functionName":"int_parse","ranges":[{"startOffset":205567,"endOffset":205845,"count":0}],"isBlockCoverage":false},{"functionName":"Error__objectToString","ranges":[{"startOffset":205874,"endOffset":206053,"count":0}],"isBlockCoverage":false},{"functionName":"List_List$filled","ranges":[{"startOffset":206077,"endOffset":206334,"count":0}],"isBlockCoverage":false},{"functionName":"List_List$from","ranges":[{"startOffset":206356,"endOffset":206723,"count":1}],"isBlockCoverage":true},{"functionName":"List_List$unmodifiable","ranges":[{"startOffset":206753,"endOffset":206964,"count":1}],"isBlockCoverage":true},{"functionName":"String_String$fromCharCodes","ranges":[{"startOffset":206999,"endOffset":207622,"count":0}],"isBlockCoverage":false},{"functionName":"String_String$fromCharCode","ranges":[{"startOffset":207656,"endOffset":207738,"count":0}],"isBlockCoverage":false},{"functionName":"String__stringFromIterable","ranges":[{"startOffset":207772,"endOffset":208694,"count":0}],"isBlockCoverage":false},{"functionName":"RegExp_RegExp","ranges":[{"startOffset":208715,"endOffset":208868,"count":0}],"isBlockCoverage":false},{"functionName":"StringBuffer__writeAll","ranges":[{"startOffset":208898,"endOffset":209382,"count":0}],"isBlockCoverage":false},{"functionName":"Uri_base","ranges":[{"startOffset":209398,"endOffset":209596,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__uriEncode","ranges":[{"startOffset":209619,"endOffset":210718,"count":0}],"isBlockCoverage":false},{"functionName":"StackTrace_current","ranges":[{"startOffset":210744,"endOffset":211119,"count":1},{"startOffset":210908,"endOffset":211113,"count":0}],"isBlockCoverage":true},{"functionName":"DateTime__fourDigits","ranges":[{"startOffset":211147,"endOffset":211424,"count":0}],"isBlockCoverage":false},{"functionName":"DateTime__threeDigits","ranges":[{"startOffset":211453,"endOffset":211581,"count":0}],"isBlockCoverage":false},{"functionName":"DateTime__twoDigits","ranges":[{"startOffset":211608,"endOffset":211691,"count":0}],"isBlockCoverage":false},{"functionName":"Duration$","ranges":[{"startOffset":211708,"endOffset":211891,"count":1},{"startOffset":211794,"endOffset":211821,"count":0}],"isBlockCoverage":true},{"functionName":"Error_safeToString","ranges":[{"startOffset":211917,"endOffset":212177,"count":0}],"isBlockCoverage":false},{"functionName":"AssertionError$","ranges":[{"startOffset":212200,"endOffset":212269,"count":0}],"isBlockCoverage":false},{"functionName":"ArgumentError$","ranges":[{"startOffset":212291,"endOffset":212378,"count":0}],"isBlockCoverage":false},{"functionName":"ArgumentError$value","ranges":[{"startOffset":212405,"endOffset":212507,"count":0}],"isBlockCoverage":false},{"functionName":"ArgumentError$notNull","ranges":[{"startOffset":212536,"endOffset":212633,"count":0}],"isBlockCoverage":false},{"functionName":"RangeError$","ranges":[{"startOffset":212652,"endOffset":212776,"count":0}],"isBlockCoverage":false},{"functionName":"RangeError$value","ranges":[{"startOffset":212800,"endOffset":212915,"count":0}],"isBlockCoverage":false},{"functionName":"RangeError$range","ranges":[{"startOffset":212939,"endOffset":213100,"count":0}],"isBlockCoverage":false},{"functionName":"RangeError_checkValueInInterval","ranges":[{"startOffset":213139,"endOffset":213328,"count":0}],"isBlockCoverage":false},{"functionName":"RangeError_checkValidRange","ranges":[{"startOffset":213362,"endOffset":213728,"count":1},{"startOffset":213442,"endOffset":213518,"count":0},{"startOffset":213596,"endOffset":213672,"count":0},{"startOffset":213700,"endOffset":213727,"count":0}],"isBlockCoverage":true},{"functionName":"RangeError_checkNotNegative","ranges":[{"startOffset":213763,"endOffset":213959,"count":0}],"isBlockCoverage":false},{"functionName":"IndexError$","ranges":[{"startOffset":213978,"endOffset":214221,"count":0}],"isBlockCoverage":false},{"functionName":"UnsupportedError$","ranges":[{"startOffset":214246,"endOffset":214317,"count":0}],"isBlockCoverage":false},{"functionName":"UnimplementedError$","ranges":[{"startOffset":214344,"endOffset":214417,"count":0}],"isBlockCoverage":false},{"functionName":"StateError$","ranges":[{"startOffset":214436,"endOffset":214501,"count":0}],"isBlockCoverage":false},{"functionName":"ConcurrentModificationError$","ranges":[{"startOffset":214537,"endOffset":214633,"count":0}],"isBlockCoverage":false},{"functionName":"FormatException$","ranges":[{"startOffset":214657,"endOffset":214759,"count":0}],"isBlockCoverage":false},{"functionName":"List_List$generate","ranges":[{"startOffset":214785,"endOffset":215096,"count":1}],"isBlockCoverage":true},{"functionName":"Map_castFrom","ranges":[{"startOffset":215116,"endOffset":215276,"count":1}],"isBlockCoverage":true},{"functionName":"print","ranges":[{"startOffset":215289,"endOffset":215458,"count":0}],"isBlockCoverage":false},{"functionName":"_combineSurrogatePair","ranges":[{"startOffset":215487,"endOffset":215575,"count":0}],"isBlockCoverage":false},{"functionName":"Uri_parse","ranges":[{"startOffset":215592,"endOffset":222061,"count":1},{"startOffset":216121,"endOffset":216228,"count":0},{"startOffset":216270,"endOffset":216359,"count":0},{"startOffset":216950,"endOffset":216995,"count":0},{"startOffset":217075,"endOffset":217098,"count":0},{"startOffset":217195,"endOffset":217218,"count":0},{"startOffset":217284,"endOffset":217301,"count":0},{"startOffset":217506,"endOffset":217533,"count":0},{"startOffset":217584,"endOffset":217609,"count":0},{"startOffset":217656,"endOffset":217683,"count":0},{"startOffset":217733,"endOffset":217756,"count":0},{"startOffset":217798,"endOffset":217821,"count":0},{"startOffset":217869,"endOffset":217895,"count":0},{"startOffset":217945,"endOffset":217968,"count":0},{"startOffset":218399,"endOffset":218415,"count":0},{"startOffset":218500,"endOffset":218565,"count":0},{"startOffset":218652,"endOffset":218723,"count":0},{"startOffset":218766,"endOffset":218797,"count":0},{"startOffset":218798,"endOffset":218839,"count":0},{"startOffset":218936,"endOffset":218978,"count":0},{"startOffset":218999,"endOffset":219076,"count":0},{"startOffset":219213,"endOffset":219911,"count":0},{"startOffset":219947,"endOffset":220222,"count":0},{"startOffset":220275,"endOffset":221412,"count":0},{"startOffset":221479,"endOffset":221514,"count":0},{"startOffset":221584,"endOffset":221802,"count":0},{"startOffset":221927,"endOffset":222060,"count":0}],"isBlockCoverage":true},{"functionName":"Uri_decodeComponent","ranges":[{"startOffset":222088,"endOffset":222270,"count":0}],"isBlockCoverage":false},{"functionName":"Uri__parseIPv4Address","ranges":[{"startOffset":222299,"endOffset":223833,"count":0}],"isBlockCoverage":false},{"functionName":"Uri_parseIPv6Address","ranges":[{"startOffset":223861,"endOffset":226795,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__Uri$notSimple","ranges":[{"startOffset":226822,"endOffset":228163,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__Uri","ranges":[{"startOffset":228180,"endOffset":229390,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__defaultPort","ranges":[{"startOffset":229415,"endOffset":229553,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__fail","ranges":[{"startOffset":229571,"endOffset":229678,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__Uri$file","ranges":[{"startOffset":229700,"endOffset":229830,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__checkNonWindowsPathReservedCharacters","ranges":[{"startOffset":229881,"endOffset":230033,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__checkWindowsPathReservedCharacters","ranges":[{"startOffset":230081,"endOffset":230721,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__checkWindowsDriveLetter","ranges":[{"startOffset":230758,"endOffset":231242,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__makeFileUri","ranges":[{"startOffset":231267,"endOffset":231594,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__makeWindowsFileUrl","ranges":[{"startOffset":231626,"endOffset":234062,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__makePort","ranges":[{"startOffset":234084,"endOffset":234218,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__makeHost","ranges":[{"startOffset":234240,"endOffset":235817,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__checkZoneID","ranges":[{"startOffset":235842,"endOffset":236000,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__normalizeZoneID","ranges":[{"startOffset":236029,"endOffset":238805,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__normalizeRegName","ranges":[{"startOffset":238835,"endOffset":242233,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__makeScheme","ranges":[{"startOffset":242257,"endOffset":243253,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__canonicalizeScheme","ranges":[{"startOffset":243285,"endOffset":243546,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__makeUserInfo","ranges":[{"startOffset":243572,"endOffset":243741,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__makePath","ranges":[{"startOffset":243763,"endOffset":244818,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__normalizePath","ranges":[{"startOffset":244845,"endOffset":245122,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__makeQuery","ranges":[{"startOffset":245145,"endOffset":245323,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__makeFragment","ranges":[{"startOffset":245349,"endOffset":245519,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__normalizeEscape","ranges":[{"startOffset":245548,"endOffset":246720,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__escapeChar","ranges":[{"startOffset":246744,"endOffset":248292,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__normalizeOrSubstring","ranges":[{"startOffset":248326,"endOffset":248566,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__normalize","ranges":[{"startOffset":248589,"endOffset":251311,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__mayContainDotSegments","ranges":[{"startOffset":251346,"endOffset":251505,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__removeDotSegments","ranges":[{"startOffset":251536,"endOffset":252526,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__normalizeRelativePath","ranges":[{"startOffset":252561,"endOffset":254222,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__escapeScheme","ranges":[{"startOffset":254248,"endOffset":254933,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__toWindowsFilePath","ranges":[{"startOffset":254964,"endOffset":255945,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__hexCharPairToByte","ranges":[{"startOffset":255976,"endOffset":256491,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__uriDecode","ranges":[{"startOffset":256514,"endOffset":258126,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__isAlphabeticCharacter","ranges":[{"startOffset":258161,"endOffset":258274,"count":0}],"isBlockCoverage":false},{"functionName":"UriData__writeUri","ranges":[{"startOffset":258299,"endOffset":258967,"count":0}],"isBlockCoverage":false},{"functionName":"UriData__validateMimeType","ranges":[{"startOffset":259000,"endOffset":259351,"count":0}],"isBlockCoverage":false},{"functionName":"UriData__parse","ranges":[{"startOffset":259373,"endOffset":261418,"count":0}],"isBlockCoverage":false},{"functionName":"UriData__uriEncodeBytes","ranges":[{"startOffset":261449,"endOffset":262927,"count":0}],"isBlockCoverage":false},{"functionName":"_createTables","ranges":[{"startOffset":262948,"endOffset":267507,"count":1}],"isBlockCoverage":true},{"functionName":"_scan","ranges":[{"startOffset":267520,"endOffset":268208,"count":1},{"startOffset":267816,"endOffset":267846,"count":0},{"startOffset":267957,"endOffset":267967,"count":0},{"startOffset":268012,"endOffset":268040,"count":0}],"isBlockCoverage":true},{"functionName":"bool","ranges":[{"startOffset":268220,"endOffset":268243,"count":0}],"isBlockCoverage":false},{"functionName":"DateTime","ranges":[{"startOffset":268259,"endOffset":268339,"count":0}],"isBlockCoverage":false},{"functionName":"double","ranges":[{"startOffset":268353,"endOffset":268378,"count":0}],"isBlockCoverage":false},{"functionName":"Duration","ranges":[{"startOffset":268394,"endOffset":268450,"count":1}],"isBlockCoverage":true},{"functionName":"Duration_toString_sixDigits","ranges":[{"startOffset":268485,"endOffset":268531,"count":0}],"isBlockCoverage":false},{"functionName":"Duration_toString_twoDigits","ranges":[{"startOffset":268566,"endOffset":268612,"count":0}],"isBlockCoverage":false},{"functionName":"Error","ranges":[{"startOffset":268625,"endOffset":268649,"count":0}],"isBlockCoverage":false},{"functionName":"AssertionError","ranges":[{"startOffset":268671,"endOffset":268731,"count":0}],"isBlockCoverage":false},{"functionName":"NullThrownError","ranges":[{"startOffset":268754,"endOffset":268788,"count":0}],"isBlockCoverage":false},{"functionName":"ArgumentError","ranges":[{"startOffset":268809,"endOffset":268967,"count":0}],"isBlockCoverage":false},{"functionName":"RangeError","ranges":[{"startOffset":268985,"endOffset":269186,"count":0}],"isBlockCoverage":false},{"functionName":"IndexError","ranges":[{"startOffset":269204,"endOffset":269384,"count":0}],"isBlockCoverage":false},{"functionName":"UnsupportedError","ranges":[{"startOffset":269408,"endOffset":269470,"count":0}],"isBlockCoverage":false},{"functionName":"UnimplementedError","ranges":[{"startOffset":269496,"endOffset":269560,"count":0}],"isBlockCoverage":false},{"functionName":"StateError","ranges":[{"startOffset":269578,"endOffset":269634,"count":0}],"isBlockCoverage":false},{"functionName":"ConcurrentModificationError","ranges":[{"startOffset":269669,"endOffset":269749,"count":0}],"isBlockCoverage":false},{"functionName":"OutOfMemoryError","ranges":[{"startOffset":269773,"endOffset":269808,"count":1}],"isBlockCoverage":true},{"functionName":"StackOverflowError","ranges":[{"startOffset":269834,"endOffset":269871,"count":0}],"isBlockCoverage":false},{"functionName":"CyclicInitializationError","ranges":[{"startOffset":269904,"endOffset":269980,"count":0}],"isBlockCoverage":false},{"functionName":"_Exception","ranges":[{"startOffset":269998,"endOffset":270054,"count":0}],"isBlockCoverage":false},{"functionName":"FormatException","ranges":[{"startOffset":270077,"endOffset":270194,"count":0}],"isBlockCoverage":false},{"functionName":"Expando","ranges":[{"startOffset":270209,"endOffset":270321,"count":1}],"isBlockCoverage":true},{"functionName":"Function","ranges":[{"startOffset":270337,"endOffset":270364,"count":0}],"isBlockCoverage":false},{"functionName":"int","ranges":[{"startOffset":270375,"endOffset":270397,"count":0}],"isBlockCoverage":false},{"functionName":"Iterable","ranges":[{"startOffset":270413,"endOffset":270440,"count":0}],"isBlockCoverage":false},{"functionName":"Iterator","ranges":[{"startOffset":270456,"endOffset":270483,"count":0}],"isBlockCoverage":false},{"functionName":"List","ranges":[{"startOffset":270495,"endOffset":270518,"count":0}],"isBlockCoverage":false},{"functionName":"Map","ranges":[{"startOffset":270529,"endOffset":270551,"count":0}],"isBlockCoverage":false},{"functionName":"MapEntry","ranges":[{"startOffset":270567,"endOffset":270669,"count":1}],"isBlockCoverage":true},{"functionName":"Null","ranges":[{"startOffset":270681,"endOffset":270704,"count":0}],"isBlockCoverage":false},{"functionName":"num","ranges":[{"startOffset":270715,"endOffset":270737,"count":0}],"isBlockCoverage":false},{"functionName":"Object","ranges":[{"startOffset":270751,"endOffset":270776,"count":1}],"isBlockCoverage":true},{"functionName":"Pattern","ranges":[{"startOffset":270791,"endOffset":270817,"count":0}],"isBlockCoverage":false},{"functionName":"Match","ranges":[{"startOffset":270830,"endOffset":270854,"count":0}],"isBlockCoverage":false},{"functionName":"RegExpMatch","ranges":[{"startOffset":270873,"endOffset":270903,"count":0}],"isBlockCoverage":false},{"functionName":"Set","ranges":[{"startOffset":270914,"endOffset":270936,"count":0}],"isBlockCoverage":false},{"functionName":"StackTrace","ranges":[{"startOffset":270954,"endOffset":270983,"count":0}],"isBlockCoverage":false},{"functionName":"_StringStackTrace","ranges":[{"startOffset":271008,"endOffset":271075,"count":0}],"isBlockCoverage":false},{"functionName":"Stopwatch","ranges":[{"startOffset":271092,"endOffset":271162,"count":0}],"isBlockCoverage":false},{"functionName":"String","ranges":[{"startOffset":271176,"endOffset":271201,"count":0}],"isBlockCoverage":false},{"functionName":"Runes","ranges":[{"startOffset":271214,"endOffset":271264,"count":0}],"isBlockCoverage":false},{"functionName":"RuneIterator","ranges":[{"startOffset":271284,"endOffset":271439,"count":0}],"isBlockCoverage":false},{"functionName":"StringBuffer","ranges":[{"startOffset":271459,"endOffset":271519,"count":0}],"isBlockCoverage":false},{"functionName":"Uri","ranges":[{"startOffset":271530,"endOffset":271552,"count":0}],"isBlockCoverage":false},{"functionName":"Uri__parseIPv4Address_error","ranges":[{"startOffset":271587,"endOffset":271657,"count":0}],"isBlockCoverage":false},{"functionName":"Uri_parseIPv6Address_error","ranges":[{"startOffset":271691,"endOffset":271760,"count":0}],"isBlockCoverage":false},{"functionName":"Uri_parseIPv6Address_parseHex","ranges":[{"startOffset":271797,"endOffset":271896,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri","ranges":[{"startOffset":271908,"endOffset":272185,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__Uri$notSimple_closure","ranges":[{"startOffset":272220,"endOffset":272320,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__checkNonWindowsPathReservedCharacters_closure","ranges":[{"startOffset":272379,"endOffset":272482,"count":0}],"isBlockCoverage":false},{"functionName":"_Uri__makePath_closure","ranges":[{"startOffset":272512,"endOffset":272553,"count":0}],"isBlockCoverage":false},{"functionName":"UriData","ranges":[{"startOffset":272568,"endOffset":272689,"count":0}],"isBlockCoverage":false},{"functionName":"_createTables_closure","ranges":[{"startOffset":272718,"endOffset":272758,"count":1}],"isBlockCoverage":true},{"functionName":"_createTables_build","ranges":[{"startOffset":272785,"endOffset":272849,"count":1}],"isBlockCoverage":true},{"functionName":"_createTables_setChars","ranges":[{"startOffset":272879,"endOffset":272920,"count":1}],"isBlockCoverage":true},{"functionName":"_createTables_setRange","ranges":[{"startOffset":272950,"endOffset":272991,"count":1}],"isBlockCoverage":true},{"functionName":"_SimpleUri","ranges":[{"startOffset":273009,"endOffset":273320,"count":1}],"isBlockCoverage":true},{"functionName":"_DataUri","ranges":[{"startOffset":273336,"endOffset":273617,"count":0}],"isBlockCoverage":false},{"functionName":"_StructuredClone","ranges":[{"startOffset":273641,"endOffset":273676,"count":0}],"isBlockCoverage":false},{"functionName":"_StructuredClone_walk_closure","ranges":[{"startOffset":273713,"endOffset":273814,"count":1}],"isBlockCoverage":true},{"functionName":"_StructuredClone_walk_closure0","ranges":[{"startOffset":273852,"endOffset":273954,"count":0}],"isBlockCoverage":false},{"functionName":"_AcceptStructuredClone","ranges":[{"startOffset":273984,"endOffset":274025,"count":0}],"isBlockCoverage":false},{"functionName":"_AcceptStructuredClone_walk_closure","ranges":[{"startOffset":274068,"endOffset":274175,"count":1}],"isBlockCoverage":true},{"functionName":"_StructuredCloneDart2Js","ranges":[{"startOffset":274206,"endOffset":274302,"count":1}],"isBlockCoverage":true},{"functionName":"_AcceptStructuredCloneDart2Js","ranges":[{"startOffset":274339,"endOffset":274470,"count":1}],"isBlockCoverage":true},{"functionName":"_convertDataTree","ranges":[{"startOffset":274494,"endOffset":274639,"count":1}],"isBlockCoverage":true},{"functionName":"promiseToFuture","ranges":[{"startOffset":274662,"endOffset":275033,"count":0}],"isBlockCoverage":false},{"functionName":"_convertDataTree__convert","ranges":[{"startOffset":275066,"endOffset":275147,"count":1}],"isBlockCoverage":true},{"functionName":"promiseToFuture_closure","ranges":[{"startOffset":275178,"endOffset":275272,"count":0}],"isBlockCoverage":false},{"functionName":"promiseToFuture_closure0","ranges":[{"startOffset":275304,"endOffset":275376,"count":0}],"isBlockCoverage":false},{"functionName":"ByteBuffer","ranges":[{"startOffset":275394,"endOffset":275423,"count":0}],"isBlockCoverage":false},{"functionName":"ByteData","ranges":[{"startOffset":275439,"endOffset":275466,"count":0}],"isBlockCoverage":false},{"functionName":"Int8List","ranges":[{"startOffset":275482,"endOffset":275509,"count":0}],"isBlockCoverage":false},{"functionName":"Uint8List","ranges":[{"startOffset":275526,"endOffset":275554,"count":0}],"isBlockCoverage":false},{"functionName":"Uint8ClampedList","ranges":[{"startOffset":275578,"endOffset":275613,"count":0}],"isBlockCoverage":false},{"functionName":"Int16List","ranges":[{"startOffset":275630,"endOffset":275658,"count":0}],"isBlockCoverage":false},{"functionName":"Uint16List","ranges":[{"startOffset":275676,"endOffset":275705,"count":0}],"isBlockCoverage":false},{"functionName":"Int32List","ranges":[{"startOffset":275722,"endOffset":275750,"count":0}],"isBlockCoverage":false},{"functionName":"Uint32List","ranges":[{"startOffset":275768,"endOffset":275797,"count":0}],"isBlockCoverage":false},{"functionName":"Float32List","ranges":[{"startOffset":275816,"endOffset":275846,"count":0}],"isBlockCoverage":false},{"functionName":"Float64List","ranges":[{"startOffset":275865,"endOffset":275895,"count":0}],"isBlockCoverage":false},{"functionName":"SqlError","ranges":[{"startOffset":275911,"endOffset":275938,"count":0}],"isBlockCoverage":false},{"functionName":"max","ranges":[{"startOffset":275949,"endOffset":276119,"count":0}],"isBlockCoverage":false},{"functionName":"pow","ranges":[{"startOffset":276130,"endOffset":276195,"count":0}],"isBlockCoverage":false},{"functionName":"_EventStreamSubscription$","ranges":[{"startOffset":276240,"endOffset":276575,"count":1},{"startOffset":276327,"endOffset":276333,"count":0}],"isBlockCoverage":true},{"functionName":"_wrapZone","ranges":[{"startOffset":276592,"endOffset":276771,"count":1},{"startOffset":276705,"endOffset":276770,"count":0}],"isBlockCoverage":true},{"functionName":"ApplicationCacheErrorEvent","ranges":[{"startOffset":276805,"endOffset":276850,"count":0}],"isBlockCoverage":false},{"functionName":"Blob","ranges":[{"startOffset":276862,"endOffset":276885,"count":0}],"isBlockCoverage":false},{"functionName":"DomError","ranges":[{"startOffset":276901,"endOffset":276928,"count":0}],"isBlockCoverage":false},{"functionName":"DomException","ranges":[{"startOffset":276948,"endOffset":276979,"count":0}],"isBlockCoverage":false},{"functionName":"ErrorEvent","ranges":[{"startOffset":276997,"endOffset":277026,"count":0}],"isBlockCoverage":false},{"functionName":"Event","ranges":[{"startOffset":277039,"endOffset":277063,"count":0}],"isBlockCoverage":false},{"functionName":"EventTarget","ranges":[{"startOffset":277082,"endOffset":277112,"count":0}],"isBlockCoverage":false},{"functionName":"File","ranges":[{"startOffset":277124,"endOffset":277147,"count":0}],"isBlockCoverage":false},{"functionName":"Location","ranges":[{"startOffset":277163,"endOffset":277190,"count":0}],"isBlockCoverage":false},{"functionName":"MediaError","ranges":[{"startOffset":277208,"endOffset":277237,"count":0}],"isBlockCoverage":false},{"functionName":"MediaKeyMessageEvent","ranges":[{"startOffset":277265,"endOffset":277304,"count":0}],"isBlockCoverage":false},{"functionName":"MessageEvent","ranges":[{"startOffset":277324,"endOffset":277355,"count":0}],"isBlockCoverage":false},{"functionName":"MessagePort","ranges":[{"startOffset":277374,"endOffset":277404,"count":0}],"isBlockCoverage":false},{"functionName":"NavigatorUserMediaError","ranges":[{"startOffset":277435,"endOffset":277477,"count":0}],"isBlockCoverage":false},{"functionName":"OverconstrainedError","ranges":[{"startOffset":277505,"endOffset":277544,"count":0}],"isBlockCoverage":false},{"functionName":"PositionError","ranges":[{"startOffset":277565,"endOffset":277597,"count":0}],"isBlockCoverage":false},{"functionName":"PresentationConnectionCloseEvent","ranges":[{"startOffset":277637,"endOffset":277688,"count":0}],"isBlockCoverage":false},{"functionName":"SpeechRecognitionError","ranges":[{"startOffset":277718,"endOffset":277759,"count":0}],"isBlockCoverage":false},{"functionName":"EventStreamProvider","ranges":[{"startOffset":277786,"endOffset":277847,"count":0}],"isBlockCoverage":false},{"functionName":"_EventStream","ranges":[{"startOffset":277867,"endOffset":278029,"count":1}],"isBlockCoverage":true},{"functionName":"_EventStreamSubscription","ranges":[{"startOffset":278061,"endOffset":278292,"count":1}],"isBlockCoverage":true},{"functionName":"_EventStreamSubscription_closure","ranges":[{"startOffset":278332,"endOffset":278409,"count":1}],"isBlockCoverage":true},{"functionName":"AsyncMemoizer","ranges":[{"startOffset":278437,"endOffset":278540,"count":0}],"isBlockCoverage":false},{"functionName":"NullStreamSink","ranges":[{"startOffset":278558,"endOffset":278715,"count":0}],"isBlockCoverage":false},{"functionName":"NullStreamSink_addStream_closure","ranges":[{"startOffset":278751,"endOffset":278827,"count":0}],"isBlockCoverage":false},{"functionName":"Validator","ranges":[{"startOffset":278840,"endOffset":278898,"count":0}],"isBlockCoverage":false},{"functionName":"SpanScanner$","ranges":[{"startOffset":278918,"endOffset":279265,"count":0}],"isBlockCoverage":false},{"functionName":"SpanScanner","ranges":[{"startOffset":279284,"endOffset":279530,"count":0}],"isBlockCoverage":false},{"functionName":"_SpanScannerState","ranges":[{"startOffset":279555,"endOffset":279663,"count":0}],"isBlockCoverage":false},{"functionName":"RemoteListener_start","ranges":[{"startOffset":279691,"endOffset":280824,"count":1}],"isBlockCoverage":true},{"functionName":"RemoteListener__deserializeSet","ranges":[{"startOffset":280862,"endOffset":281054,"count":1},{"startOffset":280911,"endOffset":280923,"count":0},{"startOffset":280979,"endOffset":281053,"count":0}],"isBlockCoverage":true},{"functionName":"RemoteListener__sendLoadException","ranges":[{"startOffset":281095,"endOffset":281308,"count":0}],"isBlockCoverage":false},{"functionName":"RemoteListener__sendError","ranges":[{"startOffset":281341,"endOffset":281720,"count":0}],"isBlockCoverage":false},{"functionName":"RemoteListener","ranges":[{"startOffset":281742,"endOffset":281833,"count":1}],"isBlockCoverage":true},{"functionName":"RemoteListener_start_closure","ranges":[{"startOffset":281869,"endOffset":281974,"count":1}],"isBlockCoverage":true},{"functionName":"RemoteListener_start_closure0","ranges":[{"startOffset":282011,"endOffset":282059,"count":1}],"isBlockCoverage":true},{"functionName":"RemoteListener_start_closure1","ranges":[{"startOffset":282096,"endOffset":282348,"count":1}],"isBlockCoverage":true},{"functionName":"RemoteListener_start__closure","ranges":[{"startOffset":282385,"endOffset":282637,"count":1}],"isBlockCoverage":true},{"functionName":"RemoteListener_start___closure","ranges":[{"startOffset":282675,"endOffset":282905,"count":1}],"isBlockCoverage":true},{"functionName":"RemoteListener_start____closure","ranges":[{"startOffset":282944,"endOffset":283053,"count":1}],"isBlockCoverage":true},{"functionName":"RemoteListener_start____closure0","ranges":[{"startOffset":283093,"endOffset":283229,"count":1}],"isBlockCoverage":true},{"functionName":"RemoteListener_start_____closure","ranges":[{"startOffset":283269,"endOffset":283405,"count":1}],"isBlockCoverage":true},{"functionName":"RemoteListener_start___closure0","ranges":[{"startOffset":283444,"endOffset":283549,"count":1}],"isBlockCoverage":true},{"functionName":"RemoteListener__serializeGroup_closure","ranges":[{"startOffset":283595,"endOffset":283734,"count":1}],"isBlockCoverage":true},{"functionName":"RemoteListener__serializeTest_closure","ranges":[{"startOffset":283779,"endOffset":283951,"count":1}],"isBlockCoverage":true},{"functionName":"RemoteListener__runLiveTest_closure","ranges":[{"startOffset":283994,"endOffset":284076,"count":1}],"isBlockCoverage":true},{"functionName":"RemoteListener__runLiveTest_closure0","ranges":[{"startOffset":284120,"endOffset":284202,"count":1}],"isBlockCoverage":true},{"functionName":"RemoteListener__runLiveTest_closure1","ranges":[{"startOffset":284246,"endOffset":284358,"count":1}],"isBlockCoverage":true},{"functionName":"RemoteListener__runLiveTest_closure2","ranges":[{"startOffset":284402,"endOffset":284511,"count":1}],"isBlockCoverage":true},{"functionName":"RemoteListener__runLiveTest_closure3","ranges":[{"startOffset":284555,"endOffset":284667,"count":1}],"isBlockCoverage":true},{"functionName":"RemoteListener__runLiveTest__closure","ranges":[{"startOffset":284711,"endOffset":284793,"count":1}],"isBlockCoverage":true},{"functionName":"DelegatingSink","ranges":[{"startOffset":284822,"endOffset":284911,"count":0}],"isBlockCoverage":false},{"functionName":"None","ranges":[{"startOffset":284919,"endOffset":284942,"count":1}],"isBlockCoverage":true},{"functionName":"Scanner","ranges":[{"startOffset":284953,"endOffset":285079,"count":0}],"isBlockCoverage":false},{"functionName":"EmptyUnmodifiableSet","ranges":[{"startOffset":285103,"endOffset":285165,"count":1}],"isBlockCoverage":true},{"functionName":"Style__getPlatformStyle","ranges":[{"startOffset":285196,"endOffset":285573,"count":0}],"isBlockCoverage":false},{"functionName":"Style","ranges":[{"startOffset":285586,"endOffset":285610,"count":0}],"isBlockCoverage":false},{"functionName":"Pool$","ranges":[{"startOffset":285623,"endOffset":286231,"count":0}],"isBlockCoverage":false},{"functionName":"Pool","ranges":[{"startOffset":286243,"endOffset":286547,"count":0}],"isBlockCoverage":false},{"functionName":"Pool_close_closure","ranges":[{"startOffset":286573,"endOffset":286635,"count":0}],"isBlockCoverage":false},{"functionName":"Pool__onResourceReleaseAllowed_closure","ranges":[{"startOffset":286681,"endOffset":286794,"count":0}],"isBlockCoverage":false},{"functionName":"Pool__runOnRelease_closure","ranges":[{"startOffset":286828,"endOffset":286898,"count":0}],"isBlockCoverage":false},{"functionName":"Pool__runOnRelease_closure0","ranges":[{"startOffset":286933,"endOffset":287004,"count":0}],"isBlockCoverage":false},{"functionName":"PoolResource","ranges":[{"startOffset":287024,"endOffset":287110,"count":0}],"isBlockCoverage":false},{"functionName":"mapStackTrace","ranges":[{"startOffset":287131,"endOffset":288220,"count":0}],"isBlockCoverage":false},{"functionName":"_prettifyMember","ranges":[{"startOffset":288243,"endOffset":289263,"count":0}],"isBlockCoverage":false},{"functionName":"mapStackTrace_closure","ranges":[{"startOffset":289292,"endOffset":289456,"count":0}],"isBlockCoverage":false},{"functionName":"mapStackTrace_closure0","ranges":[{"startOffset":289486,"endOffset":289676,"count":0}],"isBlockCoverage":false},{"functionName":"mapStackTrace_closure1","ranges":[{"startOffset":289706,"endOffset":289747,"count":0}],"isBlockCoverage":false},{"functionName":"_prettifyMember_closure","ranges":[{"startOffset":289778,"endOffset":289820,"count":0}],"isBlockCoverage":false},{"functionName":"_prettifyMember_closure0","ranges":[{"startOffset":289852,"endOffset":289895,"count":0}],"isBlockCoverage":false},{"functionName":"StackZoneSpecification","ranges":[{"startOffset":289925,"endOffset":290121,"count":1}],"isBlockCoverage":true},{"functionName":"StackZoneSpecification_chainFor_closure","ranges":[{"startOffset":290168,"endOffset":290252,"count":0}],"isBlockCoverage":false},{"functionName":"StackZoneSpecification_chainFor_closure0","ranges":[{"startOffset":290300,"endOffset":290414,"count":0}],"isBlockCoverage":false},{"functionName":"StackZoneSpecification__registerCallback_closure","ranges":[{"startOffset":290470,"endOffset":290642,"count":1}],"isBlockCoverage":true},{"functionName":"StackZoneSpecification__registerUnaryCallback_closure","ranges":[{"startOffset":290703,"endOffset":290900,"count":1}],"isBlockCoverage":true},{"functionName":"StackZoneSpecification__registerUnaryCallback__closure","ranges":[{"startOffset":290962,"endOffset":291104,"count":1}],"isBlockCoverage":true},{"functionName":"StackZoneSpecification__registerBinaryCallback_closure","ranges":[{"startOffset":291166,"endOffset":291386,"count":1}],"isBlockCoverage":true},{"functionName":"StackZoneSpecification__registerBinaryCallback__closure","ranges":[{"startOffset":291449,"endOffset":291627,"count":1}],"isBlockCoverage":true},{"functionName":"StackZoneSpecification__currentTrace_closure","ranges":[{"startOffset":291679,"endOffset":291827,"count":1}],"isBlockCoverage":true},{"functionName":"_Node","ranges":[{"startOffset":291840,"endOffset":291919,"count":1}],"isBlockCoverage":true},{"functionName":"Group$","ranges":[{"startOffset":291933,"endOffset":292150,"count":1}],"isBlockCoverage":true},{"functionName":"Group","ranges":[{"startOffset":292163,"endOffset":292362,"count":1}],"isBlockCoverage":true},{"functionName":"Group_forPlatform_closure","ranges":[{"startOffset":292395,"endOffset":292467,"count":1}],"isBlockCoverage":true},{"functionName":"Group__map_closure","ranges":[{"startOffset":292493,"endOffset":292558,"count":1}],"isBlockCoverage":true},{"functionName":"Group__map_closure0","ranges":[{"startOffset":292585,"endOffset":292623,"count":1}],"isBlockCoverage":true},{"functionName":"Metadata__parseOnPlatform","ranges":[{"startOffset":292656,"endOffset":292775,"count":1}],"isBlockCoverage":true},{"functionName":"Metadata__parseTags","ranges":[{"startOffset":292802,"endOffset":292889,"count":1}],"isBlockCoverage":true},{"functionName":"Metadata_Metadata","ranges":[{"startOffset":292914,"endOffset":293928,"count":1},{"startOffset":293321,"endOffset":293340,"count":0},{"startOffset":293880,"endOffset":293927,"count":0}],"isBlockCoverage":true},{"functionName":"Metadata$_","ranges":[{"startOffset":293946,"endOffset":294846,"count":1},{"startOffset":294749,"endOffset":294795,"count":0}],"isBlockCoverage":true},{"functionName":"Metadata$parse","ranges":[{"startOffset":294868,"endOffset":295398,"count":1},{"startOffset":294999,"endOffset":295008,"count":0},{"startOffset":295061,"endOffset":295067,"count":0},{"startOffset":295301,"endOffset":295347,"count":0}],"isBlockCoverage":true},{"functionName":"Metadata$deserialize","ranges":[{"startOffset":295426,"endOffset":296886,"count":1},{"startOffset":295595,"endOffset":295675,"count":0},{"startOffset":296451,"endOffset":296672,"count":0}],"isBlockCoverage":true},{"functionName":"Metadata__deserializeTimeout","ranges":[{"startOffset":296922,"endOffset":297350,"count":1},{"startOffset":297058,"endOffset":297085,"count":0},{"startOffset":297241,"endOffset":297349,"count":0}],"isBlockCoverage":true},{"functionName":"Metadata","ranges":[{"startOffset":297366,"endOffset":297685,"count":1}],"isBlockCoverage":true},{"functionName":"Metadata_Metadata__unresolved","ranges":[{"startOffset":297722,"endOffset":298035,"count":1}],"isBlockCoverage":true},{"functionName":"Metadata_Metadata_closure","ranges":[{"startOffset":298068,"endOffset":298138,"count":1}],"isBlockCoverage":true},{"functionName":"Metadata$deserialize_closure","ranges":[{"startOffset":298174,"endOffset":298221,"count":1}],"isBlockCoverage":true},{"functionName":"Metadata__validateTags_closure","ranges":[{"startOffset":298259,"endOffset":298308,"count":1}],"isBlockCoverage":true},{"functionName":"Metadata__validateTags_closure0","ranges":[{"startOffset":298347,"endOffset":298397,"count":1}],"isBlockCoverage":true},{"functionName":"Metadata_validatePlatformSelectors_closure","ranges":[{"startOffset":298447,"endOffset":298542,"count":1}],"isBlockCoverage":true},{"functionName":"Metadata_merge_closure","ranges":[{"startOffset":298572,"endOffset":298613,"count":1}],"isBlockCoverage":true},{"functionName":"Metadata_merge_closure0","ranges":[{"startOffset":298644,"endOffset":298686,"count":1}],"isBlockCoverage":true},{"functionName":"Metadata_forPlatform_closure","ranges":[{"startOffset":298722,"endOffset":298825,"count":0}],"isBlockCoverage":false},{"functionName":"Metadata_serialize_closure","ranges":[{"startOffset":298859,"endOffset":298944,"count":1}],"isBlockCoverage":true},{"functionName":"Metadata_serialize_closure0","ranges":[{"startOffset":298979,"endOffset":299025,"count":1}],"isBlockCoverage":true},{"functionName":"IterableSet","ranges":[{"startOffset":299044,"endOffset":299138,"count":0}],"isBlockCoverage":false},{"functionName":"_IterableSet_SetMixin_UnmodifiableSetMixin","ranges":[{"startOffset":299188,"endOffset":299249,"count":0}],"isBlockCoverage":false},{"functionName":"Engine$","ranges":[{"startOffset":299264,"endOffset":300874,"count":0}],"isBlockCoverage":false},{"functionName":"Engine","ranges":[{"startOffset":300888,"endOffset":301558,"count":0}],"isBlockCoverage":false},{"functionName":"Engine_success_closure","ranges":[{"startOffset":301588,"endOffset":301629,"count":0}],"isBlockCoverage":false},{"functionName":"Engine_closure","ranges":[{"startOffset":301651,"endOffset":301709,"count":0}],"isBlockCoverage":false},{"functionName":"Engine_closure0","ranges":[{"startOffset":301732,"endOffset":301766,"count":0}],"isBlockCoverage":false},{"functionName":"Engine_run_closure","ranges":[{"startOffset":301792,"endOffset":301854,"count":0}],"isBlockCoverage":false},{"functionName":"Engine_run__closure","ranges":[{"startOffset":301881,"endOffset":301971,"count":0}],"isBlockCoverage":false},{"functionName":"Engine_run___closure","ranges":[{"startOffset":301999,"endOffset":302125,"count":0}],"isBlockCoverage":false},{"functionName":"Engine_run____closure","ranges":[{"startOffset":302154,"endOffset":302220,"count":0}],"isBlockCoverage":false},{"functionName":"Engine_run_closure0","ranges":[{"startOffset":302247,"endOffset":302338,"count":0}],"isBlockCoverage":false},{"functionName":"Engine__runLiveTest_closure","ranges":[{"startOffset":302373,"endOffset":302474,"count":0}],"isBlockCoverage":false},{"functionName":"Engine__runLiveTest_closure0","ranges":[{"startOffset":302510,"endOffset":302610,"count":0}],"isBlockCoverage":false},{"functionName":"Engine__runLiveTest_closure1","ranges":[{"startOffset":302646,"endOffset":302693,"count":0}],"isBlockCoverage":false},{"functionName":"Engine__runSkippedTest_closure","ranges":[{"startOffset":302731,"endOffset":302780,"count":0}],"isBlockCoverage":false},{"functionName":"Engine__runSkippedTest_closure0","ranges":[{"startOffset":302819,"endOffset":302924,"count":0}],"isBlockCoverage":false},{"functionName":"Engine__runSkippedTest_closure1","ranges":[{"startOffset":302963,"endOffset":303013,"count":0}],"isBlockCoverage":false},{"functionName":"binarySearch","ranges":[{"startOffset":303033,"endOffset":303712,"count":0}],"isBlockCoverage":false},{"functionName":"DelegatingStreamSubscription","ranges":[{"startOffset":303755,"endOffset":303802,"count":0}],"isBlockCoverage":false},{"functionName":"StreamCompleter","ranges":[{"startOffset":303821,"endOffset":303907,"count":1}],"isBlockCoverage":true},{"functionName":"_CompleterStream","ranges":[{"startOffset":303927,"endOffset":304055,"count":1}],"isBlockCoverage":true},{"functionName":"BooleanSelectorImpl","ranges":[{"startOffset":304078,"endOffset":304145,"count":0}],"isBlockCoverage":false},{"functionName":"mapMap","ranges":[{"startOffset":304159,"endOffset":304498,"count":1}],"isBlockCoverage":true},{"functionName":"mergeMaps","ranges":[{"startOffset":304515,"endOffset":304721,"count":1}],"isBlockCoverage":true},{"functionName":"mapMap_closure","ranges":[{"startOffset":304743,"endOffset":304846,"count":1}],"isBlockCoverage":true},{"functionName":"mapMap_closure0","ranges":[{"startOffset":304869,"endOffset":305013,"count":1}],"isBlockCoverage":true},{"functionName":"mergeMaps_closure","ranges":[{"startOffset":305038,"endOffset":305181,"count":1}],"isBlockCoverage":true},{"functionName":"UnionSetController$","ranges":[{"startOffset":305208,"endOffset":305497,"count":0}],"isBlockCoverage":false},{"functionName":"UnionSetController","ranges":[{"startOffset":305523,"endOffset":305678,"count":0}],"isBlockCoverage":false},{"functionName":"_IsTrue","ranges":[{"startOffset":305693,"endOffset":305719,"count":1}],"isBlockCoverage":true},{"functionName":"_Predicate","ranges":[{"startOffset":305737,"endOffset":305868,"count":0}],"isBlockCoverage":false},{"functionName":"FileLocation$_","ranges":[{"startOffset":305890,"endOffset":306294,"count":0}],"isBlockCoverage":false},{"functionName":"_FileSpan$","ranges":[{"startOffset":306312,"endOffset":306850,"count":0}],"isBlockCoverage":false},{"functionName":"SourceFile","ranges":[{"startOffset":306868,"endOffset":307027,"count":0}],"isBlockCoverage":false},{"functionName":"FileLocation","ranges":[{"startOffset":307047,"endOffset":307130,"count":0}],"isBlockCoverage":false},{"functionName":"_FileSpan","ranges":[{"startOffset":307147,"endOffset":307265,"count":0}],"isBlockCoverage":false},{"functionName":"SourceSpanMixin","ranges":[{"startOffset":307288,"endOffset":307322,"count":0}],"isBlockCoverage":false},{"functionName":"Trace_Trace$current","ranges":[{"startOffset":307349,"endOffset":307488,"count":0}],"isBlockCoverage":false},{"functionName":"Trace_Trace$from","ranges":[{"startOffset":307512,"endOffset":307838,"count":1},{"startOffset":307563,"endOffset":307639,"count":0},{"startOffset":307695,"endOffset":307837,"count":0}],"isBlockCoverage":true},{"functionName":"Trace_Trace$parse","ranges":[{"startOffset":307863,"endOffset":309377,"count":0}],"isBlockCoverage":false},{"functionName":"Trace__parseVM","ranges":[{"startOffset":309399,"endOffset":310090,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseV8","ranges":[{"startOffset":310111,"endOffset":310662,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseJSCore","ranges":[{"startOffset":310687,"endOffset":311118,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseFirefox","ranges":[{"startOffset":311144,"endOffset":311604,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseFriendly","ranges":[{"startOffset":311631,"endOffset":312181,"count":0}],"isBlockCoverage":false},{"functionName":"Trace","ranges":[{"startOffset":312194,"endOffset":312274,"count":0}],"isBlockCoverage":false},{"functionName":"Trace_Trace$current_closure","ranges":[{"startOffset":312309,"endOffset":312407,"count":0}],"isBlockCoverage":false},{"functionName":"Trace_Trace$from_closure","ranges":[{"startOffset":312439,"endOffset":312507,"count":0}],"isBlockCoverage":false},{"functionName":"Trace__parseVM_closure","ranges":[{"startOffset":312537,"endOffset":312578,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseV8_closure","ranges":[{"startOffset":312607,"endOffset":312647,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseV8_closure0","ranges":[{"startOffset":312677,"endOffset":312718,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseJSCore_closure","ranges":[{"startOffset":312751,"endOffset":312795,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseJSCore_closure0","ranges":[{"startOffset":312829,"endOffset":312874,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseFirefox_closure","ranges":[{"startOffset":312908,"endOffset":312953,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseFirefox_closure0","ranges":[{"startOffset":312988,"endOffset":313034,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseFriendly_closure","ranges":[{"startOffset":313069,"endOffset":313115,"count":0}],"isBlockCoverage":false},{"functionName":"Trace$parseFriendly_closure0","ranges":[{"startOffset":313151,"endOffset":313198,"count":0}],"isBlockCoverage":false},{"functionName":"Trace_foldFrames_closure","ranges":[{"startOffset":313230,"endOffset":313305,"count":0}],"isBlockCoverage":false},{"functionName":"Trace_foldFrames_closure0","ranges":[{"startOffset":313338,"endOffset":313408,"count":0}],"isBlockCoverage":false},{"functionName":"Trace_toString_closure0","ranges":[{"startOffset":313439,"endOffset":313481,"count":0}],"isBlockCoverage":false},{"functionName":"Trace_toString_closure","ranges":[{"startOffset":313511,"endOffset":313579,"count":0}],"isBlockCoverage":false},{"functionName":"RunnerSuite","ranges":[{"startOffset":313598,"endOffset":313764,"count":0}],"isBlockCoverage":false},{"functionName":"RunnerSuiteController","ranges":[{"startOffset":313793,"endOffset":314020,"count":0}],"isBlockCoverage":false},{"functionName":"RunnerSuiteController__close_closure","ranges":[{"startOffset":314064,"endOffset":314144,"count":0}],"isBlockCoverage":false},{"functionName":"FutureGroup","ranges":[{"startOffset":314170,"endOffset":314384,"count":0}],"isBlockCoverage":false},{"functionName":"FutureGroup_add_closure","ranges":[{"startOffset":314411,"endOffset":314505,"count":0}],"isBlockCoverage":false},{"functionName":"FutureGroup_add_closure0","ranges":[{"startOffset":314533,"endOffset":314601,"count":0}],"isBlockCoverage":false},{"functionName":"ValueResult","ranges":[{"startOffset":314616,"endOffset":314696,"count":1}],"isBlockCoverage":true},{"functionName":"PackageConfigResolver__normalizeMap","ranges":[{"startOffset":314739,"endOffset":314975,"count":1}],"isBlockCoverage":true},{"functionName":"PackageConfigResolver","ranges":[{"startOffset":315004,"endOffset":315080,"count":1}],"isBlockCoverage":true},{"functionName":"PackageConfigResolver__normalizeMap_closure","ranges":[{"startOffset":315131,"endOffset":315193,"count":1}],"isBlockCoverage":true},{"functionName":"UrlStyle","ranges":[{"startOffset":315209,"endOffset":315397,"count":0}],"isBlockCoverage":false},{"functionName":"ErrorResult","ranges":[{"startOffset":315423,"endOffset":315510,"count":0}],"isBlockCoverage":false},{"functionName":"SourceLocation$","ranges":[{"startOffset":315533,"endOffset":316255,"count":0}],"isBlockCoverage":false},{"functionName":"SourceLocation","ranges":[{"startOffset":316277,"endOffset":316429,"count":0}],"isBlockCoverage":false},{"functionName":"SourceSpan","ranges":[{"startOffset":316447,"endOffset":316476,"count":0}],"isBlockCoverage":false},{"functionName":"SourceSpanBase","ranges":[{"startOffset":316498,"endOffset":316531,"count":0}],"isBlockCoverage":false},{"functionName":"GroupEntry","ranges":[{"startOffset":316549,"endOffset":316578,"count":0}],"isBlockCoverage":false},{"functionName":"LiveTestController$","ranges":[{"startOffset":316605,"endOffset":317396,"count":1}],"isBlockCoverage":true},{"functionName":"_LiveTest","ranges":[{"startOffset":317413,"endOffset":317494,"count":1}],"isBlockCoverage":true},{"functionName":"LiveTestController","ranges":[{"startOffset":317520,"endOffset":318000,"count":1}],"isBlockCoverage":true},{"functionName":"Test","ranges":[{"startOffset":318012,"endOffset":318035,"count":0}],"isBlockCoverage":false},{"functionName":"errorsDontStopTest","ranges":[{"startOffset":318061,"endOffset":318525,"count":0}],"isBlockCoverage":false},{"functionName":"errorsDontStopTest_closure","ranges":[{"startOffset":318559,"endOffset":318659,"count":0}],"isBlockCoverage":false},{"functionName":"errorsDontStopTest_closure0","ranges":[{"startOffset":318694,"endOffset":318740,"count":0}],"isBlockCoverage":false},{"functionName":"Result","ranges":[{"startOffset":318761,"endOffset":318786,"count":0}],"isBlockCoverage":false},{"functionName":"StringDescription","ranges":[{"startOffset":318807,"endOffset":318867,"count":0}],"isBlockCoverage":false},{"functionName":"FeatureMatcher","ranges":[{"startOffset":318885,"endOffset":318918,"count":0}],"isBlockCoverage":false},{"functionName":"PosixStyle","ranges":[{"startOffset":318932,"endOffset":319073,"count":0}],"isBlockCoverage":false},{"functionName":"StringScannerException$","ranges":[{"startOffset":319104,"endOffset":319201,"count":0}],"isBlockCoverage":false},{"functionName":"StringScannerException","ranges":[{"startOffset":319231,"endOffset":319359,"count":0}],"isBlockCoverage":false},{"functionName":"PlatformSelector$parse","ranges":[{"startOffset":319389,"endOffset":319570,"count":0}],"isBlockCoverage":false},{"functionName":"PlatformSelector__wrapFormatException","ranges":[{"startOffset":319615,"endOffset":319694,"count":0}],"isBlockCoverage":false},{"functionName":"PlatformSelector","ranges":[{"startOffset":319718,"endOffset":319798,"count":1}],"isBlockCoverage":true},{"functionName":"PlatformSelector$parse_closure","ranges":[{"startOffset":319836,"endOffset":319913,"count":0}],"isBlockCoverage":false},{"functionName":"PlatformSelector_validate_closure","ranges":[{"startOffset":319954,"endOffset":320067,"count":0}],"isBlockCoverage":false},{"functionName":"PlatformSelector_validate__closure","ranges":[{"startOffset":320109,"endOffset":320196,"count":0}],"isBlockCoverage":false},{"functionName":"PlatformSelector_evaluate_closure","ranges":[{"startOffset":320237,"endOffset":320317,"count":1}],"isBlockCoverage":true},{"functionName":"SuitePlatform$","ranges":[{"startOffset":320339,"endOffset":320703,"count":1},{"startOffset":320429,"endOffset":320433,"count":0},{"startOffset":320533,"endOffset":320640,"count":0}],"isBlockCoverage":true},{"functionName":"SuitePlatform","ranges":[{"startOffset":320724,"endOffset":320837,"count":1}],"isBlockCoverage":true},{"functionName":"StackTraceMapper","ranges":[{"startOffset":320861,"endOffset":320896,"count":0}],"isBlockCoverage":false},{"functionName":"LiveSuite","ranges":[{"startOffset":320913,"endOffset":320941,"count":0}],"isBlockCoverage":false},{"functionName":"JSStackTraceMapper_deserialize","ranges":[{"startOffset":320979,"endOffset":321921,"count":1},{"startOffset":321375,"endOffset":321508,"count":0}],"isBlockCoverage":true},{"functionName":"JSStackTraceMapper__deserializePackageConfigMap","ranges":[{"startOffset":321976,"endOffset":322130,"count":1}],"isBlockCoverage":true},{"functionName":"JSStackTraceMapper","ranges":[{"startOffset":322156,"endOffset":322355,"count":1}],"isBlockCoverage":true},{"functionName":"JSStackTraceMapper__deserializePackageConfigMap_closure","ranges":[{"startOffset":322418,"endOffset":322492,"count":1}],"isBlockCoverage":true},{"functionName":"StreamGroup","ranges":[{"startOffset":322518,"endOffset":322755,"count":0}],"isBlockCoverage":false},{"functionName":"StreamGroup_add_closure","ranges":[{"startOffset":322782,"endOffset":322824,"count":0}],"isBlockCoverage":false},{"functionName":"StreamGroup_add_closure0","ranges":[{"startOffset":322852,"endOffset":322948,"count":0}],"isBlockCoverage":false},{"functionName":"StreamGroup__onListen_closure","ranges":[{"startOffset":322981,"endOffset":323054,"count":0}],"isBlockCoverage":false},{"functionName":"StreamGroup__onCancelBroadcast_closure","ranges":[{"startOffset":323096,"endOffset":323178,"count":0}],"isBlockCoverage":false},{"functionName":"StreamGroup__listenToStream_closure","ranges":[{"startOffset":323217,"endOffset":323324,"count":0}],"isBlockCoverage":false},{"functionName":"_StreamGroupState","ranges":[{"startOffset":323345,"endOffset":323405,"count":1}],"isBlockCoverage":true},{"functionName":"Token","ranges":[{"startOffset":323414,"endOffset":323488,"count":0}],"isBlockCoverage":false},{"functionName":"IdentifierToken","ranges":[{"startOffset":323507,"endOffset":323591,"count":0}],"isBlockCoverage":false},{"functionName":"TokenType","ranges":[{"startOffset":323604,"endOffset":323656,"count":1}],"isBlockCoverage":true},{"functionName":"UnmodifiableSetView$","ranges":[{"startOffset":323684,"endOffset":323800,"count":0}],"isBlockCoverage":false},{"functionName":"UnmodifiableSetView","ranges":[{"startOffset":323827,"endOffset":323915,"count":1}],"isBlockCoverage":true},{"functionName":"UnmodifiableSetMixin","ranges":[{"startOffset":323943,"endOffset":323982,"count":0}],"isBlockCoverage":false},{"functionName":"_UnmodifiableSetView_DelegatingSet_UnmodifiableSetMixin","ranges":[{"startOffset":324045,"endOffset":324119,"count":0}],"isBlockCoverage":false},{"functionName":"WindowsStyle","ranges":[{"startOffset":324139,"endOffset":324331,"count":0}],"isBlockCoverage":false},{"functionName":"WindowsStyle_absolutePathToUri_closure","ranges":[{"startOffset":324377,"endOffset":324434,"count":0}],"isBlockCoverage":false},{"functionName":"decodeVlq","ranges":[{"startOffset":324451,"endOffset":325682,"count":0}],"isBlockCoverage":false},{"functionName":"closure","ranges":[{"startOffset":325697,"endOffset":325723,"count":0}],"isBlockCoverage":false},{"functionName":"internalBootstrapBrowserTest","ranges":[{"startOffset":325759,"endOffset":326211,"count":1}],"isBlockCoverage":true},{"functionName":"internalBootstrapBrowserTest_closure","ranges":[{"startOffset":326255,"endOffset":326310,"count":1}],"isBlockCoverage":true},{"functionName":"StreamQueue","ranges":[{"startOffset":326336,"endOffset":326620,"count":1}],"isBlockCoverage":true},{"functionName":"StreamQueue__ensureListening_closure","ranges":[{"startOffset":326660,"endOffset":326740,"count":1}],"isBlockCoverage":true},{"functionName":"StreamQueue__ensureListening_closure1","ranges":[{"startOffset":326781,"endOffset":326862,"count":1}],"isBlockCoverage":true},{"functionName":"StreamQueue__ensureListening_closure0","ranges":[{"startOffset":326903,"endOffset":326984,"count":1}],"isBlockCoverage":true},{"functionName":"_EventRequest","ranges":[{"startOffset":327001,"endOffset":327033,"count":0}],"isBlockCoverage":false},{"functionName":"_NextRequest","ranges":[{"startOffset":327049,"endOffset":327135,"count":1}],"isBlockCoverage":true},{"functionName":"_RestRequest","ranges":[{"startOffset":327151,"endOffset":327271,"count":1}],"isBlockCoverage":true},{"functionName":"Parser","ranges":[{"startOffset":327281,"endOffset":327343,"count":0}],"isBlockCoverage":false},{"functionName":"Matcher","ranges":[{"startOffset":327354,"endOffset":327380,"count":0}],"isBlockCoverage":false},{"functionName":"SourceMapSpan","ranges":[{"startOffset":327397,"endOffset":327547,"count":0}],"isBlockCoverage":false},{"functionName":"SourceSpanFormatException$","ranges":[{"startOffset":327581,"endOffset":327682,"count":0}],"isBlockCoverage":false},{"functionName":"SourceSpanException","ranges":[{"startOffset":327709,"endOffset":327747,"count":0}],"isBlockCoverage":false},{"functionName":"SourceSpanFormatException","ranges":[{"startOffset":327780,"endOffset":327911,"count":0}],"isBlockCoverage":false},{"functionName":"State","ranges":[{"startOffset":327924,"endOffset":328002,"count":1}],"isBlockCoverage":true},{"functionName":"Status","ranges":[{"startOffset":328016,"endOffset":328065,"count":1}],"isBlockCoverage":true},{"functionName":"Result0","ranges":[{"startOffset":328080,"endOffset":328130,"count":1}],"isBlockCoverage":true},{"functionName":"expect","ranges":[{"startOffset":328144,"endOffset":328244,"count":1}],"isBlockCoverage":true},{"functionName":"_expect","ranges":[{"startOffset":328259,"endOffset":329408,"count":1},{"startOffset":328467,"endOffset":328550,"count":0},{"startOffset":328759,"endOffset":328803,"count":0},{"startOffset":329097,"endOffset":329407,"count":0}],"isBlockCoverage":true},{"functionName":"fail","ranges":[{"startOffset":329420,"endOffset":329505,"count":0}],"isBlockCoverage":false},{"functionName":"formatFailure","ranges":[{"startOffset":329526,"endOffset":330135,"count":0}],"isBlockCoverage":false},{"functionName":"TestFailure","ranges":[{"startOffset":330154,"endOffset":330211,"count":0}],"isBlockCoverage":false},{"functionName":"_expect_closure0","ranges":[{"startOffset":330235,"endOffset":330270,"count":0}],"isBlockCoverage":false},{"functionName":"_expect_closure","ranges":[{"startOffset":330293,"endOffset":330327,"count":1}],"isBlockCoverage":true},{"functionName":"method1","ranges":[{"startOffset":330342,"endOffset":330388,"count":1}],"isBlockCoverage":true},{"functionName":"method2","ranges":[{"startOffset":330403,"endOffset":330449,"count":0}],"isBlockCoverage":false},{"functionName":"main0","ranges":[{"startOffset":330462,"endOffset":330529,"count":1}],"isBlockCoverage":true},{"functionName":"main_closure0","ranges":[{"startOffset":330550,"endOffset":330582,"count":1}],"isBlockCoverage":true},{"functionName":"main__closure","ranges":[{"startOffset":330603,"endOffset":330635,"count":1}],"isBlockCoverage":true},{"functionName":"StreamSinkCompleter","ranges":[{"startOffset":330669,"endOffset":330756,"count":1}],"isBlockCoverage":true},{"functionName":"_CompleterSink","ranges":[{"startOffset":330774,"endOffset":330961,"count":1}],"isBlockCoverage":true},{"functionName":"_CompleterSink__setDestinationSink_closure","ranges":[{"startOffset":331007,"endOffset":331068,"count":0}],"isBlockCoverage":false},{"functionName":"SubscriptionStream","ranges":[{"startOffset":331090,"endOffset":331200,"count":1}],"isBlockCoverage":true},{"functionName":"_CancelOnErrorSubscriptionWrapper","ranges":[{"startOffset":331237,"endOffset":331362,"count":0}],"isBlockCoverage":false},{"functionName":"_CancelOnErrorSubscriptionWrapper_onError_closure","ranges":[{"startOffset":331415,"endOffset":331541,"count":0}],"isBlockCoverage":false},{"functionName":"_CancelOnErrorSubscriptionWrapper_onError__closure","ranges":[{"startOffset":331595,"endOffset":331754,"count":0}],"isBlockCoverage":false},{"functionName":"Evaluator","ranges":[{"startOffset":331767,"endOffset":331825,"count":0}],"isBlockCoverage":false},{"functionName":"parseJsonExtended","ranges":[{"startOffset":331850,"endOffset":332085,"count":0}],"isBlockCoverage":false},{"functionName":"parseJson","ranges":[{"startOffset":332102,"endOffset":332830,"count":0}],"isBlockCoverage":false},{"functionName":"MultiSectionMapping$fromJson","ranges":[{"startOffset":332866,"endOffset":333186,"count":0}],"isBlockCoverage":false},{"functionName":"MappingBundle$fromJson","ranges":[{"startOffset":333216,"endOffset":333428,"count":0}],"isBlockCoverage":false},{"functionName":"SingleMapping$fromJson","ranges":[{"startOffset":333458,"endOffset":334453,"count":0}],"isBlockCoverage":false},{"functionName":"Mapping","ranges":[{"startOffset":334468,"endOffset":334494,"count":0}],"isBlockCoverage":false},{"functionName":"MultiSectionMapping","ranges":[{"startOffset":334521,"endOffset":334650,"count":0}],"isBlockCoverage":false},{"functionName":"MappingBundle","ranges":[{"startOffset":334671,"endOffset":334732,"count":0}],"isBlockCoverage":false},{"functionName":"SingleMapping","ranges":[{"startOffset":334753,"endOffset":335018,"count":0}],"isBlockCoverage":false},{"functionName":"SingleMapping$fromJson_closure","ranges":[{"startOffset":335056,"endOffset":335130,"count":0}],"isBlockCoverage":false},{"functionName":"SingleMapping__findLine_closure","ranges":[{"startOffset":335169,"endOffset":335243,"count":0}],"isBlockCoverage":false},{"functionName":"SingleMapping__findColumn_closure","ranges":[{"startOffset":335284,"endOffset":335362,"count":0}],"isBlockCoverage":false},{"functionName":"TargetLineEntry","ranges":[{"startOffset":335385,"endOffset":335472,"count":0}],"isBlockCoverage":false},{"functionName":"TargetEntry","ranges":[{"startOffset":335491,"endOffset":335685,"count":0}],"isBlockCoverage":false},{"functionName":"_MappingTokenizer","ranges":[{"startOffset":335710,"endOffset":335835,"count":0}],"isBlockCoverage":false},{"functionName":"_TokenKind","ranges":[{"startOffset":335853,"endOffset":335972,"count":1}],"isBlockCoverage":true},{"functionName":"LazyTrace","ranges":[{"startOffset":335989,"endOffset":336093,"count":1}],"isBlockCoverage":true},{"functionName":"LazyTrace_foldFrames_closure","ranges":[{"startOffset":336129,"endOffset":336259,"count":0}],"isBlockCoverage":false},{"functionName":"RuntimeSelection","ranges":[{"startOffset":336283,"endOffset":336318,"count":0}],"isBlockCoverage":false},{"functionName":"BooleanSelector","ranges":[{"startOffset":336348,"endOffset":336382,"count":0}],"isBlockCoverage":false},{"functionName":"All","ranges":[{"startOffset":336389,"endOffset":336411,"count":1}],"isBlockCoverage":true},{"functionName":"ParsedPath_ParsedPath$parse","ranges":[{"startOffset":336446,"endOffset":337648,"count":0}],"isBlockCoverage":false},{"functionName":"ParsedPath","ranges":[{"startOffset":337666,"endOffset":337813,"count":0}],"isBlockCoverage":false},{"functionName":"ParsedPath_normalize_closure","ranges":[{"startOffset":337849,"endOffset":337921,"count":0}],"isBlockCoverage":false},{"functionName":"PathException$","ranges":[{"startOffset":337943,"endOffset":338011,"count":0}],"isBlockCoverage":false},{"functionName":"PathException","ranges":[{"startOffset":338032,"endOffset":338091,"count":0}],"isBlockCoverage":false},{"functionName":"SourceSpanWithContext$","ranges":[{"startOffset":338121,"endOffset":338709,"count":0}],"isBlockCoverage":false},{"functionName":"SourceSpanWithContext","ranges":[{"startOffset":338738,"endOffset":338892,"count":0}],"isBlockCoverage":false},{"functionName":"LazyChain","ranges":[{"startOffset":338909,"endOffset":339001,"count":0}],"isBlockCoverage":false},{"functionName":"LazyChain_foldFrames_closure","ranges":[{"startOffset":339037,"endOffset":339167,"count":0}],"isBlockCoverage":false},{"functionName":"LazyChain_toTrace_closure","ranges":[{"startOffset":339200,"endOffset":339269,"count":0}],"isBlockCoverage":false},{"functionName":"StringScanner","ranges":[{"startOffset":339290,"endOffset":339322,"count":0}],"isBlockCoverage":false},{"functionName":"Declarer$","ranges":[{"startOffset":339339,"endOffset":340044,"count":1},{"startOffset":339457,"endOffset":339548,"count":0},{"startOffset":339600,"endOffset":339626,"count":0}],"isBlockCoverage":true},{"functionName":"Declarer","ranges":[{"startOffset":340060,"endOffset":340568,"count":1}],"isBlockCoverage":true},{"functionName":"Declarer_test_closure","ranges":[{"startOffset":340597,"endOffset":340688,"count":1}],"isBlockCoverage":true},{"functionName":"Declarer_test__closure","ranges":[{"startOffset":340718,"endOffset":340810,"count":1}],"isBlockCoverage":true},{"functionName":"Declarer_test___closure","ranges":[{"startOffset":340841,"endOffset":340934,"count":1}],"isBlockCoverage":true},{"functionName":"Declarer_group_closure","ranges":[{"startOffset":340964,"endOffset":341029,"count":1}],"isBlockCoverage":true},{"functionName":"Declarer_build_closure","ranges":[{"startOffset":341059,"endOffset":341125,"count":1}],"isBlockCoverage":true},{"functionName":"Declarer__runSetUps_closure","ranges":[{"startOffset":341160,"endOffset":341206,"count":1}],"isBlockCoverage":true},{"functionName":"Declarer__tearDownAll_closure","ranges":[{"startOffset":341243,"endOffset":341316,"count":0}],"isBlockCoverage":false},{"functionName":"Declarer__tearDownAll__closure","ranges":[{"startOffset":341354,"endOffset":341428,"count":0}],"isBlockCoverage":false},{"functionName":"Declarer__tearDownAll___closure","ranges":[{"startOffset":341467,"endOffset":341542,"count":0}],"isBlockCoverage":false},{"functionName":"PrintSink","ranges":[{"startOffset":341559,"endOffset":341626,"count":0}],"isBlockCoverage":false},{"functionName":"_expandSafe","ranges":[{"startOffset":341657,"endOffset":341839,"count":0}],"isBlockCoverage":false},{"functionName":"VariableNode","ranges":[{"startOffset":341859,"endOffset":341940,"count":0}],"isBlockCoverage":false},{"functionName":"NotNode","ranges":[{"startOffset":341955,"endOffset":342032,"count":0}],"isBlockCoverage":false},{"functionName":"OrNode","ranges":[{"startOffset":342046,"endOffset":342122,"count":0}],"isBlockCoverage":false},{"functionName":"AndNode","ranges":[{"startOffset":342137,"endOffset":342214,"count":0}],"isBlockCoverage":false},{"functionName":"ConditionalNode","ranges":[{"startOffset":342237,"endOffset":342361,"count":0}],"isBlockCoverage":false},{"functionName":"Highlighter__normalizeNewlines","ranges":[{"startOffset":342399,"endOffset":343195,"count":0}],"isBlockCoverage":false},{"functionName":"Highlighter__normalizeTrailingNewline","ranges":[{"startOffset":343240,"endOffset":344711,"count":0}],"isBlockCoverage":false},{"functionName":"Highlighter__normalizeEndOfLine","ranges":[{"startOffset":344750,"endOffset":345414,"count":0}],"isBlockCoverage":false},{"functionName":"Highlighter__lastLineLength","ranges":[{"startOffset":345449,"endOffset":345775,"count":0}],"isBlockCoverage":false},{"functionName":"Highlighter","ranges":[{"startOffset":345794,"endOffset":345999,"count":0}],"isBlockCoverage":false},{"functionName":"Highlighter__writeFirstLine_closure","ranges":[{"startOffset":346042,"endOffset":346147,"count":0}],"isBlockCoverage":false},{"functionName":"Highlighter__writeFirstLine_closure0","ranges":[{"startOffset":346191,"endOffset":346303,"count":0}],"isBlockCoverage":false},{"functionName":"Highlighter__writeFirstLine_closure1","ranges":[{"startOffset":346347,"endOffset":346455,"count":0}],"isBlockCoverage":false},{"functionName":"Highlighter__writeFirstLine_closure2","ranges":[{"startOffset":346499,"endOffset":346607,"count":0}],"isBlockCoverage":false},{"functionName":"Highlighter__writeIntermediateLines_closure","ranges":[{"startOffset":346658,"endOffset":346771,"count":0}],"isBlockCoverage":false},{"functionName":"Highlighter__writeLastLine_closure","ranges":[{"startOffset":346813,"endOffset":346917,"count":0}],"isBlockCoverage":false},{"functionName":"Highlighter__writeLastLine_closure0","ranges":[{"startOffset":346960,"endOffset":347071,"count":0}],"isBlockCoverage":false},{"functionName":"Highlighter__writeLastLine_closure1","ranges":[{"startOffset":347114,"endOffset":347221,"count":0}],"isBlockCoverage":false},{"functionName":"Highlighter__writeSidebar_closure","ranges":[{"startOffset":347262,"endOffset":347390,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_capture","ranges":[{"startOffset":347411,"endOffset":348428,"count":1},{"startOffset":347512,"endOffset":347565,"count":0},{"startOffset":347633,"endOffset":347760,"count":0}],"isBlockCoverage":true},{"functionName":"Chain_Chain$current","ranges":[{"startOffset":348455,"endOffset":348942,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_Chain$forTrace","ranges":[{"startOffset":348970,"endOffset":349524,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_Chain$parse","ranges":[{"startOffset":349549,"endOffset":350621,"count":0}],"isBlockCoverage":false},{"functionName":"Chain","ranges":[{"startOffset":350634,"endOffset":350684,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_capture_closure","ranges":[{"startOffset":350713,"endOffset":350804,"count":1}],"isBlockCoverage":true},{"functionName":"Chain_Chain$current_closure","ranges":[{"startOffset":350839,"endOffset":350937,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_Chain$forTrace_closure","ranges":[{"startOffset":350973,"endOffset":351045,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_Chain$parse_closure","ranges":[{"startOffset":351078,"endOffset":351122,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_Chain$parse_closure0","ranges":[{"startOffset":351156,"endOffset":351201,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_foldFrames_closure","ranges":[{"startOffset":351233,"endOffset":351332,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_foldFrames_closure0","ranges":[{"startOffset":351365,"endOffset":351434,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_toTrace_closure","ranges":[{"startOffset":351463,"endOffset":351503,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_toString_closure0","ranges":[{"startOffset":351534,"endOffset":351576,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_toString__closure0","ranges":[{"startOffset":351608,"endOffset":351651,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_toString_closure","ranges":[{"startOffset":351681,"endOffset":351749,"count":0}],"isBlockCoverage":false},{"functionName":"Chain_toString__closure","ranges":[{"startOffset":351780,"endOffset":351849,"count":0}],"isBlockCoverage":false},{"functionName":"Invoker_guard","ranges":[{"startOffset":351870,"endOffset":352115,"count":1}],"isBlockCoverage":true},{"functionName":"LocalTest","ranges":[{"startOffset":352132,"endOffset":352335,"count":1}],"isBlockCoverage":true},{"functionName":"Invoker","ranges":[{"startOffset":352350,"endOffset":352742,"count":1}],"isBlockCoverage":true},{"functionName":"Invoker_guard_closure","ranges":[{"startOffset":352771,"endOffset":352811,"count":1}],"isBlockCoverage":true},{"functionName":"Invoker_guard__closure","ranges":[{"startOffset":352841,"endOffset":353002,"count":0}],"isBlockCoverage":false},{"functionName":"Invoker_waitForOutstandingCallbacks_closure","ranges":[{"startOffset":353053,"endOffset":353229,"count":1}],"isBlockCoverage":true},{"functionName":"Invoker_waitForOutstandingCallbacks_closure0","ranges":[{"startOffset":353281,"endOffset":353397,"count":1}],"isBlockCoverage":true},{"functionName":"Invoker_heartbeat_message","ranges":[{"startOffset":353430,"endOffset":353501,"count":1}],"isBlockCoverage":true},{"functionName":"Invoker_heartbeat_closure","ranges":[{"startOffset":353534,"endOffset":353661,"count":1}],"isBlockCoverage":true},{"functionName":"Invoker_heartbeat__closure","ranges":[{"startOffset":353695,"endOffset":353823,"count":0}],"isBlockCoverage":false},{"functionName":"Invoker__handleError_closure","ranges":[{"startOffset":353859,"endOffset":353932,"count":0}],"isBlockCoverage":false},{"functionName":"Invoker__handleError_closure0","ranges":[{"startOffset":353969,"endOffset":354042,"count":0}],"isBlockCoverage":false},{"functionName":"Invoker__onRun_closure","ranges":[{"startOffset":354072,"endOffset":354187,"count":1}],"isBlockCoverage":true},{"functionName":"Invoker__onRun__closure","ranges":[{"startOffset":354218,"endOffset":354334,"count":1}],"isBlockCoverage":true},{"functionName":"Invoker__onRun___closure","ranges":[{"startOffset":354366,"endOffset":354434,"count":1}],"isBlockCoverage":true},{"functionName":"Invoker__onRun____closure","ranges":[{"startOffset":354467,"endOffset":354536,"count":1}],"isBlockCoverage":true},{"functionName":"Invoker__onRun___closure0","ranges":[{"startOffset":354569,"endOffset":354638,"count":1}],"isBlockCoverage":true},{"functionName":"_AsyncCounter","ranges":[{"startOffset":354659,"endOffset":354753,"count":1}],"isBlockCoverage":true},{"functionName":"StackTraceFormatter","ranges":[{"startOffset":354780,"endOffset":354899,"count":1}],"isBlockCoverage":true},{"functionName":"StackTraceFormatter_formatStackTrace_closure","ranges":[{"startOffset":354951,"endOffset":355039,"count":0}],"isBlockCoverage":false},{"functionName":"Suite__filterGroup","ranges":[{"startOffset":355065,"endOffset":355410,"count":1},{"startOffset":355223,"endOffset":355409,"count":0}],"isBlockCoverage":true},{"functionName":"Suite","ranges":[{"startOffset":355423,"endOffset":355528,"count":1}],"isBlockCoverage":true},{"functionName":"SuiteConfiguration__list","ranges":[{"startOffset":355560,"endOffset":355606,"count":0}],"isBlockCoverage":false},{"functionName":"SuiteConfiguration__map","ranges":[{"startOffset":355637,"endOffset":355695,"count":0}],"isBlockCoverage":false},{"functionName":"SuiteConfiguration","ranges":[{"startOffset":355721,"endOffset":355758,"count":0}],"isBlockCoverage":false},{"functionName":"RemoteException_serialize","ranges":[{"startOffset":355791,"endOffset":356552,"count":0}],"isBlockCoverage":false},{"functionName":"IntersectionSelector","ranges":[{"startOffset":356587,"endOffset":356688,"count":0}],"isBlockCoverage":false},{"functionName":"StreamChannel","ranges":[{"startOffset":356705,"endOffset":356737,"count":0}],"isBlockCoverage":false},{"functionName":"_StreamChannel","ranges":[{"startOffset":356755,"endOffset":356865,"count":1}],"isBlockCoverage":true},{"functionName":"StreamChannelMixin","ranges":[{"startOffset":356887,"endOffset":356924,"count":0}],"isBlockCoverage":false},{"functionName":"Timeout","ranges":[{"startOffset":356935,"endOffset":357022,"count":1}],"isBlockCoverage":true},{"functionName":"ExpandedReporter","ranges":[{"startOffset":357042,"endOffset":357603,"count":0}],"isBlockCoverage":false},{"functionName":"ExpandedReporter__onTestStarted_closure","ranges":[{"startOffset":357646,"endOffset":357759,"count":0}],"isBlockCoverage":false},{"functionName":"ExpandedReporter__onTestStarted_closure0","ranges":[{"startOffset":357803,"endOffset":357917,"count":0}],"isBlockCoverage":false},{"functionName":"ExpandedReporter__onTestStarted_closure1","ranges":[{"startOffset":357961,"endOffset":358075,"count":0}],"isBlockCoverage":false},{"functionName":"_declarer","ranges":[{"startOffset":358092,"endOffset":358479,"count":1},{"startOffset":358251,"endOffset":358478,"count":0}],"isBlockCoverage":true},{"functionName":"test","ranges":[{"startOffset":358491,"endOffset":358707,"count":1}],"isBlockCoverage":true},{"functionName":"group","ranges":[{"startOffset":358720,"endOffset":358937,"count":1}],"isBlockCoverage":true},{"functionName":"_declarer_closure","ranges":[{"startOffset":358962,"endOffset":358998,"count":0}],"isBlockCoverage":false},{"functionName":"_declarer__closure","ranges":[{"startOffset":359024,"endOffset":359087,"count":0}],"isBlockCoverage":false},{"functionName":"main","ranges":[{"startOffset":359099,"endOffset":359177,"count":1}],"isBlockCoverage":true},{"functionName":"main_closure","ranges":[{"startOffset":359197,"endOffset":359228,"count":1}],"isBlockCoverage":true},{"functionName":"RecursiveVisitor","ranges":[{"startOffset":359259,"endOffset":359294,"count":0}],"isBlockCoverage":false},{"functionName":"InternalStyle","ranges":[{"startOffset":359311,"endOffset":359343,"count":0}],"isBlockCoverage":false},{"functionName":"StreamChannelController$","ranges":[{"startOffset":359375,"endOffset":360324,"count":1}],"isBlockCoverage":true},{"functionName":"StreamChannelController","ranges":[{"startOffset":360355,"endOffset":360462,"count":1}],"isBlockCoverage":true},{"functionName":"Runtime_Runtime$deserialize","ranges":[{"startOffset":360497,"endOffset":361558,"count":1},{"startOffset":360735,"endOffset":361557,"count":0}],"isBlockCoverage":true},{"functionName":"Runtime","ranges":[{"startOffset":361573,"endOffset":361827,"count":1}],"isBlockCoverage":true},{"functionName":"Runtime_Runtime$deserialize_closure","ranges":[{"startOffset":361870,"endOffset":361954,"count":1}],"isBlockCoverage":true},{"functionName":"indent","ranges":[{"startOffset":361968,"endOffset":362129,"count":0}],"isBlockCoverage":false},{"functionName":"toSentence","ranges":[{"startOffset":362147,"endOffset":362529,"count":0}],"isBlockCoverage":false},{"functionName":"pluralize","ranges":[{"startOffset":362546,"endOffset":362649,"count":0}],"isBlockCoverage":false},{"functionName":"prefixLines","ranges":[{"startOffset":362668,"endOffset":363386,"count":0}],"isBlockCoverage":false},{"functionName":"closure0","ranges":[{"startOffset":363402,"endOffset":363429,"count":0}],"isBlockCoverage":false},{"functionName":"LiveSuiteController$","ranges":[{"startOffset":363457,"endOffset":364346,"count":0}],"isBlockCoverage":false},{"functionName":"_LiveSuite","ranges":[{"startOffset":364364,"endOffset":364447,"count":0}],"isBlockCoverage":false},{"functionName":"LiveSuiteController","ranges":[{"startOffset":364474,"endOffset":364920,"count":0}],"isBlockCoverage":false},{"functionName":"LiveSuiteController_closure","ranges":[{"startOffset":364955,"endOffset":365026,"count":0}],"isBlockCoverage":false},{"functionName":"LiveSuiteController_closure0","ranges":[{"startOffset":365062,"endOffset":365109,"count":0}],"isBlockCoverage":false},{"functionName":"LiveSuiteController_reportLiveTest_closure","ranges":[{"startOffset":365159,"endOffset":365309,"count":0}],"isBlockCoverage":false},{"functionName":"LiveSuiteController_close_closure","ranges":[{"startOffset":365350,"endOffset":365427,"count":0}],"isBlockCoverage":false},{"functionName":"asUri","ranges":[{"startOffset":365440,"endOffset":365612,"count":0}],"isBlockCoverage":false},{"functionName":"ensureTrailingSlash","ranges":[{"startOffset":365639,"endOffset":366120,"count":1},{"startOffset":365724,"endOffset":365758,"count":0},{"startOffset":365898,"endOffset":366119,"count":0}],"isBlockCoverage":true},{"functionName":"isAlphabetic","ranges":[{"startOffset":366140,"endOffset":366302,"count":0}],"isBlockCoverage":false},{"functionName":"isDriveLetter","ranges":[{"startOffset":366323,"endOffset":366734,"count":0}],"isBlockCoverage":false},{"functionName":"countCodeUnits","ranges":[{"startOffset":366756,"endOffset":367071,"count":0}],"isBlockCoverage":false},{"functionName":"findLineStart","ranges":[{"startOffset":367092,"endOffset":367938,"count":0}],"isBlockCoverage":false},{"functionName":"validateErrorArgs","ranges":[{"startOffset":367963,"endOffset":368466,"count":0}],"isBlockCoverage":false},{"functionName":"QueueList$","ranges":[{"startOffset":368496,"endOffset":368736,"count":1}],"isBlockCoverage":true},{"functionName":"QueueList__nextPowerOf2","ranges":[{"startOffset":368767,"endOffset":369042,"count":0}],"isBlockCoverage":false},{"functionName":"QueueList","ranges":[{"startOffset":369059,"endOffset":369215,"count":1}],"isBlockCoverage":true},{"functionName":"_QueueList_Object_ListMixin","ranges":[{"startOffset":369250,"endOffset":369296,"count":0}],"isBlockCoverage":false},{"functionName":"UnionSet","ranges":[{"startOffset":369319,"endOffset":369427,"count":0}],"isBlockCoverage":false},{"functionName":"UnionSet_length_closure","ranges":[{"startOffset":369454,"endOffset":369521,"count":0}],"isBlockCoverage":false},{"functionName":"UnionSet__iterable_closure","ranges":[{"startOffset":369551,"endOffset":369621,"count":0}],"isBlockCoverage":false},{"functionName":"_UnionSet_SetBase_UnmodifiableSetMixin","ranges":[{"startOffset":369663,"endOffset":369720,"count":0}],"isBlockCoverage":false},{"functionName":"_DelegatingIterableBase","ranges":[{"startOffset":369747,"endOffset":369789,"count":0}],"isBlockCoverage":false},{"functionName":"DelegatingIterable","ranges":[{"startOffset":369811,"endOffset":369848,"count":0}],"isBlockCoverage":false},{"functionName":"DelegatingSet","ranges":[{"startOffset":369865,"endOffset":369947,"count":0}],"isBlockCoverage":false},{"functionName":"TypeMatcher","ranges":[{"startOffset":369962,"endOffset":369992,"count":0}],"isBlockCoverage":false},{"functionName":"wrapMatcher","ranges":[{"startOffset":370011,"endOffset":370493,"count":1},{"startOffset":370116,"endOffset":370487,"count":0}],"isBlockCoverage":true},{"functionName":"escape","ranges":[{"startOffset":370507,"endOffset":370736,"count":0}],"isBlockCoverage":false},{"functionName":"_getHexLiteral","ranges":[{"startOffset":370758,"endOffset":371247,"count":0}],"isBlockCoverage":false},{"functionName":"wrapMatcher_closure","ranges":[{"startOffset":371274,"endOffset":371333,"count":0}],"isBlockCoverage":false},{"functionName":"escape_closure","ranges":[{"startOffset":371355,"endOffset":371388,"count":0}],"isBlockCoverage":false},{"functionName":"Context_Context","ranges":[{"startOffset":371411,"endOffset":371599,"count":0}],"isBlockCoverage":false},{"functionName":"_parseUri","ranges":[{"startOffset":371616,"endOffset":371786,"count":0}],"isBlockCoverage":false},{"functionName":"_validateArgList","ranges":[{"startOffset":371810,"endOffset":372805,"count":0}],"isBlockCoverage":false},{"functionName":"Context","ranges":[{"startOffset":372820,"endOffset":372910,"count":0}],"isBlockCoverage":false},{"functionName":"Context_join_closure","ranges":[{"startOffset":372938,"endOffset":372977,"count":0}],"isBlockCoverage":false},{"functionName":"Context_joinAll_closure","ranges":[{"startOffset":373008,"endOffset":373050,"count":0}],"isBlockCoverage":false},{"functionName":"Context_split_closure","ranges":[{"startOffset":373079,"endOffset":373119,"count":0}],"isBlockCoverage":false},{"functionName":"_validateArgList_closure","ranges":[{"startOffset":373151,"endOffset":373194,"count":0}],"isBlockCoverage":false},{"functionName":"_PathDirection","ranges":[{"startOffset":373216,"endOffset":373273,"count":1}],"isBlockCoverage":true},{"functionName":"_PathRelation","ranges":[{"startOffset":373294,"endOffset":373350,"count":1}],"isBlockCoverage":true},{"functionName":"_StringEqualsMatcher__writeLeading","ranges":[{"startOffset":373404,"endOffset":373714,"count":0}],"isBlockCoverage":false},{"functionName":"_StringEqualsMatcher__writeTrailing","ranges":[{"startOffset":373757,"endOffset":374094,"count":0}],"isBlockCoverage":false},{"functionName":"_StringEqualsMatcher","ranges":[{"startOffset":374122,"endOffset":374203,"count":0}],"isBlockCoverage":false},{"functionName":"_DeepMatcher","ranges":[{"startOffset":374223,"endOffset":374311,"count":0}],"isBlockCoverage":false},{"functionName":"_DeepMatcher__compareSets_closure","ranges":[{"startOffset":374352,"endOffset":374533,"count":0}],"isBlockCoverage":false},{"functionName":"PackageRootResolver","ranges":[{"startOffset":374560,"endOffset":374629,"count":0}],"isBlockCoverage":false},{"functionName":"SourceLocationMixin","ranges":[{"startOffset":374656,"endOffset":374694,"count":0}],"isBlockCoverage":false},{"functionName":"_MultiChannel$","ranges":[{"startOffset":374716,"endOffset":375095,"count":1}],"isBlockCoverage":true},{"functionName":"_MultiChannel","ranges":[{"startOffset":375116,"endOffset":375414,"count":1}],"isBlockCoverage":true},{"functionName":"_MultiChannel_closure","ranges":[{"startOffset":375443,"endOffset":375531,"count":1}],"isBlockCoverage":true},{"functionName":"_MultiChannel_closure0","ranges":[{"startOffset":375561,"endOffset":375627,"count":1}],"isBlockCoverage":true},{"functionName":"_MultiChannel_closure1","ranges":[{"startOffset":375657,"endOffset":375746,"count":1}],"isBlockCoverage":true},{"functionName":"_MultiChannel__closure","ranges":[{"startOffset":375776,"endOffset":375889,"count":1}],"isBlockCoverage":true},{"functionName":"_MultiChannel_virtualChannel_closure","ranges":[{"startOffset":375933,"endOffset":376041,"count":1}],"isBlockCoverage":true},{"functionName":"_MultiChannel_virtualChannel_closure0","ranges":[{"startOffset":376086,"endOffset":376195,"count":1}],"isBlockCoverage":true},{"functionName":"VirtualChannel","ranges":[{"startOffset":376217,"endOffset":376400,"count":1}],"isBlockCoverage":true},{"functionName":"Message","ranges":[{"startOffset":376415,"endOffset":376491,"count":0}],"isBlockCoverage":false},{"functionName":"MessageType","ranges":[{"startOffset":376510,"endOffset":376564,"count":1}],"isBlockCoverage":true},{"functionName":"current","ranges":[{"startOffset":376579,"endOffset":377522,"count":0}],"isBlockCoverage":false},{"functionName":"prettyPrint","ranges":[{"startOffset":377553,"endOffset":377748,"count":0}],"isBlockCoverage":false},{"functionName":"_typeName","ranges":[{"startOffset":377765,"endOffset":377994,"count":0}],"isBlockCoverage":false},{"functionName":"_escapeString","ranges":[{"startOffset":378015,"endOffset":378154,"count":0}],"isBlockCoverage":false},{"functionName":"prettyPrint__prettyPrint","ranges":[{"startOffset":378186,"endOffset":378292,"count":0}],"isBlockCoverage":false},{"functionName":"prettyPrint__prettyPrint_pp","ranges":[{"startOffset":378327,"endOffset":378461,"count":0}],"isBlockCoverage":false},{"functionName":"prettyPrint__prettyPrint_closure","ranges":[{"startOffset":378501,"endOffset":378578,"count":0}],"isBlockCoverage":false},{"functionName":"prettyPrint__prettyPrint_closure0","ranges":[{"startOffset":378619,"endOffset":378721,"count":0}],"isBlockCoverage":false},{"functionName":"prettyPrint__prettyPrint_closure1","ranges":[{"startOffset":378762,"endOffset":378840,"count":0}],"isBlockCoverage":false},{"functionName":"LiveTest","ranges":[{"startOffset":378856,"endOffset":378883,"count":0}],"isBlockCoverage":false},{"functionName":"Frame_Frame$parseVM","ranges":[{"startOffset":378922,"endOffset":379038,"count":0}],"isBlockCoverage":false},{"functionName":"Frame_Frame$parseV8","ranges":[{"startOffset":379065,"endOffset":379181,"count":0}],"isBlockCoverage":false},{"functionName":"Frame_Frame$parseFirefox","ranges":[{"startOffset":379213,"endOffset":379334,"count":0}],"isBlockCoverage":false},{"functionName":"Frame_Frame$parseFriendly","ranges":[{"startOffset":379367,"endOffset":379489,"count":0}],"isBlockCoverage":false},{"functionName":"Frame__uriOrPathToUri","ranges":[{"startOffset":379518,"endOffset":380076,"count":0}],"isBlockCoverage":false},{"functionName":"Frame__catchFormatException","ranges":[{"startOffset":380111,"endOffset":380455,"count":0}],"isBlockCoverage":false},{"functionName":"Frame","ranges":[{"startOffset":380468,"endOffset":380605,"count":0}],"isBlockCoverage":false},{"functionName":"Frame_Frame$parseVM_closure","ranges":[{"startOffset":380640,"endOffset":380711,"count":0}],"isBlockCoverage":false},{"functionName":"Frame_Frame$parseV8_closure","ranges":[{"startOffset":380746,"endOffset":380817,"count":0}],"isBlockCoverage":false},{"functionName":"Frame_Frame$parseV8_closure_parseLocation","ranges":[{"startOffset":380866,"endOffset":380951,"count":0}],"isBlockCoverage":false},{"functionName":"Frame_Frame$parseFirefox_closure","ranges":[{"startOffset":380991,"endOffset":381067,"count":0}],"isBlockCoverage":false},{"functionName":"Frame_Frame$parseFriendly_closure","ranges":[{"startOffset":381108,"endOffset":381185,"count":0}],"isBlockCoverage":false},{"functionName":"AsciiGlyphSet","ranges":[{"startOffset":381206,"endOffset":381238,"count":1}],"isBlockCoverage":true},{"functionName":"UnparsedFrame","ranges":[{"startOffset":381266,"endOffset":381349,"count":0}],"isBlockCoverage":false},{"functionName":"StreamChannelCompleter","ranges":[{"startOffset":381375,"endOffset":381623,"count":1}],"isBlockCoverage":true},{"functionName":"postMessageChannel","ranges":[{"startOffset":381649,"endOffset":382274,"count":1}],"isBlockCoverage":true},{"functionName":"postMessageChannel_closure","ranges":[{"startOffset":382308,"endOffset":382353,"count":1}],"isBlockCoverage":true},{"functionName":"postMessageChannel_closure0","ranges":[{"startOffset":382388,"endOffset":382464,"count":1}],"isBlockCoverage":true},{"functionName":"postMessageChannel__closure","ranges":[{"startOffset":382499,"endOffset":382575,"count":1}],"isBlockCoverage":true},{"functionName":"postMessageChannel__closure0","ranges":[{"startOffset":382611,"endOffset":382682,"count":1}],"isBlockCoverage":true},{"functionName":"postMessageChannel__closure1","ranges":[{"startOffset":382718,"endOffset":382827,"count":1}],"isBlockCoverage":true},{"functionName":"OperatingSystem_find","ranges":[{"startOffset":382855,"endOffset":383034,"count":1}],"isBlockCoverage":true},{"functionName":"OperatingSystem","ranges":[{"startOffset":383057,"endOffset":383147,"count":1}],"isBlockCoverage":true},{"functionName":"OperatingSystem_find_closure","ranges":[{"startOffset":383183,"endOffset":383260,"count":1}],"isBlockCoverage":true},{"functionName":"OperatingSystem_find_closure0","ranges":[{"startOffset":383297,"endOffset":383345,"count":1}],"isBlockCoverage":true},{"functionName":"SuiteChannelManager","ranges":[{"startOffset":383372,"endOffset":383520,"count":1}],"isBlockCoverage":true},{"functionName":"GuaranteeChannel$","ranges":[{"startOffset":383557,"endOffset":383845,"count":1}],"isBlockCoverage":true},{"functionName":"GuaranteeChannel","ranges":[{"startOffset":383869,"endOffset":384037,"count":1}],"isBlockCoverage":true},{"functionName":"GuaranteeChannel_closure","ranges":[{"startOffset":384069,"endOffset":384165,"count":1}],"isBlockCoverage":true},{"functionName":"GuaranteeChannel__closure","ranges":[{"startOffset":384198,"endOffset":384267,"count":1}],"isBlockCoverage":true},{"functionName":"_GuaranteeSink","ranges":[{"startOffset":384289,"endOffset":384584,"count":1}],"isBlockCoverage":true},{"functionName":"_GuaranteeSink__addError_closure","ranges":[{"startOffset":384624,"endOffset":384675,"count":0}],"isBlockCoverage":false},{"functionName":"_GuaranteeSink_addStream_closure","ranges":[{"startOffset":384715,"endOffset":384791,"count":1}],"isBlockCoverage":true},{"functionName":"UnicodeGlyphSet","ranges":[{"startOffset":384814,"endOffset":384848,"count":1}],"isBlockCoverage":true},{"functionName":"ClosedException$","ranges":[{"startOffset":384872,"endOffset":384928,"count":0}],"isBlockCoverage":false},{"functionName":"ClosedException","ranges":[{"startOffset":384951,"endOffset":384985,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":385218,"endOffset":385284,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":385304,"endOffset":385382,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":385400,"endOffset":385507,"count":0}],"isBlockCoverage":false},{"functionName":"get$runtimeType","ranges":[{"startOffset":385530,"endOffset":385597,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":385644,"endOffset":385701,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":385721,"endOffset":385788,"count":1},{"startOffset":385773,"endOffset":385781,"count":0}],"isBlockCoverage":true},{"functionName":"get$runtimeType","ranges":[{"startOffset":385811,"endOffset":385867,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":385923,"endOffset":385984,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":386002,"endOffset":386049,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":386069,"endOffset":386111,"count":0}],"isBlockCoverage":false},{"functionName":"get$runtimeType","ranges":[{"startOffset":386134,"endOffset":386190,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":386294,"endOffset":386336,"count":0}],"isBlockCoverage":false},{"functionName":"get$runtimeType","ranges":[{"startOffset":386359,"endOffset":386419,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":386437,"endOffset":386494,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":386659,"endOffset":386925,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":386943,"endOffset":387010,"count":0}],"isBlockCoverage":false},{"functionName":"add$1","ranges":[{"startOffset":387073,"endOffset":387290,"count":1},{"startOffset":387210,"endOffset":387256,"count":0}],"isBlockCoverage":true},{"functionName":"removeAt$1","ranges":[{"startOffset":387308,"endOffset":387608,"count":0}],"isBlockCoverage":false},{"functionName":"insert$2","ranges":[{"startOffset":387624,"endOffset":387991,"count":0}],"isBlockCoverage":false},{"functionName":"insertAll$2","ranges":[{"startOffset":388010,"endOffset":388615,"count":0}],"isBlockCoverage":false},{"functionName":"removeLast$0","ranges":[{"startOffset":388635,"endOffset":388887,"count":0}],"isBlockCoverage":false},{"functionName":"remove$1","ranges":[{"startOffset":388903,"endOffset":389218,"count":1},{"startOffset":388989,"endOffset":389038,"count":0},{"startOffset":389192,"endOffset":389217,"count":0}],"isBlockCoverage":true},{"functionName":"addAll$1","ranges":[{"startOffset":389234,"endOffset":389764,"count":0}],"isBlockCoverage":false},{"functionName":"forEach$1","ranges":[{"startOffset":389781,"endOffset":390106,"count":0}],"isBlockCoverage":false},{"functionName":"map$1$1","ranges":[{"startOffset":390121,"endOffset":390359,"count":0}],"isBlockCoverage":false},{"functionName":"join$1","ranges":[{"startOffset":390373,"endOffset":390629,"count":0}],"isBlockCoverage":false},{"functionName":"join$0","ranges":[{"startOffset":390643,"endOffset":390711,"count":0}],"isBlockCoverage":false},{"functionName":"fold$1$2","ranges":[{"startOffset":390727,"endOffset":391213,"count":1},{"startOffset":391010,"endOffset":391187,"count":0}],"isBlockCoverage":true},{"functionName":"firstWhere$2$orElse","ranges":[{"startOffset":391240,"endOffset":391854,"count":1},{"startOffset":391653,"endOffset":391717,"count":0},{"startOffset":391783,"endOffset":391853,"count":0}],"isBlockCoverage":true},{"functionName":"firstWhere$1","ranges":[{"startOffset":391874,"endOffset":391969,"count":1}],"isBlockCoverage":true},{"functionName":"elementAt$1","ranges":[{"startOffset":391988,"endOffset":392141,"count":1},{"startOffset":392073,"endOffset":392105,"count":0}],"isBlockCoverage":true},{"functionName":"sublist$2","ranges":[{"startOffset":392158,"endOffset":392671,"count":0}],"isBlockCoverage":false},{"functionName":"get$first","ranges":[{"startOffset":392688,"endOffset":392838,"count":1},{"startOffset":392767,"endOffset":392837,"count":0}],"isBlockCoverage":true},{"functionName":"get$last","ranges":[{"startOffset":392854,"endOffset":393028,"count":1},{"startOffset":392957,"endOffset":393027,"count":0}],"isBlockCoverage":true},{"functionName":"get$single","ranges":[{"startOffset":393046,"endOffset":393372,"count":0}],"isBlockCoverage":false},{"functionName":"setRange$4","ranges":[{"startOffset":393390,"endOffset":394326,"count":0}],"isBlockCoverage":false},{"functionName":"setRange$3","ranges":[{"startOffset":394344,"endOffset":394459,"count":0}],"isBlockCoverage":false},{"functionName":"fillRange$3","ranges":[{"startOffset":394478,"endOffset":394843,"count":0}],"isBlockCoverage":false},{"functionName":"replaceRange$3","ranges":[{"startOffset":394865,"endOffset":395890,"count":0}],"isBlockCoverage":false},{"functionName":"contains$1","ranges":[{"startOffset":395908,"endOffset":396081,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":396100,"endOffset":396162,"count":1}],"isBlockCoverage":true},{"functionName":"toString$0","ranges":[{"startOffset":396180,"endOffset":396276,"count":0}],"isBlockCoverage":false},{"functionName":"toSet$0","ranges":[{"startOffset":396291,"endOffset":396422,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":396442,"endOffset":396589,"count":1}],"isBlockCoverage":true},{"functionName":"get$hashCode","ranges":[{"startOffset":396609,"endOffset":396687,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":396705,"endOffset":396761,"count":1}],"isBlockCoverage":true},{"functionName":"set$length","ranges":[{"startOffset":396779,"endOffset":397195,"count":1},{"startOffset":396884,"endOffset":396937,"count":0},{"startOffset":396978,"endOffset":397046,"count":0},{"startOffset":397080,"endOffset":397154,"count":0}],"isBlockCoverage":true},{"functionName":"$index","ranges":[{"startOffset":397209,"endOffset":397523,"count":1},{"startOffset":397307,"endOffset":397368,"count":0},{"startOffset":397426,"endOffset":397487,"count":0}],"isBlockCoverage":true},{"functionName":"$indexSet","ranges":[{"startOffset":397540,"endOffset":398028,"count":1},{"startOffset":397720,"endOffset":397774,"count":0},{"startOffset":397811,"endOffset":397872,"count":0},{"startOffset":397930,"endOffset":397991,"count":0}],"isBlockCoverage":true},{"functionName":"get$current","ranges":[{"startOffset":398194,"endOffset":398240,"count":1}],"isBlockCoverage":true},{"functionName":"moveNext$0","ranges":[{"startOffset":398258,"endOffset":398662,"count":1},{"startOffset":398403,"endOffset":398465,"count":0}],"isBlockCoverage":true},{"functionName":"set$_current","ranges":[{"startOffset":398682,"endOffset":398771,"count":1}],"isBlockCoverage":true},{"functionName":"floor$0","ranges":[{"startOffset":398837,"endOffset":399285,"count":0}],"isBlockCoverage":false},{"functionName":"round$0","ranges":[{"startOffset":399300,"endOffset":399582,"count":1},{"startOffset":399425,"endOffset":399581,"count":0}],"isBlockCoverage":true},{"functionName":"toRadixString$1","ranges":[{"startOffset":399605,"endOffset":400471,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":400489,"endOffset":400625,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":400645,"endOffset":401151,"count":0}],"isBlockCoverage":false},{"functionName":"$mod","ranges":[{"startOffset":401163,"endOffset":401414,"count":0}],"isBlockCoverage":false},{"functionName":"$tdiv","ranges":[{"startOffset":401427,"endOffset":401624,"count":0}],"isBlockCoverage":false},{"functionName":"_tdivFast$1","ranges":[{"startOffset":401643,"endOffset":401777,"count":1},{"startOffset":401735,"endOffset":401770,"count":0}],"isBlockCoverage":true},{"functionName":"_tdivSlow$1","ranges":[{"startOffset":401796,"endOffset":402270,"count":0}],"isBlockCoverage":false},{"functionName":"_shlPositive$1","ranges":[{"startOffset":402292,"endOffset":402380,"count":0}],"isBlockCoverage":false},{"functionName":"_shrOtherPositive$1","ranges":[{"startOffset":402407,"endOffset":402644,"count":0}],"isBlockCoverage":false},{"functionName":"_shrReceiverPositive$1","ranges":[{"startOffset":402674,"endOffset":402843,"count":0}],"isBlockCoverage":false},{"functionName":"_shrBothPositive$1","ranges":[{"startOffset":402869,"endOffset":402952,"count":0}],"isBlockCoverage":false},{"functionName":"get$runtimeType","ranges":[{"startOffset":402975,"endOffset":403030,"count":0}],"isBlockCoverage":false},{"functionName":"get$runtimeType","ranges":[{"startOffset":403114,"endOffset":403169,"count":0}],"isBlockCoverage":false},{"functionName":"get$runtimeType","ranges":[{"startOffset":403238,"endOffset":403296,"count":0}],"isBlockCoverage":false},{"functionName":"codeUnitAt$1","ranges":[{"startOffset":403347,"endOffset":403614,"count":1},{"startOffset":403404,"endOffset":403465,"count":0},{"startOffset":403510,"endOffset":403567,"count":0}],"isBlockCoverage":true},{"functionName":"_codeUnitAt$1","ranges":[{"startOffset":403635,"endOffset":403815,"count":1},{"startOffset":403707,"endOffset":403768,"count":0}],"isBlockCoverage":true},{"functionName":"allMatches$2","ranges":[{"startOffset":403835,"endOffset":404180,"count":0}],"isBlockCoverage":false},{"functionName":"allMatches$1","ranges":[{"startOffset":404200,"endOffset":404289,"count":0}],"isBlockCoverage":false},{"functionName":"matchAsPrefix$2","ranges":[{"startOffset":404312,"endOffset":404833,"count":0}],"isBlockCoverage":false},{"functionName":"$add","ranges":[{"startOffset":404845,"endOffset":405018,"count":0}],"isBlockCoverage":false},{"functionName":"endsWith$1","ranges":[{"startOffset":405036,"endOffset":405256,"count":0}],"isBlockCoverage":false},{"functionName":"splitMapJoin$2$onMatch","ranges":[{"startOffset":405286,"endOffset":405477,"count":0}],"isBlockCoverage":false},{"functionName":"replaceFirst$2","ranges":[{"startOffset":405499,"endOffset":405680,"count":0}],"isBlockCoverage":false},{"functionName":"replaceRange$3","ranges":[{"startOffset":405702,"endOffset":405903,"count":0}],"isBlockCoverage":false},{"functionName":"startsWith$2","ranges":[{"startOffset":405923,"endOffset":406447,"count":1},{"startOffset":406073,"endOffset":406154,"count":0},{"startOffset":406288,"endOffset":406301,"count":0},{"startOffset":406373,"endOffset":406446,"count":0}],"isBlockCoverage":true},{"functionName":"startsWith$1","ranges":[{"startOffset":406467,"endOffset":406558,"count":0}],"isBlockCoverage":false},{"functionName":"substring$2","ranges":[{"startOffset":406577,"endOffset":407046,"count":1},{"startOffset":406656,"endOffset":406683,"count":0},{"startOffset":406718,"endOffset":406778,"count":0},{"startOffset":406820,"endOffset":406880,"count":0},{"startOffset":406927,"endOffset":406985,"count":0}],"isBlockCoverage":true},{"functionName":"substring$1","ranges":[{"startOffset":407065,"endOffset":407164,"count":0}],"isBlockCoverage":false},{"functionName":"trim$0","ranges":[{"startOffset":407178,"endOffset":407844,"count":0}],"isBlockCoverage":false},{"functionName":"$mul","ranges":[{"startOffset":407856,"endOffset":408335,"count":0}],"isBlockCoverage":false},{"functionName":"padLeft$2","ranges":[{"startOffset":408352,"endOffset":408535,"count":0}],"isBlockCoverage":false},{"functionName":"padRight$1","ranges":[{"startOffset":408553,"endOffset":408802,"count":0}],"isBlockCoverage":false},{"functionName":"indexOf$2","ranges":[{"startOffset":408819,"endOffset":409075,"count":0}],"isBlockCoverage":false},{"functionName":"indexOf$1","ranges":[{"startOffset":409092,"endOffset":409180,"count":0}],"isBlockCoverage":false},{"functionName":"lastIndexOf$2","ranges":[{"startOffset":409201,"endOffset":409620,"count":0}],"isBlockCoverage":false},{"functionName":"lastIndexOf$1","ranges":[{"startOffset":409641,"endOffset":409736,"count":0}],"isBlockCoverage":false},{"functionName":"contains$1","ranges":[{"startOffset":409754,"endOffset":409928,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":409946,"endOffset":409995,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":410015,"endOffset":410421,"count":1}],"isBlockCoverage":true},{"functionName":"get$runtimeType","ranges":[{"startOffset":410444,"endOffset":410502,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":410520,"endOffset":410576,"count":1}],"isBlockCoverage":true},{"functionName":"$index","ranges":[{"startOffset":410590,"endOffset":410806,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":410903,"endOffset":411111,"count":1}],"isBlockCoverage":true},{"functionName":"get$length","ranges":[{"startOffset":411129,"endOffset":411209,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":411228,"endOffset":411309,"count":0}],"isBlockCoverage":false},{"functionName":"get$first","ranges":[{"startOffset":411326,"endOffset":411441,"count":0}],"isBlockCoverage":false},{"functionName":"get$last","ranges":[{"startOffset":411457,"endOffset":411571,"count":0}],"isBlockCoverage":false},{"functionName":"contains$1","ranges":[{"startOffset":411589,"endOffset":411663,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":411681,"endOffset":411741,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":411794,"endOffset":411852,"count":1}],"isBlockCoverage":true},{"functionName":"get$current","ranges":[{"startOffset":411871,"endOffset":411953,"count":1}],"isBlockCoverage":true},{"functionName":"cast$2$0","ranges":[{"startOffset":412130,"endOffset":412317,"count":0}],"isBlockCoverage":false},{"functionName":"containsKey$1","ranges":[{"startOffset":412338,"endOffset":412405,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":412419,"endOffset":412508,"count":1}],"isBlockCoverage":true},{"functionName":"remove$1","ranges":[{"startOffset":412524,"endOffset":412615,"count":0}],"isBlockCoverage":false},{"functionName":"forEach$1","ranges":[{"startOffset":412632,"endOffset":412762,"count":0}],"isBlockCoverage":false},{"functionName":"get$keys","ranges":[{"startOffset":412778,"endOffset":412919,"count":1}],"isBlockCoverage":true},{"functionName":"get$length","ranges":[{"startOffset":412937,"endOffset":413017,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":413036,"endOffset":413117,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":413177,"endOffset":413372,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":413390,"endOffset":413458,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":413508,"endOffset":413561,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":413575,"endOffset":413681,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":413780,"endOffset":413952,"count":1}],"isBlockCoverage":true},{"functionName":"get$isEmpty","ranges":[{"startOffset":413971,"endOffset":414032,"count":0}],"isBlockCoverage":false},{"functionName":"get$first","ranges":[{"startOffset":414049,"endOffset":414211,"count":0}],"isBlockCoverage":false},{"functionName":"get$last","ranges":[{"startOffset":414227,"endOffset":414442,"count":0}],"isBlockCoverage":false},{"functionName":"contains$1","ranges":[{"startOffset":414460,"endOffset":414822,"count":0}],"isBlockCoverage":false},{"functionName":"join$1","ranges":[{"startOffset":414836,"endOffset":415796,"count":0}],"isBlockCoverage":false},{"functionName":"join$0","ranges":[{"startOffset":415810,"endOffset":415878,"count":0}],"isBlockCoverage":false},{"functionName":"map$1$1","ranges":[{"startOffset":415893,"endOffset":416137,"count":0}],"isBlockCoverage":false},{"functionName":"fold$1$2","ranges":[{"startOffset":416153,"endOffset":416676,"count":0}],"isBlockCoverage":false},{"functionName":"toList$1$growable","ranges":[{"startOffset":416701,"endOffset":417074,"count":1}],"isBlockCoverage":true},{"functionName":"toList$0","ranges":[{"startOffset":417090,"endOffset":417171,"count":1}],"isBlockCoverage":true},{"functionName":"toSet$0","ranges":[{"startOffset":417186,"endOffset":417453,"count":0}],"isBlockCoverage":false},{"functionName":"get$_endIndex","ranges":[{"startOffset":417512,"endOffset":417706,"count":0}],"isBlockCoverage":false},{"functionName":"get$_startIndex","ranges":[{"startOffset":417729,"endOffset":417914,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":417932,"endOffset":418288,"count":0}],"isBlockCoverage":false},{"functionName":"elementAt$1","ranges":[{"startOffset":418307,"endOffset":418765,"count":0}],"isBlockCoverage":false},{"functionName":"take$1","ranges":[{"startOffset":418779,"endOffset":419284,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":419338,"endOffset":419395,"count":1}],"isBlockCoverage":true},{"functionName":"moveNext$0","ranges":[{"startOffset":419413,"endOffset":419942,"count":1},{"startOffset":419627,"endOffset":419685,"count":0}],"isBlockCoverage":true},{"functionName":"set$__internal$_current","ranges":[{"startOffset":419973,"endOffset":420073,"count":1}],"isBlockCoverage":true},{"functionName":"get$iterator","ranges":[{"startOffset":420150,"endOffset":420369,"count":1}],"isBlockCoverage":true},{"functionName":"get$length","ranges":[{"startOffset":420387,"endOffset":420464,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":420483,"endOffset":420561,"count":0}],"isBlockCoverage":false},{"functionName":"get$first","ranges":[{"startOffset":420578,"endOffset":420669,"count":0}],"isBlockCoverage":false},{"functionName":"get$last","ranges":[{"startOffset":420685,"endOffset":420775,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":420909,"endOffset":421176,"count":1},{"startOffset":421003,"endOffset":421107,"count":0}],"isBlockCoverage":true},{"functionName":"get$current","ranges":[{"startOffset":421195,"endOffset":421252,"count":0}],"isBlockCoverage":false},{"functionName":"set$__internal$_current","ranges":[{"startOffset":421283,"endOffset":421378,"count":1}],"isBlockCoverage":true},{"functionName":"get$length","ranges":[{"startOffset":421437,"endOffset":421501,"count":1}],"isBlockCoverage":true},{"functionName":"elementAt$1","ranges":[{"startOffset":421520,"endOffset":421614,"count":1}],"isBlockCoverage":true},{"functionName":"get$iterator","ranges":[{"startOffset":421670,"endOffset":421816,"count":1}],"isBlockCoverage":true},{"functionName":"map$1$1","ranges":[{"startOffset":421831,"endOffset":422028,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":422082,"endOffset":422289,"count":1}],"isBlockCoverage":true},{"functionName":"get$current","ranges":[{"startOffset":422308,"endOffset":422369,"count":1}],"isBlockCoverage":true},{"functionName":"get$iterator","ranges":[{"startOffset":422426,"endOffset":422651,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":422707,"endOffset":422764,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":422782,"endOffset":423337,"count":0}],"isBlockCoverage":false},{"functionName":"set$_currentExpansion","ranges":[{"startOffset":423366,"endOffset":423491,"count":0}],"isBlockCoverage":false},{"functionName":"set$__internal$_current","ranges":[{"startOffset":423522,"endOffset":423617,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":423697,"endOffset":423851,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":423909,"endOffset":424236,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":424255,"endOffset":424316,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":424370,"endOffset":424408,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":424427,"endOffset":424464,"count":0}],"isBlockCoverage":false},{"functionName":"set$length","ranges":[{"startOffset":424545,"endOffset":424683,"count":0}],"isBlockCoverage":false},{"functionName":"$indexSet","ranges":[{"startOffset":424744,"endOffset":424977,"count":0}],"isBlockCoverage":false},{"functionName":"set$length","ranges":[{"startOffset":424995,"endOffset":425127,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":425229,"endOffset":425293,"count":1}],"isBlockCoverage":true},{"functionName":"elementAt$1","ranges":[{"startOffset":425312,"endOffset":425470,"count":1}],"isBlockCoverage":true},{"functionName":"get$hashCode","ranges":[{"startOffset":425519,"endOffset":425738,"count":1}],"isBlockCoverage":true},{"functionName":"toString$0","ranges":[{"startOffset":425756,"endOffset":425836,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":425847,"endOffset":426011,"count":1},{"startOffset":425901,"endOffset":425914,"count":0}],"isBlockCoverage":true},{"functionName":"cast$2$0","ranges":[{"startOffset":426061,"endOffset":426200,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":426219,"endOffset":426280,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":426298,"endOffset":426359,"count":0}],"isBlockCoverage":false},{"functionName":"remove$1","ranges":[{"startOffset":426375,"endOffset":426448,"count":0}],"isBlockCoverage":false},{"functionName":"map$2$1","ranges":[{"startOffset":426463,"endOffset":426752,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":426827,"endOffset":427051,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":427069,"endOffset":427150,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":427208,"endOffset":427266,"count":0}],"isBlockCoverage":false},{"functionName":"containsKey$1","ranges":[{"startOffset":427287,"endOffset":427466,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":427480,"endOffset":427594,"count":0}],"isBlockCoverage":false},{"functionName":"_fetch$1","ranges":[{"startOffset":427610,"endOffset":427689,"count":0}],"isBlockCoverage":false},{"functionName":"forEach$1","ranges":[{"startOffset":427706,"endOffset":428021,"count":1},{"startOffset":427929,"endOffset":428015,"count":0}],"isBlockCoverage":true},{"functionName":"get$keys","ranges":[{"startOffset":428037,"endOffset":428166,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":428232,"endOffset":428410,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":428428,"endOffset":428508,"count":0}],"isBlockCoverage":false},{"functionName":"Instantiation$1","ranges":[{"startOffset":428567,"endOffset":428666,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":428684,"endOffset":428871,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":428922,"endOffset":429017,"count":0}],"isBlockCoverage":false},{"functionName":"call$4","ranges":[{"startOffset":429031,"endOffset":429142,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":429160,"endOffset":429281,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":429347,"endOffset":429437,"count":0}],"isBlockCoverage":false},{"functionName":"matchTypeError$1","ranges":[{"startOffset":429520,"endOffset":430192,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":430242,"endOffset":430457,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":430546,"endOffset":430987,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":431075,"endOffset":431193,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":431303,"endOffset":431464,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":431536,"endOffset":431793,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":431863,"endOffset":432075,"count":0}],"isBlockCoverage":false},{"functionName":"get$$call","ranges":[{"startOffset":432112,"endOffset":432149,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":432313,"endOffset":432502,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":432548,"endOffset":432877,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":432897,"endOffset":433264,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":433282,"endOffset":433522,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":433586,"endOffset":433632,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":433651,"endOffset":433704,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":433757,"endOffset":433827,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":433846,"endOffset":433899,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":433955,"endOffset":434046,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":434102,"endOffset":434160,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":434179,"endOffset":434243,"count":1}],"isBlockCoverage":true},{"functionName":"get$keys","ranges":[{"startOffset":434259,"endOffset":434390,"count":1}],"isBlockCoverage":true},{"functionName":"get$values","ranges":[{"startOffset":434408,"endOffset":434602,"count":0}],"isBlockCoverage":false},{"functionName":"containsKey$1","ranges":[{"startOffset":434623,"endOffset":435155,"count":1},{"startOffset":435019,"endOffset":435032,"count":0},{"startOffset":435095,"endOffset":435149,"count":0}],"isBlockCoverage":true},{"functionName":"internalContainsKey$1","ranges":[{"startOffset":435184,"endOffset":435440,"count":0}],"isBlockCoverage":false},{"functionName":"addAll$1","ranges":[{"startOffset":435456,"endOffset":435602,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":435616,"endOffset":436311,"count":1},{"startOffset":435819,"endOffset":435832,"count":0},{"startOffset":435911,"endOffset":435918,"count":0},{"startOffset":436111,"endOffset":436124,"count":0},{"startOffset":436200,"endOffset":436207,"count":0},{"startOffset":436259,"endOffset":436305,"count":0}],"isBlockCoverage":true},{"functionName":"internalGet$1","ranges":[{"startOffset":436332,"endOffset":436708,"count":0}],"isBlockCoverage":false},{"functionName":"$indexSet","ranges":[{"startOffset":436725,"endOffset":437424,"count":1}],"isBlockCoverage":true},{"functionName":"internalSet$2","ranges":[{"startOffset":437445,"endOffset":438198,"count":1},{"startOffset":437963,"endOffset":438192,"count":0}],"isBlockCoverage":true},{"functionName":"putIfAbsent$2","ranges":[{"startOffset":438219,"endOffset":438560,"count":1},{"startOffset":438463,"endOffset":438559,"count":0}],"isBlockCoverage":true},{"functionName":"remove$1","ranges":[{"startOffset":438576,"endOffset":438960,"count":1},{"startOffset":438743,"endOffset":438954,"count":0}],"isBlockCoverage":true},{"functionName":"internalRemove$1","ranges":[{"startOffset":438984,"endOffset":439546,"count":0}],"isBlockCoverage":false},{"functionName":"clear$0","ranges":[{"startOffset":439561,"endOffset":439847,"count":0}],"isBlockCoverage":false},{"functionName":"forEach$1","ranges":[{"startOffset":439864,"endOffset":440326,"count":1},{"startOffset":440224,"endOffset":440285,"count":0}],"isBlockCoverage":true},{"functionName":"__js_helper$_addHashTableEntry$3","ranges":[{"startOffset":440366,"endOffset":440739,"count":1},{"startOffset":440683,"endOffset":440733,"count":0}],"isBlockCoverage":true},{"functionName":"__js_helper$_removeHashTableEntry$2","ranges":[{"startOffset":440782,"endOffset":441088,"count":1},{"startOffset":440854,"endOffset":440866,"count":0},{"startOffset":440946,"endOffset":440958,"count":0}],"isBlockCoverage":true},{"functionName":"_modified$0","ranges":[{"startOffset":441107,"endOffset":441189,"count":1}],"isBlockCoverage":true},{"functionName":"_newLinkedCell$2","ranges":[{"startOffset":441213,"endOffset":441682,"count":1}],"isBlockCoverage":true},{"functionName":"__js_helper$_unlinkCell$1","ranges":[{"startOffset":441715,"endOffset":442185,"count":1},{"startOffset":441930,"endOffset":441966,"count":0},{"startOffset":442077,"endOffset":442117,"count":0}],"isBlockCoverage":true},{"functionName":"internalComputeHashCode$1","ranges":[{"startOffset":442218,"endOffset":442286,"count":1}],"isBlockCoverage":true},{"functionName":"internalFindBucketIndex$2","ranges":[{"startOffset":442319,"endOffset":442570,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":442588,"endOffset":442649,"count":0}],"isBlockCoverage":false},{"functionName":"_getTableCell$2","ranges":[{"startOffset":442672,"endOffset":442725,"count":1}],"isBlockCoverage":true},{"functionName":"_getTableBucket$2","ranges":[{"startOffset":442750,"endOffset":442803,"count":1}],"isBlockCoverage":true},{"functionName":"_setTableEntry$3","ranges":[{"startOffset":442827,"endOffset":442925,"count":1}],"isBlockCoverage":true},{"functionName":"_deleteTableEntry$2","ranges":[{"startOffset":442952,"endOffset":443005,"count":1}],"isBlockCoverage":true},{"functionName":"_containsTableEntry$2","ranges":[{"startOffset":443034,"endOffset":443117,"count":1}],"isBlockCoverage":true},{"functionName":"_newHashTable$0","ranges":[{"startOffset":443140,"endOffset":443353,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":443445,"endOffset":443569,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":443587,"endOffset":443663,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":443730,"endOffset":443899,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":443917,"endOffset":443998,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":444101,"endOffset":444176,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":444195,"endOffset":444276,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":444296,"endOffset":444515,"count":1}],"isBlockCoverage":true},{"functionName":"contains$1","ranges":[{"startOffset":444533,"endOffset":444620,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":444686,"endOffset":444744,"count":1}],"isBlockCoverage":true},{"functionName":"moveNext$0","ranges":[{"startOffset":444762,"endOffset":445261,"count":1},{"startOffset":444898,"endOffset":444956,"count":0}],"isBlockCoverage":true},{"functionName":"set$__js_helper$_current","ranges":[{"startOffset":445293,"endOffset":445394,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":445468,"endOffset":445516,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":445591,"endOffset":445656,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":445732,"endOffset":445817,"count":1}],"isBlockCoverage":true},{"functionName":"toString$0","ranges":[{"startOffset":445892,"endOffset":445983,"count":0}],"isBlockCoverage":false},{"functionName":"get$_nativeGlobalVersion","ranges":[{"startOffset":446015,"endOffset":446314,"count":0}],"isBlockCoverage":false},{"functionName":"get$_nativeAnchoredVersion","ranges":[{"startOffset":446348,"endOffset":446659,"count":0}],"isBlockCoverage":false},{"functionName":"firstMatch$1","ranges":[{"startOffset":446679,"endOffset":446942,"count":0}],"isBlockCoverage":false},{"functionName":"allMatches$2","ranges":[{"startOffset":446962,"endOffset":447186,"count":0}],"isBlockCoverage":false},{"functionName":"allMatches$1","ranges":[{"startOffset":447206,"endOffset":447295,"count":0}],"isBlockCoverage":false},{"functionName":"_execGlobal$2","ranges":[{"startOffset":447316,"endOffset":447578,"count":0}],"isBlockCoverage":false},{"functionName":"_execAnchored$2","ranges":[{"startOffset":447601,"endOffset":447981,"count":0}],"isBlockCoverage":false},{"functionName":"matchAsPrefix$2","ranges":[{"startOffset":448004,"endOffset":448222,"count":0}],"isBlockCoverage":false},{"functionName":"get$start","ranges":[{"startOffset":448319,"endOffset":448369,"count":0}],"isBlockCoverage":false},{"functionName":"get$end","ranges":[{"startOffset":448384,"endOffset":448468,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":448482,"endOffset":448669,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":448771,"endOffset":448879,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":448940,"endOffset":448998,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":449016,"endOffset":450272,"count":0}],"isBlockCoverage":false},{"functionName":"get$end","ranges":[{"startOffset":450341,"endOffset":450406,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":450420,"endOffset":450574,"count":0}],"isBlockCoverage":false},{"functionName":"get$start","ranges":[{"startOffset":450608,"endOffset":450651,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":450719,"endOffset":450837,"count":0}],"isBlockCoverage":false},{"functionName":"get$first","ranges":[{"startOffset":450854,"endOffset":451101,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":451167,"endOffset":451827,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":451846,"endOffset":451904,"count":0}],"isBlockCoverage":false},{"functionName":"get$runtimeType","ranges":[{"startOffset":451986,"endOffset":452048,"count":0}],"isBlockCoverage":false},{"functionName":"get$runtimeType","ranges":[{"startOffset":452215,"endOffset":452275,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":452332,"endOffset":452388,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":452487,"endOffset":452644,"count":0}],"isBlockCoverage":false},{"functionName":"$indexSet","ranges":[{"startOffset":452661,"endOffset":452863,"count":0}],"isBlockCoverage":false},{"functionName":"$indexSet","ranges":[{"startOffset":452995,"endOffset":453194,"count":1}],"isBlockCoverage":true},{"functionName":"get$runtimeType","ranges":[{"startOffset":453328,"endOffset":453391,"count":0}],"isBlockCoverage":false},{"functionName":"get$runtimeType","ranges":[{"startOffset":453454,"endOffset":453517,"count":0}],"isBlockCoverage":false},{"functionName":"get$runtimeType","ranges":[{"startOffset":453578,"endOffset":453639,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":453653,"endOffset":453810,"count":0}],"isBlockCoverage":false},{"functionName":"get$runtimeType","ranges":[{"startOffset":453871,"endOffset":453932,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":453946,"endOffset":454103,"count":0}],"isBlockCoverage":false},{"functionName":"get$runtimeType","ranges":[{"startOffset":454163,"endOffset":454223,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":454237,"endOffset":454394,"count":0}],"isBlockCoverage":false},{"functionName":"get$runtimeType","ranges":[{"startOffset":454456,"endOffset":454518,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":454532,"endOffset":454689,"count":0}],"isBlockCoverage":false},{"functionName":"get$runtimeType","ranges":[{"startOffset":454751,"endOffset":454813,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":454827,"endOffset":454984,"count":0}],"isBlockCoverage":false},{"functionName":"sublist$2","ranges":[{"startOffset":455001,"endOffset":455144,"count":0}],"isBlockCoverage":false},{"functionName":"get$runtimeType","ranges":[{"startOffset":455234,"endOffset":455302,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":455320,"endOffset":455376,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":455390,"endOffset":455547,"count":0}],"isBlockCoverage":false},{"functionName":"get$runtimeType","ranges":[{"startOffset":455608,"endOffset":455669,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":455687,"endOffset":455743,"count":1}],"isBlockCoverage":true},{"functionName":"$index","ranges":[{"startOffset":455757,"endOffset":455914,"count":0}],"isBlockCoverage":false},{"functionName":"sublist$2","ranges":[{"startOffset":455931,"endOffset":456073,"count":0}],"isBlockCoverage":false},{"functionName":"_eval$1","ranges":[{"startOffset":456490,"endOffset":456591,"count":1}],"isBlockCoverage":true},{"functionName":"_bind$1","ranges":[{"startOffset":456606,"endOffset":456704,"count":1}],"isBlockCoverage":true},{"functionName":"get$hashCode","ranges":[{"startOffset":456792,"endOffset":457109,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":457120,"endOffset":457259,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":457277,"endOffset":457342,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":457405,"endOffset":457452,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":457535,"endOffset":457582,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":457674,"endOffset":457802,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":457904,"endOffset":458207,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":458319,"endOffset":458367,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":458484,"endOffset":458532,"count":0}],"isBlockCoverage":false},{"functionName":"_TimerImpl$2","ranges":[{"startOffset":458604,"endOffset":458905,"count":1},{"startOffset":458807,"endOffset":458899,"count":0}],"isBlockCoverage":true},{"functionName":"_TimerImpl$periodic$2","ranges":[{"startOffset":458934,"endOffset":459252,"count":0}],"isBlockCoverage":false},{"functionName":"cancel$0","ranges":[{"startOffset":459268,"endOffset":459616,"count":1},{"startOffset":459383,"endOffset":459390,"count":0},{"startOffset":459447,"endOffset":459494,"count":0},{"startOffset":459531,"endOffset":459610,"count":0}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":459697,"endOffset":459817,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":459900,"endOffset":460263,"count":0}],"isBlockCoverage":false},{"functionName":"complete$1","ranges":[{"startOffset":460343,"endOffset":460659,"count":1}],"isBlockCoverage":true},{"functionName":"completeError$2","ranges":[{"startOffset":460682,"endOffset":460845,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":460925,"endOffset":460999,"count":1}],"isBlockCoverage":true},{"functionName":"call$2","ranges":[{"startOffset":461079,"endOffset":461223,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":461310,"endOffset":461408,"count":1}],"isBlockCoverage":true},{"functionName":"get$isBroadcast","ranges":[{"startOffset":461490,"endOffset":461527,"count":0}],"isBlockCoverage":false},{"functionName":"_onPause$0","ranges":[{"startOffset":461590,"endOffset":461608,"count":0}],"isBlockCoverage":false},{"functionName":"_onResume$0","ranges":[{"startOffset":461627,"endOffset":461645,"count":0}],"isBlockCoverage":false},{"functionName":"set$_async$_next","ranges":[{"startOffset":461669,"endOffset":461742,"count":1}],"isBlockCoverage":true},{"functionName":"set$_async$_previous","ranges":[{"startOffset":461770,"endOffset":461855,"count":1}],"isBlockCoverage":true},{"functionName":"get$_mayAddEvent","ranges":[{"startOffset":461928,"endOffset":461976,"count":1}],"isBlockCoverage":true},{"functionName":"_ensureDoneFuture$0","ranges":[{"startOffset":462003,"endOffset":462182,"count":0}],"isBlockCoverage":false},{"functionName":"_removeListener$1","ranges":[{"startOffset":462207,"endOffset":462934,"count":0}],"isBlockCoverage":false},{"functionName":"_subscribe$4","ranges":[{"startOffset":462954,"endOffset":464472,"count":1},{"startOffset":463220,"endOffset":463469,"count":0},{"startOffset":463523,"endOffset":463526,"count":0},{"startOffset":464278,"endOffset":464337,"count":0}],"isBlockCoverage":true},{"functionName":"_recordCancel$1","ranges":[{"startOffset":464495,"endOffset":465046,"count":0}],"isBlockCoverage":false},{"functionName":"_recordPause$1","ranges":[{"startOffset":465068,"endOffset":465181,"count":0}],"isBlockCoverage":false},{"functionName":"_recordResume$1","ranges":[{"startOffset":465204,"endOffset":465317,"count":0}],"isBlockCoverage":false},{"functionName":"_addEventError$0","ranges":[{"startOffset":465341,"endOffset":465610,"count":0}],"isBlockCoverage":false},{"functionName":"add$1","ranges":[{"startOffset":465623,"endOffset":465854,"count":1},{"startOffset":465769,"endOffset":465817,"count":0}],"isBlockCoverage":true},{"functionName":"addError$2","ranges":[{"startOffset":465872,"endOffset":466438,"count":0}],"isBlockCoverage":false},{"functionName":"addError$1","ranges":[{"startOffset":466456,"endOffset":466522,"count":0}],"isBlockCoverage":false},{"functionName":"close$0","ranges":[{"startOffset":466537,"endOffset":466942,"count":0}],"isBlockCoverage":false},{"functionName":"_async$_addError$2","ranges":[{"startOffset":466968,"endOffset":467072,"count":0}],"isBlockCoverage":false},{"functionName":"_close$0","ranges":[{"startOffset":467088,"endOffset":467356,"count":0}],"isBlockCoverage":false},{"functionName":"_forEachListener$1","ranges":[{"startOffset":467382,"endOffset":468483,"count":0}],"isBlockCoverage":false},{"functionName":"_callOnCancel$0","ranges":[{"startOffset":468506,"endOffset":468761,"count":0}],"isBlockCoverage":false},{"functionName":"set$_firstSubscription","ranges":[{"startOffset":468791,"endOffset":468946,"count":1}],"isBlockCoverage":true},{"functionName":"set$_lastSubscription","ranges":[{"startOffset":468975,"endOffset":469127,"count":1}],"isBlockCoverage":true},{"functionName":"set$_addStreamState","ranges":[{"startOffset":469154,"endOffset":469293,"count":0}],"isBlockCoverage":false},{"functionName":"get$_mayAddEvent","ranges":[{"startOffset":469547,"endOffset":469673,"count":1}],"isBlockCoverage":true},{"functionName":"_addEventError$0","ranges":[{"startOffset":469697,"endOffset":469916,"count":0}],"isBlockCoverage":false},{"functionName":"_sendData$1","ranges":[{"startOffset":469935,"endOffset":470463,"count":1},{"startOffset":470076,"endOffset":470083,"count":0},{"startOffset":470308,"endOffset":470332,"count":0},{"startOffset":470356,"endOffset":470462,"count":0}],"isBlockCoverage":true},{"functionName":"_sendError$2","ranges":[{"startOffset":470483,"endOffset":470690,"count":0}],"isBlockCoverage":false},{"functionName":"_sendDone$0","ranges":[{"startOffset":470709,"endOffset":471070,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":471155,"endOffset":471289,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":471307,"endOffset":471403,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":471489,"endOffset":471653,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":471671,"endOffset":471767,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":471852,"endOffset":471979,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":471997,"endOffset":472093,"count":0}],"isBlockCoverage":false},{"functionName":"_sendData$1","ranges":[{"startOffset":472166,"endOffset":472489,"count":0}],"isBlockCoverage":false},{"functionName":"_sendError$2","ranges":[{"startOffset":472509,"endOffset":472759,"count":0}],"isBlockCoverage":false},{"functionName":"_sendDone$0","ranges":[{"startOffset":472778,"endOffset":473214,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":473299,"endOffset":473599,"count":1},{"startOffset":473419,"endOffset":473593,"count":0}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":473686,"endOffset":473986,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":474065,"endOffset":474620,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":474695,"endOffset":475141,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":475159,"endOffset":475217,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":475276,"endOffset":475578,"count":1},{"startOffset":475384,"endOffset":475577,"count":0}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":475657,"endOffset":476933,"count":1},{"startOffset":475992,"endOffset":476655,"count":0},{"startOffset":476684,"endOffset":476827,"count":0}],"isBlockCoverage":true},{"functionName":"toString$0","ranges":[{"startOffset":477010,"endOffset":477201,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":477241,"endOffset":477294,"count":0}],"isBlockCoverage":false},{"functionName":"completeError$2","ranges":[{"startOffset":477380,"endOffset":477925,"count":0}],"isBlockCoverage":false},{"functionName":"completeError$1","ranges":[{"startOffset":477948,"endOffset":478019,"count":0}],"isBlockCoverage":false},{"functionName":"complete$1","ranges":[{"startOffset":478096,"endOffset":478336,"count":1},{"startOffset":478231,"endOffset":478296,"count":0}],"isBlockCoverage":true},{"functionName":"complete$0","ranges":[{"startOffset":478354,"endOffset":478408,"count":1}],"isBlockCoverage":true},{"functionName":"_completeError$2","ranges":[{"startOffset":478432,"endOffset":478527,"count":0}],"isBlockCoverage":false},{"functionName":"complete$1","ranges":[{"startOffset":478582,"endOffset":478817,"count":0}],"isBlockCoverage":false},{"functionName":"complete$0","ranges":[{"startOffset":478835,"endOffset":478889,"count":0}],"isBlockCoverage":false},{"functionName":"_completeError$2","ranges":[{"startOffset":478913,"endOffset":479003,"count":0}],"isBlockCoverage":false},{"functionName":"matchesErrorTest$1","ranges":[{"startOffset":479067,"endOffset":479290,"count":0}],"isBlockCoverage":false},{"functionName":"handleError$1","ranges":[{"startOffset":479311,"endOffset":480110,"count":0}],"isBlockCoverage":false},{"functionName":"then$1$2$onError","ranges":[{"startOffset":480164,"endOffset":480845,"count":1},{"startOffset":480507,"endOffset":480563,"count":0},{"startOffset":480676,"endOffset":480679,"count":0}],"isBlockCoverage":true},{"functionName":"then$1$1","ranges":[{"startOffset":480861,"endOffset":480933,"count":1}],"isBlockCoverage":true},{"functionName":"_thenAwait$1$2","ranges":[{"startOffset":480955,"endOffset":481337,"count":1}],"isBlockCoverage":true},{"functionName":"catchError$1","ranges":[{"startOffset":481357,"endOffset":481806,"count":0}],"isBlockCoverage":false},{"functionName":"whenComplete$1","ranges":[{"startOffset":481828,"endOffset":482281,"count":1}],"isBlockCoverage":true},{"functionName":"_cloneResult$1","ranges":[{"startOffset":482303,"endOffset":482502,"count":0}],"isBlockCoverage":false},{"functionName":"_addListener$1","ranges":[{"startOffset":482524,"endOffset":483257,"count":1},{"startOffset":482868,"endOffset":483106,"count":0}],"isBlockCoverage":true},{"functionName":"_prependListeners$1","ranges":[{"startOffset":483284,"endOffset":484374,"count":1},{"startOffset":483471,"endOffset":484368,"count":0}],"isBlockCoverage":true},{"functionName":"_removeListeners$0","ranges":[{"startOffset":484400,"endOffset":484667,"count":1}],"isBlockCoverage":true},{"functionName":"_reverseListeners$1","ranges":[{"startOffset":484694,"endOffset":484951,"count":1}],"isBlockCoverage":true},{"functionName":"_complete$1","ranges":[{"startOffset":484970,"endOffset":485601,"count":1},{"startOffset":485249,"endOffset":485317,"count":0}],"isBlockCoverage":true},{"functionName":"_completeWithValue$1","ranges":[{"startOffset":485629,"endOffset":486055,"count":1}],"isBlockCoverage":true},{"functionName":"_completeError$2","ranges":[{"startOffset":486079,"endOffset":486469,"count":0}],"isBlockCoverage":false},{"functionName":"_completeError$1","ranges":[{"startOffset":486493,"endOffset":486565,"count":0}],"isBlockCoverage":false},{"functionName":"_asyncComplete$1","ranges":[{"startOffset":486589,"endOffset":487004,"count":1},{"startOffset":486779,"endOffset":486841,"count":0}],"isBlockCoverage":true},{"functionName":"_chainFuture$1","ranges":[{"startOffset":487026,"endOffset":487512,"count":0}],"isBlockCoverage":false},{"functionName":"_asyncCompleteError$2","ranges":[{"startOffset":487541,"endOffset":487857,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":487940,"endOffset":488024,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":488113,"endOffset":488205,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":488296,"endOffset":488475,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":488567,"endOffset":488768,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":488782,"endOffset":488844,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":488937,"endOffset":489007,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":489093,"endOffset":489210,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":489294,"endOffset":489370,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":489461,"endOffset":489543,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":489655,"endOffset":491612,"count":1},{"startOffset":490115,"endOffset":490871,"count":0},{"startOffset":491050,"endOffset":491298,"count":0},{"startOffset":491326,"endOffset":491606,"count":0}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":491732,"endOffset":491785,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":491891,"endOffset":492537,"count":1},{"startOffset":492293,"endOffset":492531,"count":0}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":492634,"endOffset":493916,"count":0}],"isBlockCoverage":false},{"functionName":"get$isBroadcast","ranges":[{"startOffset":494027,"endOffset":494065,"count":1}],"isBlockCoverage":true},{"functionName":"pipe$1","ranges":[{"startOffset":494079,"endOffset":494313,"count":1}],"isBlockCoverage":true},{"functionName":"get$length","ranges":[{"startOffset":494331,"endOffset":494644,"count":0}],"isBlockCoverage":false},{"functionName":"get$first","ranges":[{"startOffset":494661,"endOffset":495037,"count":1}],"isBlockCoverage":true},{"functionName":"get$last","ranges":[{"startOffset":495053,"endOffset":495429,"count":0}],"isBlockCoverage":false},{"functionName":"firstWhere$1","ranges":[{"startOffset":495449,"endOffset":495994,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":496063,"endOffset":496187,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":496205,"endOffset":496263,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":496333,"endOffset":496503,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":496593,"endOffset":496811,"count":1}],"isBlockCoverage":true},{"functionName":"$signature","ranges":[{"startOffset":496829,"endOffset":496907,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":496963,"endOffset":497027,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":497105,"endOffset":497216,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":497234,"endOffset":497320,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":497379,"endOffset":497447,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":497523,"endOffset":497686,"count":1}],"isBlockCoverage":true},{"functionName":"$signature","ranges":[{"startOffset":497704,"endOffset":497790,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":497848,"endOffset":498176,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":498251,"endOffset":498435,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":498453,"endOffset":498539,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":498596,"endOffset":499042,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":499123,"endOffset":499482,"count":1}],"isBlockCoverage":true},{"functionName":"$signature","ranges":[{"startOffset":499500,"endOffset":499586,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":499649,"endOffset":499710,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":499794,"endOffset":499961,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":500044,"endOffset":500372,"count":0}],"isBlockCoverage":false},{"functionName":"get$_pendingEvents","ranges":[{"startOffset":500561,"endOffset":500951,"count":1},{"startOffset":500776,"endOffset":500950,"count":0}],"isBlockCoverage":true},{"functionName":"_ensurePendingEvents$0","ranges":[{"startOffset":500981,"endOffset":501700,"count":0}],"isBlockCoverage":false},{"functionName":"get$_async$_subscription","ranges":[{"startOffset":501732,"endOffset":502152,"count":1}],"isBlockCoverage":true},{"functionName":"_badEventState$0","ranges":[{"startOffset":502176,"endOffset":502426,"count":0}],"isBlockCoverage":false},{"functionName":"addStream$2$cancelOnError","ranges":[{"startOffset":502459,"endOffset":503511,"count":1},{"startOffset":502668,"endOffset":502716,"count":0},{"startOffset":502743,"endOffset":502874,"count":0},{"startOffset":503017,"endOffset":503060,"count":0},{"startOffset":503300,"endOffset":503316,"count":0},{"startOffset":503326,"endOffset":503339,"count":0}],"isBlockCoverage":true},{"functionName":"_ensureDoneFuture$0","ranges":[{"startOffset":503538,"endOffset":503771,"count":1},{"startOffset":503692,"endOffset":503747,"count":0}],"isBlockCoverage":true},{"functionName":"add$1","ranges":[{"startOffset":503784,"endOffset":504005,"count":1},{"startOffset":503924,"endOffset":503972,"count":0}],"isBlockCoverage":true},{"functionName":"addError$2","ranges":[{"startOffset":504023,"endOffset":504587,"count":0}],"isBlockCoverage":false},{"functionName":"addError$1","ranges":[{"startOffset":504605,"endOffset":504671,"count":0}],"isBlockCoverage":false},{"functionName":"close$0","ranges":[{"startOffset":504686,"endOffset":504977,"count":1},{"startOffset":504785,"endOffset":504820,"count":0},{"startOffset":504848,"endOffset":504896,"count":0}],"isBlockCoverage":true},{"functionName":"_closeUnchecked$0","ranges":[{"startOffset":505002,"endOffset":505204,"count":1},{"startOffset":505082,"endOffset":505101,"count":0},{"startOffset":505141,"endOffset":505198,"count":0}],"isBlockCoverage":true},{"functionName":"_add$1","ranges":[{"startOffset":505218,"endOffset":505567,"count":1},{"startOffset":505423,"endOffset":505561,"count":0}],"isBlockCoverage":true},{"functionName":"_async$_addError$2","ranges":[{"startOffset":505593,"endOffset":505900,"count":0}],"isBlockCoverage":false},{"functionName":"_close$0","ranges":[{"startOffset":505916,"endOffset":506256,"count":0}],"isBlockCoverage":false},{"functionName":"_subscribe$4","ranges":[{"startOffset":506276,"endOffset":507433,"count":1},{"startOffset":506562,"endOffset":506639,"count":0},{"startOffset":507026,"endOffset":507213,"count":0}],"isBlockCoverage":true},{"functionName":"_recordCancel$1","ranges":[{"startOffset":507456,"endOffset":508586,"count":1},{"startOffset":507936,"endOffset":508391,"count":0}],"isBlockCoverage":true},{"functionName":"_recordPause$1","ranges":[{"startOffset":508608,"endOffset":508942,"count":1},{"startOffset":508802,"endOffset":508900,"count":0}],"isBlockCoverage":true},{"functionName":"_recordResume$1","ranges":[{"startOffset":508965,"endOffset":509301,"count":1},{"startOffset":509159,"endOffset":509258,"count":0}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":509551,"endOffset":509611,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":509707,"endOffset":509840,"count":1},{"startOffset":509780,"endOffset":509798,"count":0},{"startOffset":509808,"endOffset":509834,"count":0}],"isBlockCoverage":true},{"functionName":"_sendData$1","ranges":[{"startOffset":509930,"endOffset":510047,"count":1}],"isBlockCoverage":true},{"functionName":"_sendError$2","ranges":[{"startOffset":510067,"endOffset":510179,"count":0}],"isBlockCoverage":false},{"functionName":"_sendDone$0","ranges":[{"startOffset":510198,"endOffset":510266,"count":0}],"isBlockCoverage":false},{"functionName":"_sendData$1","ranges":[{"startOffset":510338,"endOffset":510532,"count":0}],"isBlockCoverage":false},{"functionName":"_sendError$2","ranges":[{"startOffset":510552,"endOffset":510680,"count":0}],"isBlockCoverage":false},{"functionName":"_sendDone$0","ranges":[{"startOffset":510699,"endOffset":510788,"count":0}],"isBlockCoverage":false},{"functionName":"_createSubscription$4","ranges":[{"startOffset":510942,"endOffset":511156,"count":1}],"isBlockCoverage":true},{"functionName":"get$hashCode","ranges":[{"startOffset":511176,"endOffset":511275,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":511286,"endOffset":511499,"count":0}],"isBlockCoverage":false},{"functionName":"_onCancel$0","ranges":[{"startOffset":511564,"endOffset":511635,"count":1}],"isBlockCoverage":true},{"functionName":"_onPause$0","ranges":[{"startOffset":511653,"endOffset":511716,"count":1}],"isBlockCoverage":true},{"functionName":"_onResume$0","ranges":[{"startOffset":511735,"endOffset":511799,"count":1}],"isBlockCoverage":true},{"functionName":"add$1","ranges":[{"startOffset":511853,"endOffset":511951,"count":1}],"isBlockCoverage":true},{"functionName":"cancel$0","ranges":[{"startOffset":512090,"endOffset":512350,"count":1},{"startOffset":512181,"endOffset":512264,"count":0}],"isBlockCoverage":true},{"functionName":"call$2","ranges":[{"startOffset":512427,"endOffset":512562,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":512648,"endOffset":512723,"count":1}],"isBlockCoverage":true},{"functionName":"_BufferingStreamSubscription$4","ranges":[{"startOffset":512883,"endOffset":513035,"count":1}],"isBlockCoverage":true},{"functionName":"_setPendingEvents$1","ranges":[{"startOffset":513062,"endOffset":513518,"count":1}],"isBlockCoverage":true},{"functionName":"onData$1","ranges":[{"startOffset":513534,"endOffset":513897,"count":1}],"isBlockCoverage":true},{"functionName":"onError$1","ranges":[{"startOffset":513914,"endOffset":514590,"count":1},{"startOffset":514246,"endOffset":514584,"count":0}],"isBlockCoverage":true},{"functionName":"onDone$1","ranges":[{"startOffset":514606,"endOffset":514849,"count":1}],"isBlockCoverage":true},{"functionName":"pause$1","ranges":[{"startOffset":514864,"endOffset":515291,"count":1},{"startOffset":514982,"endOffset":514989,"count":0},{"startOffset":515094,"endOffset":515186,"count":0},{"startOffset":515240,"endOffset":515285,"count":0}],"isBlockCoverage":true},{"functionName":"pause$0","ranges":[{"startOffset":515306,"endOffset":515357,"count":1}],"isBlockCoverage":true},{"functionName":"resume$0","ranges":[{"startOffset":515373,"endOffset":516055,"count":1},{"startOffset":515471,"endOffset":515478,"count":0},{"startOffset":515591,"endOffset":515675,"count":0},{"startOffset":515735,"endOffset":515768,"count":0}],"isBlockCoverage":true},{"functionName":"cancel$0","ranges":[{"startOffset":516071,"endOffset":516331,"count":1}],"isBlockCoverage":true},{"functionName":"get$_mayResumeInput","ranges":[{"startOffset":516358,"endOffset":516536,"count":1},{"startOffset":516458,"endOffset":516479,"count":0},{"startOffset":516488,"endOffset":516513,"count":0}],"isBlockCoverage":true},{"functionName":"get$isPaused","ranges":[{"startOffset":516556,"endOffset":516607,"count":1}],"isBlockCoverage":true},{"functionName":"_cancel$0","ranges":[{"startOffset":516624,"endOffset":516954,"count":1}],"isBlockCoverage":true},{"functionName":"_add$1","ranges":[{"startOffset":516968,"endOffset":517413,"count":1},{"startOffset":517222,"endOffset":517229,"count":0},{"startOffset":517281,"endOffset":517407,"count":0}],"isBlockCoverage":true},{"functionName":"_async$_addError$2","ranges":[{"startOffset":517439,"endOffset":517688,"count":0}],"isBlockCoverage":false},{"functionName":"_close$0","ranges":[{"startOffset":517704,"endOffset":518023,"count":0}],"isBlockCoverage":false},{"functionName":"_onPause$0","ranges":[{"startOffset":518041,"endOffset":518106,"count":0}],"isBlockCoverage":false},{"functionName":"_onResume$0","ranges":[{"startOffset":518125,"endOffset":518190,"count":0}],"isBlockCoverage":false},{"functionName":"_onCancel$0","ranges":[{"startOffset":518209,"endOffset":518293,"count":1}],"isBlockCoverage":true},{"functionName":"_addPending$1","ranges":[{"startOffset":518314,"endOffset":518843,"count":0}],"isBlockCoverage":false},{"functionName":"_sendData$1","ranges":[{"startOffset":518862,"endOffset":519379,"count":1}],"isBlockCoverage":true},{"functionName":"_sendError$2","ranges":[{"startOffset":519399,"endOffset":520116,"count":0}],"isBlockCoverage":false},{"functionName":"_sendDone$0","ranges":[{"startOffset":520135,"endOffset":520625,"count":0}],"isBlockCoverage":false},{"functionName":"_guardCallback$1","ranges":[{"startOffset":520649,"endOffset":520983,"count":1}],"isBlockCoverage":true},{"functionName":"_checkState$1","ranges":[{"startOffset":521004,"endOffset":522070,"count":1},{"startOffset":521160,"endOffset":521231,"count":0},{"startOffset":521271,"endOffset":521474,"count":0},{"startOffset":521848,"endOffset":521892,"count":0},{"startOffset":522010,"endOffset":522021,"count":0},{"startOffset":522031,"endOffset":522064,"count":0}],"isBlockCoverage":true},{"functionName":"set$_onData","ranges":[{"startOffset":522089,"endOffset":522219,"count":1}],"isBlockCoverage":true},{"functionName":"set$_onDone","ranges":[{"startOffset":522238,"endOffset":522321,"count":1}],"isBlockCoverage":true},{"functionName":"set$_pending","ranges":[{"startOffset":522341,"endOffset":522487,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":522629,"endOffset":523285,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":523388,"endOffset":523626,"count":0}],"isBlockCoverage":false},{"functionName":"listen$4$cancelOnError$onDone$onError","ranges":[{"startOffset":523724,"endOffset":523966,"count":1}],"isBlockCoverage":true},{"functionName":"listen$2$onDone","ranges":[{"startOffset":523989,"endOffset":524106,"count":1}],"isBlockCoverage":true},{"functionName":"listen$3$onDone$onError","ranges":[{"startOffset":524137,"endOffset":524266,"count":1}],"isBlockCoverage":true},{"functionName":"listen$1","ranges":[{"startOffset":524282,"endOffset":524389,"count":1}],"isBlockCoverage":true},{"functionName":"_createSubscription$4","ranges":[{"startOffset":524418,"endOffset":524671,"count":0}],"isBlockCoverage":false},{"functionName":"_createSubscription$4","ranges":[{"startOffset":524743,"endOffset":525243,"count":1},{"startOffset":524958,"endOffset":525035,"count":0}],"isBlockCoverage":true},{"functionName":"get$isEmpty","ranges":[{"startOffset":525307,"endOffset":525370,"count":1}],"isBlockCoverage":true},{"functionName":"handleNext$1","ranges":[{"startOffset":525390,"endOffset":526251,"count":0}],"isBlockCoverage":false},{"functionName":"set$_async$_iterator","ranges":[{"startOffset":526279,"endOffset":526387,"count":0}],"isBlockCoverage":false},{"functionName":"set$next","ranges":[{"startOffset":526439,"endOffset":526521,"count":0}],"isBlockCoverage":false},{"functionName":"get$next","ranges":[{"startOffset":526537,"endOffset":526579,"count":0}],"isBlockCoverage":false},{"functionName":"perform$1","ranges":[{"startOffset":526631,"endOffset":526743,"count":0}],"isBlockCoverage":false},{"functionName":"perform$1","ranges":[{"startOffset":526796,"endOffset":526880,"count":0}],"isBlockCoverage":false},{"functionName":"perform$1","ranges":[{"startOffset":526932,"endOffset":526988,"count":0}],"isBlockCoverage":false},{"functionName":"get$next","ranges":[{"startOffset":527004,"endOffset":527041,"count":0}],"isBlockCoverage":false},{"functionName":"set$next","ranges":[{"startOffset":527057,"endOffset":527147,"count":0}],"isBlockCoverage":false},{"functionName":"schedule$1","ranges":[{"startOffset":527227,"endOffset":527689,"count":1},{"startOffset":527390,"endOffset":527397,"count":0},{"startOffset":527491,"endOffset":527576,"count":0}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":527757,"endOffset":527933,"count":1},{"startOffset":527889,"endOffset":527932,"count":0}],"isBlockCoverage":true},{"functionName":"get$isEmpty","ranges":[{"startOffset":528011,"endOffset":528074,"count":0}],"isBlockCoverage":false},{"functionName":"add$1","ranges":[{"startOffset":528087,"endOffset":528355,"count":0}],"isBlockCoverage":false},{"functionName":"handleNext$1","ranges":[{"startOffset":528375,"endOffset":528743,"count":0}],"isBlockCoverage":false},{"functionName":"get$isPaused","ranges":[{"startOffset":528809,"endOffset":528858,"count":0}],"isBlockCoverage":false},{"functionName":"_schedule$0","ranges":[{"startOffset":528877,"endOffset":529080,"count":0}],"isBlockCoverage":false},{"functionName":"onData$1","ranges":[{"startOffset":529096,"endOffset":529175,"count":0}],"isBlockCoverage":false},{"functionName":"onError$1","ranges":[{"startOffset":529192,"endOffset":529224,"count":0}],"isBlockCoverage":false},{"functionName":"onDone$1","ranges":[{"startOffset":529240,"endOffset":529332,"count":0}],"isBlockCoverage":false},{"functionName":"pause$1","ranges":[{"startOffset":529347,"endOffset":529401,"count":0}],"isBlockCoverage":false},{"functionName":"pause$0","ranges":[{"startOffset":529416,"endOffset":529467,"count":0}],"isBlockCoverage":false},{"functionName":"resume$0","ranges":[{"startOffset":529483,"endOffset":529661,"count":0}],"isBlockCoverage":false},{"functionName":"cancel$0","ranges":[{"startOffset":529677,"endOffset":529737,"count":0}],"isBlockCoverage":false},{"functionName":"_sendDone$0","ranges":[{"startOffset":529756,"endOffset":530019,"count":0}],"isBlockCoverage":false},{"functionName":"set$_onDone","ranges":[{"startOffset":530038,"endOffset":530121,"count":0}],"isBlockCoverage":false},{"functionName":"get$isBroadcast","ranges":[{"startOffset":530245,"endOffset":530282,"count":0}],"isBlockCoverage":false},{"functionName":"listen$4$cancelOnError$onDone$onError","ranges":[{"startOffset":530327,"endOffset":530684,"count":0}],"isBlockCoverage":false},{"functionName":"listen$3$onDone$onError","ranges":[{"startOffset":530715,"endOffset":530844,"count":0}],"isBlockCoverage":false},{"functionName":"listen$1","ranges":[{"startOffset":530860,"endOffset":530967,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":531027,"endOffset":531117,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":531203,"endOffset":531339,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":531418,"endOffset":531486,"count":1}],"isBlockCoverage":true},{"functionName":"toString$0","ranges":[{"startOffset":531582,"endOffset":531631,"count":0}],"isBlockCoverage":false},{"functionName":"handleUncaughtError$3","ranges":[{"startOffset":531905,"endOffset":532247,"count":0}],"isBlockCoverage":false},{"functionName":"registerCallback$1$2","ranges":[{"startOffset":532275,"endOffset":532668,"count":1}],"isBlockCoverage":true},{"functionName":"registerUnaryCallback$2$2","ranges":[{"startOffset":532701,"endOffset":533146,"count":1}],"isBlockCoverage":true},{"functionName":"registerBinaryCallback$3$2","ranges":[{"startOffset":533180,"endOffset":533670,"count":1}],"isBlockCoverage":true},{"functionName":"errorCallback$3","ranges":[{"startOffset":533693,"endOffset":534015,"count":0}],"isBlockCoverage":false},{"functionName":"get$_delegate","ranges":[{"startOffset":534130,"endOffset":534287,"count":1}],"isBlockCoverage":true},{"functionName":"get$errorZone","ranges":[{"startOffset":534308,"endOffset":534371,"count":1}],"isBlockCoverage":true},{"functionName":"runGuarded$1","ranges":[{"startOffset":534391,"endOffset":534691,"count":1},{"startOffset":534526,"endOffset":534685,"count":0}],"isBlockCoverage":true},{"functionName":"runUnaryGuarded$1$2","ranges":[{"startOffset":534718,"endOffset":535062,"count":1},{"startOffset":534897,"endOffset":535056,"count":0}],"isBlockCoverage":true},{"functionName":"runBinaryGuarded$2$3","ranges":[{"startOffset":535090,"endOffset":535511,"count":0}],"isBlockCoverage":false},{"functionName":"bindCallback$1$1","ranges":[{"startOffset":535535,"endOffset":535681,"count":1}],"isBlockCoverage":true},{"functionName":"bindUnaryCallback$2$1","ranges":[{"startOffset":535710,"endOffset":535907,"count":0}],"isBlockCoverage":false},{"functionName":"bindCallbackGuarded$1","ranges":[{"startOffset":535936,"endOffset":536091,"count":1}],"isBlockCoverage":true},{"functionName":"bindUnaryCallbackGuarded$1$1","ranges":[{"startOffset":536127,"endOffset":536303,"count":1}],"isBlockCoverage":true},{"functionName":"$index","ranges":[{"startOffset":536317,"endOffset":536623,"count":1}],"isBlockCoverage":true},{"functionName":"handleUncaughtError$2","ranges":[{"startOffset":536652,"endOffset":537041,"count":0}],"isBlockCoverage":false},{"functionName":"fork$2$specification$zoneValues","ranges":[{"startOffset":537080,"endOffset":537413,"count":1}],"isBlockCoverage":true},{"functionName":"run$1$1","ranges":[{"startOffset":537428,"endOffset":537846,"count":1}],"isBlockCoverage":true},{"functionName":"runUnary$2$2","ranges":[{"startOffset":537866,"endOffset":538372,"count":1}],"isBlockCoverage":true},{"functionName":"runBinary$3$3","ranges":[{"startOffset":538393,"endOffset":538980,"count":0}],"isBlockCoverage":false},{"functionName":"registerCallback$1$1","ranges":[{"startOffset":539008,"endOffset":539469,"count":1}],"isBlockCoverage":true},{"functionName":"registerUnaryCallback$2$1","ranges":[{"startOffset":539502,"endOffset":540015,"count":1}],"isBlockCoverage":true},{"functionName":"registerBinaryCallback$3$1","ranges":[{"startOffset":540049,"endOffset":540607,"count":1}],"isBlockCoverage":true},{"functionName":"errorCallback$2","ranges":[{"startOffset":540630,"endOffset":541146,"count":0}],"isBlockCoverage":false},{"functionName":"scheduleMicrotask$1","ranges":[{"startOffset":541173,"endOffset":541522,"count":1}],"isBlockCoverage":true},{"functionName":"createTimer$2","ranges":[{"startOffset":541543,"endOffset":541906,"count":1}],"isBlockCoverage":true},{"functionName":"print$1","ranges":[{"startOffset":541921,"endOffset":542216,"count":0}],"isBlockCoverage":false},{"functionName":"set$_run","ranges":[{"startOffset":542232,"endOffset":542315,"count":1}],"isBlockCoverage":true},{"functionName":"set$_runUnary","ranges":[{"startOffset":542336,"endOffset":542434,"count":1}],"isBlockCoverage":true},{"functionName":"set$_runBinary","ranges":[{"startOffset":542456,"endOffset":542557,"count":1}],"isBlockCoverage":true},{"functionName":"set$_registerCallback","ranges":[{"startOffset":542586,"endOffset":542708,"count":1}],"isBlockCoverage":true},{"functionName":"set$_registerUnaryCallback","ranges":[{"startOffset":542742,"endOffset":542879,"count":1}],"isBlockCoverage":true},{"functionName":"set$_registerBinaryCallback","ranges":[{"startOffset":542914,"endOffset":543054,"count":1}],"isBlockCoverage":true},{"functionName":"set$_errorCallback","ranges":[{"startOffset":543080,"endOffset":543248,"count":1}],"isBlockCoverage":true},{"functionName":"set$_scheduleMicrotask","ranges":[{"startOffset":543278,"endOffset":543462,"count":1}],"isBlockCoverage":true},{"functionName":"set$_createTimer","ranges":[{"startOffset":543486,"endOffset":543666,"count":1}],"isBlockCoverage":true},{"functionName":"set$_createPeriodicTimer","ranges":[{"startOffset":543698,"endOffset":543908,"count":1}],"isBlockCoverage":true},{"functionName":"set$_print","ranges":[{"startOffset":543926,"endOffset":544053,"count":1}],"isBlockCoverage":true},{"functionName":"set$_fork","ranges":[{"startOffset":544070,"endOffset":544243,"count":1}],"isBlockCoverage":true},{"functionName":"set$_handleUncaughtError","ranges":[{"startOffset":544275,"endOffset":544455,"count":1}],"isBlockCoverage":true},{"functionName":"get$_run","ranges":[{"startOffset":544471,"endOffset":544513,"count":1}],"isBlockCoverage":true},{"functionName":"get$_runUnary","ranges":[{"startOffset":544534,"endOffset":544581,"count":1}],"isBlockCoverage":true},{"functionName":"get$_runBinary","ranges":[{"startOffset":544603,"endOffset":544651,"count":1}],"isBlockCoverage":true},{"functionName":"get$_registerCallback","ranges":[{"startOffset":544680,"endOffset":544735,"count":1}],"isBlockCoverage":true},{"functionName":"get$_registerUnaryCallback","ranges":[{"startOffset":544769,"endOffset":544829,"count":1}],"isBlockCoverage":true},{"functionName":"get$_registerBinaryCallback","ranges":[{"startOffset":544864,"endOffset":544925,"count":1}],"isBlockCoverage":true},{"functionName":"get$_errorCallback","ranges":[{"startOffset":544951,"endOffset":545003,"count":1}],"isBlockCoverage":true},{"functionName":"get$_scheduleMicrotask","ranges":[{"startOffset":545033,"endOffset":545089,"count":1}],"isBlockCoverage":true},{"functionName":"get$_createTimer","ranges":[{"startOffset":545113,"endOffset":545163,"count":1}],"isBlockCoverage":true},{"functionName":"get$_createPeriodicTimer","ranges":[{"startOffset":545195,"endOffset":545253,"count":1}],"isBlockCoverage":true},{"functionName":"get$_print","ranges":[{"startOffset":545271,"endOffset":545315,"count":1}],"isBlockCoverage":true},{"functionName":"get$_fork","ranges":[{"startOffset":545332,"endOffset":545375,"count":1}],"isBlockCoverage":true},{"functionName":"get$_handleUncaughtError","ranges":[{"startOffset":545407,"endOffset":545465,"count":1}],"isBlockCoverage":true},{"functionName":"get$parent","ranges":[{"startOffset":545483,"endOffset":545535,"count":1}],"isBlockCoverage":true},{"functionName":"get$_async$_map","ranges":[{"startOffset":545558,"endOffset":545607,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":545676,"endOffset":545752,"count":1}],"isBlockCoverage":true},{"functionName":"$signature","ranges":[{"startOffset":545770,"endOffset":545824,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":545898,"endOffset":546051,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":546069,"endOffset":546156,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":546232,"endOffset":546305,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":546405,"endOffset":546531,"count":1}],"isBlockCoverage":true},{"functionName":"$signature","ranges":[{"startOffset":546549,"endOffset":546604,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":546673,"endOffset":546999,"count":0}],"isBlockCoverage":false},{"functionName":"get$_run","ranges":[{"startOffset":547066,"endOffset":547133,"count":1}],"isBlockCoverage":true},{"functionName":"get$_runUnary","ranges":[{"startOffset":547154,"endOffset":547226,"count":1}],"isBlockCoverage":true},{"functionName":"get$_runBinary","ranges":[{"startOffset":547248,"endOffset":547321,"count":1}],"isBlockCoverage":true},{"functionName":"get$_registerCallback","ranges":[{"startOffset":547350,"endOffset":547430,"count":1}],"isBlockCoverage":true},{"functionName":"get$_registerUnaryCallback","ranges":[{"startOffset":547464,"endOffset":547516,"count":1}],"isBlockCoverage":true},{"functionName":"get$_registerBinaryCallback","ranges":[{"startOffset":547551,"endOffset":547603,"count":1}],"isBlockCoverage":true},{"functionName":"get$_errorCallback","ranges":[{"startOffset":547629,"endOffset":547706,"count":1}],"isBlockCoverage":true},{"functionName":"get$_scheduleMicrotask","ranges":[{"startOffset":547736,"endOffset":547817,"count":1}],"isBlockCoverage":true},{"functionName":"get$_createTimer","ranges":[{"startOffset":547841,"endOffset":547916,"count":1}],"isBlockCoverage":true},{"functionName":"get$_createPeriodicTimer","ranges":[{"startOffset":547948,"endOffset":548000,"count":1}],"isBlockCoverage":true},{"functionName":"get$_print","ranges":[{"startOffset":548018,"endOffset":548087,"count":1}],"isBlockCoverage":true},{"functionName":"get$_fork","ranges":[{"startOffset":548104,"endOffset":548172,"count":1}],"isBlockCoverage":true},{"functionName":"get$_handleUncaughtError","ranges":[{"startOffset":548204,"endOffset":548256,"count":1}],"isBlockCoverage":true},{"functionName":"get$parent","ranges":[{"startOffset":548274,"endOffset":548312,"count":1}],"isBlockCoverage":true},{"functionName":"get$_async$_map","ranges":[{"startOffset":548335,"endOffset":548395,"count":0}],"isBlockCoverage":false},{"functionName":"get$_delegate","ranges":[{"startOffset":548416,"endOffset":548585,"count":0}],"isBlockCoverage":false},{"functionName":"get$errorZone","ranges":[{"startOffset":548606,"endOffset":548643,"count":1}],"isBlockCoverage":true},{"functionName":"runGuarded$1","ranges":[{"startOffset":548663,"endOffset":549139,"count":0}],"isBlockCoverage":false},{"functionName":"runUnaryGuarded$1$2","ranges":[{"startOffset":549166,"endOffset":549689,"count":1},{"startOffset":549479,"endOffset":549683,"count":0}],"isBlockCoverage":true},{"functionName":"runBinaryGuarded$2$3","ranges":[{"startOffset":549717,"endOffset":550324,"count":0}],"isBlockCoverage":false},{"functionName":"bindCallback$1$1","ranges":[{"startOffset":550348,"endOffset":550461,"count":0}],"isBlockCoverage":false},{"functionName":"bindCallbackGuarded$1","ranges":[{"startOffset":550490,"endOffset":550604,"count":0}],"isBlockCoverage":false},{"functionName":"bindUnaryCallbackGuarded$1$1","ranges":[{"startOffset":550640,"endOffset":550766,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":550780,"endOffset":550823,"count":0}],"isBlockCoverage":false},{"functionName":"handleUncaughtError$2","ranges":[{"startOffset":550852,"endOffset":550983,"count":0}],"isBlockCoverage":false},{"functionName":"fork$2$specification$zoneValues","ranges":[{"startOffset":551022,"endOffset":551136,"count":1}],"isBlockCoverage":true},{"functionName":"run$1$1","ranges":[{"startOffset":551151,"endOffset":551331,"count":0}],"isBlockCoverage":false},{"functionName":"runUnary$2$2","ranges":[{"startOffset":551351,"endOffset":551608,"count":1},{"startOffset":551538,"endOffset":551607,"count":0}],"isBlockCoverage":true},{"functionName":"runBinary$3$3","ranges":[{"startOffset":551629,"endOffset":551954,"count":0}],"isBlockCoverage":false},{"functionName":"registerCallback$1$1","ranges":[{"startOffset":551982,"endOffset":552047,"count":1}],"isBlockCoverage":true},{"functionName":"registerUnaryCallback$2$1","ranges":[{"startOffset":552080,"endOffset":552178,"count":1}],"isBlockCoverage":true},{"functionName":"registerBinaryCallback$3$1","ranges":[{"startOffset":552212,"endOffset":552328,"count":1}],"isBlockCoverage":true},{"functionName":"errorCallback$2","ranges":[{"startOffset":552351,"endOffset":552448,"count":0}],"isBlockCoverage":false},{"functionName":"scheduleMicrotask$1","ranges":[{"startOffset":552475,"endOffset":552575,"count":1}],"isBlockCoverage":true},{"functionName":"createTimer$2","ranges":[{"startOffset":552596,"endOffset":552701,"count":0}],"isBlockCoverage":false},{"functionName":"print$1","ranges":[{"startOffset":552716,"endOffset":552768,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":552835,"endOffset":552902,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":552920,"endOffset":552974,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":553048,"endOffset":553112,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":553210,"endOffset":553327,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":553345,"endOffset":553400,"count":0}],"isBlockCoverage":false},{"functionName":"call$5","ranges":[{"startOffset":553453,"endOffset":554320,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":554389,"endOffset":554447,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":554466,"endOffset":554530,"count":0}],"isBlockCoverage":false},{"functionName":"get$keys","ranges":[{"startOffset":554546,"endOffset":554667,"count":0}],"isBlockCoverage":false},{"functionName":"containsKey$1","ranges":[{"startOffset":554688,"endOffset":555100,"count":1},{"startOffset":554860,"endOffset":554882,"count":0},{"startOffset":554924,"endOffset":554953,"count":0},{"startOffset":554955,"endOffset":555048,"count":0}],"isBlockCoverage":true},{"functionName":"_containsKey$1","ranges":[{"startOffset":555122,"endOffset":555308,"count":1}],"isBlockCoverage":true},{"functionName":"$index","ranges":[{"startOffset":555322,"endOffset":555803,"count":1},{"startOffset":555403,"endOffset":555425,"count":0},{"startOffset":555427,"endOffset":555567,"count":0},{"startOffset":555600,"endOffset":555629,"count":0},{"startOffset":555631,"endOffset":555759,"count":0}],"isBlockCoverage":true},{"functionName":"_get$1","ranges":[{"startOffset":555817,"endOffset":556095,"count":1},{"startOffset":555929,"endOffset":555941,"count":0}],"isBlockCoverage":true},{"functionName":"$indexSet","ranges":[{"startOffset":556112,"endOffset":556762,"count":1},{"startOffset":556316,"endOffset":556338,"count":0},{"startOffset":556340,"endOffset":556504,"count":0},{"startOffset":556537,"endOffset":556566,"count":0},{"startOffset":556568,"endOffset":556717,"count":0}],"isBlockCoverage":true},{"functionName":"_set$2","ranges":[{"startOffset":556776,"endOffset":557585,"count":1},{"startOffset":557442,"endOffset":557571,"count":0}],"isBlockCoverage":true},{"functionName":"remove$1","ranges":[{"startOffset":557601,"endOffset":557678,"count":0}],"isBlockCoverage":false},{"functionName":"_remove$1","ranges":[{"startOffset":557695,"endOffset":558203,"count":0}],"isBlockCoverage":false},{"functionName":"forEach$1","ranges":[{"startOffset":558220,"endOffset":558693,"count":0}],"isBlockCoverage":false},{"functionName":"_computeKeys$0","ranges":[{"startOffset":558715,"endOffset":560019,"count":0}],"isBlockCoverage":false},{"functionName":"_addHashTableEntry$3","ranges":[{"startOffset":560047,"endOffset":560344,"count":0}],"isBlockCoverage":false},{"functionName":"_computeHashCode$1","ranges":[{"startOffset":560370,"endOffset":560439,"count":1}],"isBlockCoverage":true},{"functionName":"_getBucket$2","ranges":[{"startOffset":560459,"endOffset":560537,"count":1}],"isBlockCoverage":true},{"functionName":"_findBucketIndex$2","ranges":[{"startOffset":560563,"endOffset":560802,"count":1},{"startOffset":560779,"endOffset":560801,"count":0}],"isBlockCoverage":true},{"functionName":"_computeHashCode$1","ranges":[{"startOffset":560867,"endOffset":560937,"count":1}],"isBlockCoverage":true},{"functionName":"_findBucketIndex$2","ranges":[{"startOffset":560963,"endOffset":561255,"count":1},{"startOffset":561057,"endOffset":561254,"count":0}],"isBlockCoverage":true},{"functionName":"get$length","ranges":[{"startOffset":561315,"endOffset":561378,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":561397,"endOffset":561466,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":561486,"endOffset":561640,"count":0}],"isBlockCoverage":false},{"functionName":"contains$1","ranges":[{"startOffset":561658,"endOffset":561733,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":561794,"endOffset":561852,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":561870,"endOffset":562335,"count":0}],"isBlockCoverage":false},{"functionName":"set$_collection$_current","ranges":[{"startOffset":562367,"endOffset":562468,"count":0}],"isBlockCoverage":false},{"functionName":"_newSet$0","ranges":[{"startOffset":562542,"endOffset":562647,"count":1}],"isBlockCoverage":true},{"functionName":"get$iterator","ranges":[{"startOffset":562667,"endOffset":562927,"count":1}],"isBlockCoverage":true},{"functionName":"get$length","ranges":[{"startOffset":562945,"endOffset":563003,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":563022,"endOffset":563086,"count":0}],"isBlockCoverage":false},{"functionName":"contains$1","ranges":[{"startOffset":563104,"endOffset":563663,"count":1},{"startOffset":563301,"endOffset":563382,"count":0},{"startOffset":563533,"endOffset":563657,"count":0}],"isBlockCoverage":true},{"functionName":"_contains$1","ranges":[{"startOffset":563682,"endOffset":563883,"count":0}],"isBlockCoverage":false},{"functionName":"get$first","ranges":[{"startOffset":563900,"endOffset":564112,"count":0}],"isBlockCoverage":false},{"functionName":"get$last","ranges":[{"startOffset":564128,"endOffset":564339,"count":0}],"isBlockCoverage":false},{"functionName":"add$1","ranges":[{"startOffset":564352,"endOffset":565009,"count":1},{"startOffset":564713,"endOffset":565003,"count":0}],"isBlockCoverage":true},{"functionName":"_collection$_add$1","ranges":[{"startOffset":565035,"endOffset":565721,"count":0}],"isBlockCoverage":false},{"functionName":"remove$1","ranges":[{"startOffset":565737,"endOffset":566117,"count":1},{"startOffset":565819,"endOffset":565844,"count":0},{"startOffset":565854,"endOffset":565915,"count":0},{"startOffset":566060,"endOffset":566111,"count":0}],"isBlockCoverage":true},{"functionName":"_remove$1","ranges":[{"startOffset":566134,"endOffset":566619,"count":0}],"isBlockCoverage":false},{"functionName":"_addHashTableEntry$2","ranges":[{"startOffset":566647,"endOffset":566913,"count":1},{"startOffset":566808,"endOffset":566821,"count":0}],"isBlockCoverage":true},{"functionName":"_removeHashTableEntry$2","ranges":[{"startOffset":566944,"endOffset":567227,"count":1},{"startOffset":567033,"endOffset":567226,"count":0}],"isBlockCoverage":true},{"functionName":"_collection$_modified$0","ranges":[{"startOffset":567258,"endOffset":567366,"count":1}],"isBlockCoverage":true},{"functionName":"_collection$_newLinkedCell$1","ranges":[{"startOffset":567402,"endOffset":567925,"count":1}],"isBlockCoverage":true},{"functionName":"_unlinkCell$1","ranges":[{"startOffset":567946,"endOffset":568524,"count":0}],"isBlockCoverage":false},{"functionName":"_computeHashCode$1","ranges":[{"startOffset":568550,"endOffset":568627,"count":0}],"isBlockCoverage":false},{"functionName":"_findBucketIndex$2","ranges":[{"startOffset":568653,"endOffset":568906,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":569034,"endOffset":569092,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":569110,"endOffset":569695,"count":1},{"startOffset":569258,"endOffset":569316,"count":0},{"startOffset":569475,"endOffset":569681,"count":0}],"isBlockCoverage":true},{"functionName":"set$_collection$_current","ranges":[{"startOffset":569727,"endOffset":569828,"count":1}],"isBlockCoverage":true},{"functionName":"get$length","ranges":[{"startOffset":569909,"endOffset":570001,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":570015,"endOffset":570118,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":570183,"endOffset":570273,"count":1}],"isBlockCoverage":true},{"functionName":"call$2","ranges":[{"startOffset":570402,"endOffset":570492,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":570649,"endOffset":570808,"count":0}],"isBlockCoverage":false},{"functionName":"elementAt$1","ranges":[{"startOffset":570827,"endOffset":570903,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":570922,"endOffset":570994,"count":0}],"isBlockCoverage":false},{"functionName":"get$first","ranges":[{"startOffset":571011,"endOffset":571186,"count":0}],"isBlockCoverage":false},{"functionName":"get$last","ranges":[{"startOffset":571202,"endOffset":571405,"count":0}],"isBlockCoverage":false},{"functionName":"map$1$1","ranges":[{"startOffset":571420,"endOffset":571672,"count":0}],"isBlockCoverage":false},{"functionName":"toList$1$growable","ranges":[{"startOffset":571697,"endOffset":572067,"count":0}],"isBlockCoverage":false},{"functionName":"toList$0","ranges":[{"startOffset":572083,"endOffset":572164,"count":0}],"isBlockCoverage":false},{"functionName":"toSet$0","ranges":[{"startOffset":572179,"endOffset":572441,"count":0}],"isBlockCoverage":false},{"functionName":"remove$1","ranges":[{"startOffset":572457,"endOffset":572717,"count":0}],"isBlockCoverage":false},{"functionName":"_closeGap$2","ranges":[{"startOffset":572736,"endOffset":573112,"count":0}],"isBlockCoverage":false},{"functionName":"fillRange$3","ranges":[{"startOffset":573131,"endOffset":573410,"count":1}],"isBlockCoverage":true},{"functionName":"toString$0","ranges":[{"startOffset":573428,"endOffset":573524,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":573616,"endOffset":573883,"count":0}],"isBlockCoverage":false},{"functionName":"cast$2$0","ranges":[{"startOffset":573949,"endOffset":574109,"count":1}],"isBlockCoverage":true},{"functionName":"forEach$1","ranges":[{"startOffset":574126,"endOffset":574420,"count":0}],"isBlockCoverage":false},{"functionName":"map$2$1","ranges":[{"startOffset":574435,"endOffset":574940,"count":1}],"isBlockCoverage":true},{"functionName":"containsKey$1","ranges":[{"startOffset":574961,"endOffset":575031,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":575049,"endOffset":575132,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":575151,"endOffset":575235,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":575253,"endOffset":575314,"count":0}],"isBlockCoverage":false},{"functionName":"remove$1","ranges":[{"startOffset":575389,"endOffset":575497,"count":0}],"isBlockCoverage":false},{"functionName":"cast$2$0","ranges":[{"startOffset":575543,"endOffset":575614,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":575628,"endOffset":575691,"count":0}],"isBlockCoverage":false},{"functionName":"containsKey$1","ranges":[{"startOffset":575712,"endOffset":575776,"count":0}],"isBlockCoverage":false},{"functionName":"forEach$1","ranges":[{"startOffset":575793,"endOffset":575906,"count":1}],"isBlockCoverage":true},{"functionName":"get$isEmpty","ranges":[{"startOffset":575925,"endOffset":576003,"count":1}],"isBlockCoverage":true},{"functionName":"get$length","ranges":[{"startOffset":576021,"endOffset":576098,"count":0}],"isBlockCoverage":false},{"functionName":"get$keys","ranges":[{"startOffset":576114,"endOffset":576167,"count":0}],"isBlockCoverage":false},{"functionName":"remove$1","ranges":[{"startOffset":576183,"endOffset":576248,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":576266,"endOffset":576323,"count":0}],"isBlockCoverage":false},{"functionName":"map$2$1","ranges":[{"startOffset":576338,"endOffset":576514,"count":1}],"isBlockCoverage":true},{"functionName":"cast$2$0","ranges":[{"startOffset":576587,"endOffset":576753,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":576805,"endOffset":576990,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":577009,"endOffset":577068,"count":1}],"isBlockCoverage":true},{"functionName":"get$length","ranges":[{"startOffset":577086,"endOffset":577176,"count":0}],"isBlockCoverage":false},{"functionName":"get$first","ranges":[{"startOffset":577193,"endOffset":577451,"count":0}],"isBlockCoverage":false},{"functionName":"get$last","ranges":[{"startOffset":577467,"endOffset":577803,"count":0}],"isBlockCoverage":false},{"functionName":"elementAt$1","ranges":[{"startOffset":577822,"endOffset":578227,"count":0}],"isBlockCoverage":false},{"functionName":"clear$0","ranges":[{"startOffset":578242,"endOffset":578565,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":578583,"endOffset":578668,"count":0}],"isBlockCoverage":false},{"functionName":"removeFirst$0","ranges":[{"startOffset":578689,"endOffset":579148,"count":1},{"startOffset":578802,"endOffset":578860,"count":0},{"startOffset":578955,"endOffset":578978,"count":0}],"isBlockCoverage":true},{"functionName":"_collection$_add$1","ranges":[{"startOffset":579174,"endOffset":580057,"count":1},{"startOffset":579524,"endOffset":580017,"count":0}],"isBlockCoverage":true},{"functionName":"set$_table","ranges":[{"startOffset":580075,"endOffset":580163,"count":1}],"isBlockCoverage":true},{"functionName":"get$current","ranges":[{"startOffset":580240,"endOffset":580298,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":580316,"endOffset":580875,"count":0}],"isBlockCoverage":false},{"functionName":"set$_collection$_current","ranges":[{"startOffset":580907,"endOffset":581008,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":581078,"endOffset":581139,"count":0}],"isBlockCoverage":false},{"functionName":"map$1$1","ranges":[{"startOffset":581154,"endOffset":581394,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":581412,"endOffset":581497,"count":0}],"isBlockCoverage":false},{"functionName":"every$1","ranges":[{"startOffset":581512,"endOffset":581772,"count":0}],"isBlockCoverage":false},{"functionName":"get$first","ranges":[{"startOffset":581789,"endOffset":581974,"count":0}],"isBlockCoverage":false},{"functionName":"get$last","ranges":[{"startOffset":581990,"endOffset":582256,"count":0}],"isBlockCoverage":false},{"functionName":"toSet$0","ranges":[{"startOffset":582456,"endOffset":582553,"count":1}],"isBlockCoverage":true},{"functionName":"get$isEmpty","ranges":[{"startOffset":582572,"endOffset":582636,"count":0}],"isBlockCoverage":false},{"functionName":"addAll$1","ranges":[{"startOffset":582652,"endOffset":582872,"count":1},{"startOffset":582834,"endOffset":582866,"count":0}],"isBlockCoverage":true},{"functionName":"union$1","ranges":[{"startOffset":582887,"endOffset":583059,"count":1}],"isBlockCoverage":true},{"functionName":"toList$1$growable","ranges":[{"startOffset":583084,"endOffset":583579,"count":1},{"startOffset":583450,"endOffset":583552,"count":0}],"isBlockCoverage":true},{"functionName":"toList$0","ranges":[{"startOffset":583595,"endOffset":583676,"count":1}],"isBlockCoverage":true},{"functionName":"map$1$1","ranges":[{"startOffset":583691,"endOffset":583931,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":583949,"endOffset":584034,"count":0}],"isBlockCoverage":false},{"functionName":"where$1","ranges":[{"startOffset":584049,"endOffset":584214,"count":1}],"isBlockCoverage":true},{"functionName":"fold$1$2","ranges":[{"startOffset":584230,"endOffset":584642,"count":0}],"isBlockCoverage":false},{"functionName":"every$1","ranges":[{"startOffset":584657,"endOffset":584988,"count":0}],"isBlockCoverage":false},{"functionName":"any$1","ranges":[{"startOffset":585001,"endOffset":585340,"count":0}],"isBlockCoverage":false},{"functionName":"get$first","ranges":[{"startOffset":585357,"endOffset":585627,"count":0}],"isBlockCoverage":false},{"functionName":"get$last","ranges":[{"startOffset":585643,"endOffset":585994,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":586272,"endOffset":586605,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":586623,"endOffset":586845,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":586864,"endOffset":586925,"count":0}],"isBlockCoverage":false},{"functionName":"get$keys","ranges":[{"startOffset":586941,"endOffset":587091,"count":0}],"isBlockCoverage":false},{"functionName":"containsKey$1","ranges":[{"startOffset":587112,"endOffset":587355,"count":0}],"isBlockCoverage":false},{"functionName":"remove$1","ranges":[{"startOffset":587371,"endOffset":587528,"count":0}],"isBlockCoverage":false},{"functionName":"forEach$1","ranges":[{"startOffset":587545,"endOffset":588211,"count":0}],"isBlockCoverage":false},{"functionName":"get$_upgradedMap","ranges":[{"startOffset":588235,"endOffset":588325,"count":0}],"isBlockCoverage":false},{"functionName":"_convert$_computeKeys$0","ranges":[{"startOffset":588356,"endOffset":588651,"count":0}],"isBlockCoverage":false},{"functionName":"_upgrade$0","ranges":[{"startOffset":588669,"endOffset":589287,"count":0}],"isBlockCoverage":false},{"functionName":"_process$1","ranges":[{"startOffset":589305,"endOffset":589541,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":589601,"endOffset":589681,"count":0}],"isBlockCoverage":false},{"functionName":"elementAt$1","ranges":[{"startOffset":589700,"endOffset":590025,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":590045,"endOffset":590376,"count":0}],"isBlockCoverage":false},{"functionName":"contains$1","ranges":[{"startOffset":590394,"endOffset":590464,"count":0}],"isBlockCoverage":false},{"functionName":"encode$1","ranges":[{"startOffset":590513,"endOffset":590588,"count":0}],"isBlockCoverage":false},{"functionName":"convert$1","ranges":[{"startOffset":590649,"endOffset":591298,"count":0}],"isBlockCoverage":false},{"functionName":"normalize$3","ranges":[{"startOffset":591384,"endOffset":595104,"count":0}],"isBlockCoverage":false},{"functionName":"decode$2$reviver","ranges":[{"startOffset":595311,"endOffset":595497,"count":0}],"isBlockCoverage":false},{"functionName":"get$decoder","ranges":[{"startOffset":595516,"endOffset":595567,"count":0}],"isBlockCoverage":false},{"functionName":"get$encoder","ranges":[{"startOffset":595650,"endOffset":595698,"count":0}],"isBlockCoverage":false},{"functionName":"convert$1","ranges":[{"startOffset":595749,"endOffset":596529,"count":0}],"isBlockCoverage":false},{"functionName":"_writeSurrogate$2","ranges":[{"startOffset":596589,"endOffset":598037,"count":0}],"isBlockCoverage":false},{"functionName":"_fillBuffer$3","ranges":[{"startOffset":598058,"endOffset":599908,"count":0}],"isBlockCoverage":false},{"functionName":"convert$1","ranges":[{"startOffset":599959,"endOffset":601081,"count":0}],"isBlockCoverage":false},{"functionName":"flush$2","ranges":[{"startOffset":601131,"endOffset":601378,"count":0}],"isBlockCoverage":false},{"functionName":"convert$3","ranges":[{"startOffset":601395,"endOffset":605325,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":605392,"endOffset":605547,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":605567,"endOffset":605692,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":605710,"endOffset":606328,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":606397,"endOffset":606550,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":606570,"endOffset":606648,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":606666,"endOffset":607284,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":607348,"endOffset":607623,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":607707,"endOffset":607790,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":607891,"endOffset":608058,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":608077,"endOffset":608130,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":608186,"endOffset":608236,"count":0}],"isBlockCoverage":false},{"functionName":"get$_errorName","ranges":[{"startOffset":608294,"endOffset":608378,"count":0}],"isBlockCoverage":false},{"functionName":"get$_errorExplanation","ranges":[{"startOffset":608407,"endOffset":608442,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":608460,"endOffset":608982,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":609001,"endOffset":609054,"count":0}],"isBlockCoverage":false},{"functionName":"get$_errorName","ranges":[{"startOffset":609109,"endOffset":609154,"count":0}],"isBlockCoverage":false},{"functionName":"get$_errorExplanation","ranges":[{"startOffset":609183,"endOffset":609833,"count":0}],"isBlockCoverage":false},{"functionName":"get$_errorName","ranges":[{"startOffset":609888,"endOffset":609933,"count":0}],"isBlockCoverage":false},{"functionName":"get$_errorExplanation","ranges":[{"startOffset":609962,"endOffset":610401,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":610419,"endOffset":610471,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":610528,"endOffset":610602,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":610621,"endOffset":610674,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":610733,"endOffset":610859,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":610878,"endOffset":610931,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":610982,"endOffset":611044,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":611063,"endOffset":611116,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":611184,"endOffset":611413,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":611470,"endOffset":611519,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":611595,"endOffset":611645,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":611728,"endOffset":611927,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":611978,"endOffset":612040,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":612080,"endOffset":612133,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":612189,"endOffset":614795,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":614835,"endOffset":614888,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":614932,"endOffset":615559,"count":0}],"isBlockCoverage":false},{"functionName":"$indexSet","ranges":[{"startOffset":615576,"endOffset":616073,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":616091,"endOffset":616147,"count":0}],"isBlockCoverage":false},{"functionName":"map$1$1","ranges":[{"startOffset":616246,"endOffset":616443,"count":0}],"isBlockCoverage":false},{"functionName":"where$1","ranges":[{"startOffset":616458,"endOffset":616647,"count":1}],"isBlockCoverage":true},{"functionName":"contains$1","ranges":[{"startOffset":616665,"endOffset":616856,"count":0}],"isBlockCoverage":false},{"functionName":"join$1","ranges":[{"startOffset":616870,"endOffset":617364,"count":0}],"isBlockCoverage":false},{"functionName":"join$0","ranges":[{"startOffset":617378,"endOffset":617446,"count":0}],"isBlockCoverage":false},{"functionName":"toList$1$growable","ranges":[{"startOffset":617471,"endOffset":617588,"count":0}],"isBlockCoverage":false},{"functionName":"toList$0","ranges":[{"startOffset":617604,"endOffset":617685,"count":0}],"isBlockCoverage":false},{"functionName":"toSet$0","ranges":[{"startOffset":617700,"endOffset":617819,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":617837,"endOffset":618062,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":618081,"endOffset":618152,"count":0}],"isBlockCoverage":false},{"functionName":"skipWhile$1","ranges":[{"startOffset":618171,"endOffset":618368,"count":0}],"isBlockCoverage":false},{"functionName":"get$first","ranges":[{"startOffset":618385,"endOffset":618570,"count":0}],"isBlockCoverage":false},{"functionName":"get$last","ranges":[{"startOffset":618586,"endOffset":618852,"count":0}],"isBlockCoverage":false},{"functionName":"elementAt$1","ranges":[{"startOffset":618871,"endOffset":619282,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":619300,"endOffset":619386,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":619558,"endOffset":619650,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":619697,"endOffset":619779,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":619797,"endOffset":619837,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":619937,"endOffset":619992,"count":1}],"isBlockCoverage":true},{"functionName":"get$hashCode","ranges":[{"startOffset":620012,"endOffset":620079,"count":1}],"isBlockCoverage":true},{"functionName":"toString$0","ranges":[{"startOffset":620097,"endOffset":620193,"count":0}],"isBlockCoverage":false},{"functionName":"get$runtimeType","ranges":[{"startOffset":620216,"endOffset":620272,"count":0}],"isBlockCoverage":false},{"functionName":"toString","ranges":[{"startOffset":620288,"endOffset":620342,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":620552,"endOffset":620602,"count":0}],"isBlockCoverage":false},{"functionName":"get$elapsedMicroseconds","ranges":[{"startOffset":620687,"endOffset":621099,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":621187,"endOffset":621252,"count":0}],"isBlockCoverage":false},{"functionName":"get$last","ranges":[{"startOffset":621268,"endOffset":621758,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":621812,"endOffset":621867,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":621885,"endOffset":622720,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":622793,"endOffset":622848,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":622866,"endOffset":622962,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":623072,"endOffset":623205,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":623288,"endOffset":623421,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":623435,"endOffset":623493,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":623579,"endOffset":624044,"count":0}],"isBlockCoverage":false},{"functionName":"get$userInfo","ranges":[{"startOffset":624111,"endOffset":624158,"count":0}],"isBlockCoverage":false},{"functionName":"get$host","ranges":[{"startOffset":624174,"endOffset":624399,"count":0}],"isBlockCoverage":false},{"functionName":"get$port","ranges":[{"startOffset":624415,"endOffset":624549,"count":0}],"isBlockCoverage":false},{"functionName":"get$query","ranges":[{"startOffset":624566,"endOffset":624647,"count":0}],"isBlockCoverage":false},{"functionName":"get$fragment","ranges":[{"startOffset":624667,"endOffset":624751,"count":0}],"isBlockCoverage":false},{"functionName":"replace$2$path$pathSegments","ranges":[{"startOffset":624786,"endOffset":625788,"count":0}],"isBlockCoverage":false},{"functionName":"replace$1$path","ranges":[{"startOffset":625810,"endOffset":625913,"count":0}],"isBlockCoverage":false},{"functionName":"replace$1$pathSegments","ranges":[{"startOffset":625943,"endOffset":626062,"count":0}],"isBlockCoverage":false},{"functionName":"get$pathSegments","ranges":[{"startOffset":626086,"endOffset":626770,"count":0}],"isBlockCoverage":false},{"functionName":"_mergePaths$2","ranges":[{"startOffset":626791,"endOffset":627849,"count":0}],"isBlockCoverage":false},{"functionName":"resolve$1","ranges":[{"startOffset":627866,"endOffset":627949,"count":0}],"isBlockCoverage":false},{"functionName":"resolveUri$1","ranges":[{"startOffset":627969,"endOffset":630843,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasAuthority","ranges":[{"startOffset":630867,"endOffset":630918,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasPort","ranges":[{"startOffset":630937,"endOffset":630988,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasQuery","ranges":[{"startOffset":631008,"endOffset":631060,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasFragment","ranges":[{"startOffset":631083,"endOffset":631138,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasAbsolutePath","ranges":[{"startOffset":631165,"endOffset":631245,"count":0}],"isBlockCoverage":false},{"functionName":"toFilePath$0","ranges":[{"startOffset":631265,"endOffset":632530,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":632548,"endOffset":633376,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":633387,"endOffset":634982,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":635002,"endOffset":635163,"count":0}],"isBlockCoverage":false},{"functionName":"set$_pathSegments","ranges":[{"startOffset":635188,"endOffset":635287,"count":0}],"isBlockCoverage":false},{"functionName":"get$scheme","ranges":[{"startOffset":635320,"endOffset":635364,"count":0}],"isBlockCoverage":false},{"functionName":"get$path","ranges":[{"startOffset":635380,"endOffset":635430,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":635494,"endOffset":635608,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":635716,"endOffset":636051,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":636130,"endOffset":636243,"count":0}],"isBlockCoverage":false},{"functionName":"get$uri","ranges":[{"startOffset":636307,"endOffset":637019,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":637037,"endOffset":637234,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":637292,"endOffset":637344,"count":1}],"isBlockCoverage":true},{"functionName":"call$2","ranges":[{"startOffset":637420,"endOffset":637648,"count":1},{"startOffset":637523,"endOffset":637549,"count":0}],"isBlockCoverage":true},{"functionName":"call$3","ranges":[{"startOffset":637727,"endOffset":638030,"count":1},{"startOffset":637956,"endOffset":637983,"count":0}],"isBlockCoverage":true},{"functionName":"call$3","ranges":[{"startOffset":638109,"endOffset":638448,"count":1},{"startOffset":638374,"endOffset":638401,"count":0}],"isBlockCoverage":true},{"functionName":"get$hasAuthority","ranges":[{"startOffset":638525,"endOffset":638577,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasPort","ranges":[{"startOffset":638596,"endOffset":638689,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasQuery","ranges":[{"startOffset":638709,"endOffset":638780,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasFragment","ranges":[{"startOffset":638803,"endOffset":638874,"count":0}],"isBlockCoverage":false},{"functionName":"get$_isFile","ranges":[{"startOffset":638893,"endOffset":639001,"count":0}],"isBlockCoverage":false},{"functionName":"get$_isHttp","ranges":[{"startOffset":639020,"endOffset":639128,"count":0}],"isBlockCoverage":false},{"functionName":"get$_isHttps","ranges":[{"startOffset":639148,"endOffset":639257,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasAbsolutePath","ranges":[{"startOffset":639284,"endOffset":639381,"count":0}],"isBlockCoverage":false},{"functionName":"get$scheme","ranges":[{"startOffset":639399,"endOffset":640155,"count":0}],"isBlockCoverage":false},{"functionName":"get$userInfo","ranges":[{"startOffset":640175,"endOffset":640342,"count":0}],"isBlockCoverage":false},{"functionName":"get$host","ranges":[{"startOffset":640358,"endOffset":640500,"count":0}],"isBlockCoverage":false},{"functionName":"get$port","ranges":[{"startOffset":640516,"endOffset":640832,"count":0}],"isBlockCoverage":false},{"functionName":"get$path","ranges":[{"startOffset":640848,"endOffset":640958,"count":0}],"isBlockCoverage":false},{"functionName":"get$query","ranges":[{"startOffset":640975,"endOffset":641143,"count":0}],"isBlockCoverage":false},{"functionName":"get$fragment","ranges":[{"startOffset":641163,"endOffset":641320,"count":0}],"isBlockCoverage":false},{"functionName":"get$pathSegments","ranges":[{"startOffset":641344,"endOffset":642029,"count":1},{"startOffset":641575,"endOffset":641595,"count":0}],"isBlockCoverage":true},{"functionName":"_isPort$1","ranges":[{"startOffset":642046,"endOffset":642247,"count":0}],"isBlockCoverage":false},{"functionName":"removeFragment$0","ranges":[{"startOffset":642271,"endOffset":642611,"count":0}],"isBlockCoverage":false},{"functionName":"replace$2$path$pathSegments","ranges":[{"startOffset":642646,"endOffset":644260,"count":0}],"isBlockCoverage":false},{"functionName":"replace$1$path","ranges":[{"startOffset":644282,"endOffset":644385,"count":0}],"isBlockCoverage":false},{"functionName":"replace$1$pathSegments","ranges":[{"startOffset":644415,"endOffset":644534,"count":0}],"isBlockCoverage":false},{"functionName":"resolve$1","ranges":[{"startOffset":644551,"endOffset":644634,"count":0}],"isBlockCoverage":false},{"functionName":"resolveUri$1","ranges":[{"startOffset":644654,"endOffset":644839,"count":0}],"isBlockCoverage":false},{"functionName":"_simpleMerge$2","ranges":[{"startOffset":644861,"endOffset":648814,"count":0}],"isBlockCoverage":false},{"functionName":"toFilePath$0","ranges":[{"startOffset":648834,"endOffset":649861,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":649881,"endOffset":650033,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":650044,"endOffset":650236,"count":0}],"isBlockCoverage":false},{"functionName":"_toNonSimple$0","ranges":[{"startOffset":650258,"endOffset":650822,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":650840,"endOffset":650883,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":650995,"endOffset":651052,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":651137,"endOffset":651194,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":651247,"endOffset":651304,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":651323,"endOffset":651380,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":651432,"endOffset":651489,"count":0}],"isBlockCoverage":false},{"functionName":"addEventListener$3","ranges":[{"startOffset":651586,"endOffset":651788,"count":1}],"isBlockCoverage":true},{"functionName":"_addEventListener$3","ranges":[{"startOffset":651815,"endOffset":651995,"count":1}],"isBlockCoverage":true},{"functionName":"_removeEventListener$3","ranges":[{"startOffset":652025,"endOffset":652208,"count":1}],"isBlockCoverage":true},{"functionName":"get$origin","ranges":[{"startOffset":652315,"endOffset":652470,"count":1},{"startOffset":652399,"endOffset":652469,"count":0}],"isBlockCoverage":true},{"functionName":"toString$0","ranges":[{"startOffset":652488,"endOffset":652545,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":652597,"endOffset":652654,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":652716,"endOffset":652773,"count":0}],"isBlockCoverage":false},{"functionName":"addEventListener$3","ranges":[{"startOffset":652884,"endOffset":653127,"count":1}],"isBlockCoverage":true},{"functionName":"postMessage$1","ranges":[{"startOffset":653148,"endOffset":653318,"count":1}],"isBlockCoverage":true},{"functionName":"get$message","ranges":[{"startOffset":653406,"endOffset":653463,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":653525,"endOffset":653582,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":653637,"endOffset":653694,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":653768,"endOffset":653825,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":653889,"endOffset":653946,"count":0}],"isBlockCoverage":false},{"functionName":"get$isBroadcast","ranges":[{"startOffset":654044,"endOffset":654081,"count":0}],"isBlockCoverage":false},{"functionName":"listen$4$cancelOnError$onDone$onError","ranges":[{"startOffset":654126,"endOffset":654445,"count":1}],"isBlockCoverage":true},{"functionName":"listen$3$onDone$onError","ranges":[{"startOffset":654476,"endOffset":654605,"count":0}],"isBlockCoverage":false},{"functionName":"listen$1","ranges":[{"startOffset":654621,"endOffset":654728,"count":0}],"isBlockCoverage":false},{"functionName":"cancel$0","ranges":[{"startOffset":654791,"endOffset":655010,"count":1},{"startOffset":654875,"endOffset":654887,"count":0}],"isBlockCoverage":true},{"functionName":"pause$1","ranges":[{"startOffset":655025,"endOffset":655161,"count":0}],"isBlockCoverage":false},{"functionName":"pause$0","ranges":[{"startOffset":655176,"endOffset":655227,"count":0}],"isBlockCoverage":false},{"functionName":"resume$0","ranges":[{"startOffset":655243,"endOffset":655421,"count":0}],"isBlockCoverage":false},{"functionName":"_tryResume$0","ranges":[{"startOffset":655441,"endOffset":655647,"count":1}],"isBlockCoverage":true},{"functionName":"_unlisten$0","ranges":[{"startOffset":655666,"endOffset":655969,"count":1}],"isBlockCoverage":true},{"functionName":"set$_html$_onData","ranges":[{"startOffset":655994,"endOffset":656092,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":656161,"endOffset":656236,"count":1}],"isBlockCoverage":true},{"functionName":"findSlot$1","ranges":[{"startOffset":656313,"endOffset":656603,"count":1},{"startOffset":656474,"endOffset":656483,"count":0}],"isBlockCoverage":true},{"functionName":"walk$1","ranges":[{"startOffset":656617,"endOffset":658566,"count":1},{"startOffset":656751,"endOffset":656760,"count":0},{"startOffset":656904,"endOffset":656930,"count":0},{"startOffset":656970,"endOffset":657045,"count":0},{"startOffset":657083,"endOffset":657092,"count":0},{"startOffset":657130,"endOffset":657139,"count":0},{"startOffset":657249,"endOffset":657258,"count":0},{"startOffset":657409,"endOffset":657434,"count":0},{"startOffset":657506,"endOffset":657518,"count":0},{"startOffset":657862,"endOffset":657887,"count":0},{"startOffset":657949,"endOffset":657961,"count":0},{"startOffset":658011,"endOffset":658565,"count":0}],"isBlockCoverage":true},{"functionName":"copyList$2","ranges":[{"startOffset":658584,"endOffset":658922,"count":1}],"isBlockCoverage":true},{"functionName":"call$2","ranges":[{"startOffset":658988,"endOffset":659072,"count":1}],"isBlockCoverage":true},{"functionName":"call$2","ranges":[{"startOffset":659158,"endOffset":659242,"count":0}],"isBlockCoverage":false},{"functionName":"findSlot$1","ranges":[{"startOffset":659324,"endOffset":659614,"count":1},{"startOffset":659485,"endOffset":659494,"count":0}],"isBlockCoverage":true},{"functionName":"walk$1","ranges":[{"startOffset":659628,"endOffset":661744,"count":1},{"startOffset":659949,"endOffset":660278,"count":0},{"startOffset":660318,"endOffset":660393,"count":0},{"startOffset":660467,"endOffset":660510,"count":0},{"startOffset":660713,"endOffset":660738,"count":0},{"startOffset":660814,"endOffset":660826,"count":0},{"startOffset":661277,"endOffset":661302,"count":0},{"startOffset":661364,"endOffset":661376,"count":0},{"startOffset":661502,"endOffset":661505,"count":0},{"startOffset":661722,"endOffset":661743,"count":0}],"isBlockCoverage":true},{"functionName":"convertNativeToDart_AcceptStructuredClone$2$mustCopy","ranges":[{"startOffset":661804,"endOffset":661900,"count":1}],"isBlockCoverage":true},{"functionName":"call$2","ranges":[{"startOffset":661972,"endOffset":662124,"count":1}],"isBlockCoverage":true},{"functionName":"forEachObjectKey$2","ranges":[{"startOffset":662216,"endOffset":662485,"count":0}],"isBlockCoverage":false},{"functionName":"forEachJsField$2","ranges":[{"startOffset":662561,"endOffset":662902,"count":1},{"startOffset":662770,"endOffset":662816,"count":0}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":662964,"endOffset":663725,"count":1},{"startOffset":663098,"endOffset":663121,"count":0},{"startOffset":663497,"endOffset":663696,"count":0}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":663805,"endOffset":663896,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":663977,"endOffset":664044,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":664969,"endOffset":665026,"count":0}],"isBlockCoverage":false},{"functionName":"runOnce$1","ranges":[{"startOffset":665079,"endOffset":665381,"count":0}],"isBlockCoverage":false},{"functionName":"onData$1","ranges":[{"startOffset":665493,"endOffset":665616,"count":0}],"isBlockCoverage":false},{"functionName":"onError$1","ranges":[{"startOffset":665633,"endOffset":665732,"count":0}],"isBlockCoverage":false},{"functionName":"onDone$1","ranges":[{"startOffset":665748,"endOffset":665866,"count":0}],"isBlockCoverage":false},{"functionName":"pause$1","ranges":[{"startOffset":665881,"endOffset":665974,"count":0}],"isBlockCoverage":false},{"functionName":"pause$0","ranges":[{"startOffset":665989,"endOffset":666040,"count":0}],"isBlockCoverage":false},{"functionName":"resume$0","ranges":[{"startOffset":666056,"endOffset":666126,"count":0}],"isBlockCoverage":false},{"functionName":"cancel$0","ranges":[{"startOffset":666142,"endOffset":666219,"count":0}],"isBlockCoverage":false},{"functionName":"add$1","ranges":[{"startOffset":666296,"endOffset":666782,"count":0}],"isBlockCoverage":false},{"functionName":"close$0","ranges":[{"startOffset":666797,"endOffset":667077,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":667153,"endOffset":667619,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":667637,"endOffset":667703,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":667764,"endOffset":667976,"count":0}],"isBlockCoverage":false},{"functionName":"add$1","ranges":[{"startOffset":668045,"endOffset":668148,"count":0}],"isBlockCoverage":false},{"functionName":"addStream$1","ranges":[{"startOffset":668167,"endOffset":668625,"count":0}],"isBlockCoverage":false},{"functionName":"_checkEventAllowed$0","ranges":[{"startOffset":668653,"endOffset":668914,"count":0}],"isBlockCoverage":false},{"functionName":"close$0","ranges":[{"startOffset":668929,"endOffset":669017,"count":0}],"isBlockCoverage":false},{"functionName":"get$done","ranges":[{"startOffset":669118,"endOffset":669160,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":669229,"endOffset":669287,"count":0}],"isBlockCoverage":false},{"functionName":"complete$1","ranges":[{"startOffset":669358,"endOffset":669447,"count":0}],"isBlockCoverage":false},{"functionName":"addTo$1","ranges":[{"startOffset":669462,"endOffset":669536,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":669556,"endOffset":669672,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":669683,"endOffset":669875,"count":0}],"isBlockCoverage":false},{"functionName":"complete$1","ranges":[{"startOffset":669972,"endOffset":670080,"count":1}],"isBlockCoverage":true},{"functionName":"addTo$1","ranges":[{"startOffset":670095,"endOffset":670191,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":670211,"endOffset":670292,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":670303,"endOffset":670456,"count":0}],"isBlockCoverage":false},{"functionName":"setSourceStream$1","ranges":[{"startOffset":670537,"endOffset":670945,"count":1},{"startOffset":670703,"endOffset":670769,"count":0}],"isBlockCoverage":true},{"functionName":"listen$4$cancelOnError$onDone$onError","ranges":[{"startOffset":671029,"endOffset":671873,"count":1},{"startOffset":671585,"endOffset":671619,"count":0}],"isBlockCoverage":true},{"functionName":"listen$3$onDone$onError","ranges":[{"startOffset":671904,"endOffset":672033,"count":0}],"isBlockCoverage":false},{"functionName":"listen$1","ranges":[{"startOffset":672049,"endOffset":672156,"count":1}],"isBlockCoverage":true},{"functionName":"_linkStreamToController$0","ranges":[{"startOffset":672189,"endOffset":672550,"count":1}],"isBlockCoverage":true},{"functionName":"_createController$0","ranges":[{"startOffset":672577,"endOffset":672786,"count":1}],"isBlockCoverage":true},{"functionName":"set$_stream_completer$_controller","ranges":[{"startOffset":672827,"endOffset":672960,"count":1}],"isBlockCoverage":true},{"functionName":"set$_sourceStream","ranges":[{"startOffset":672985,"endOffset":673096,"count":1}],"isBlockCoverage":true},{"functionName":"add$1","ranges":[{"startOffset":673143,"endOffset":673811,"count":0}],"isBlockCoverage":false},{"functionName":"_onListen$0","ranges":[{"startOffset":673830,"endOffset":674010,"count":0}],"isBlockCoverage":false},{"functionName":"_onCancelBroadcast$0","ranges":[{"startOffset":674038,"endOffset":674225,"count":0}],"isBlockCoverage":false},{"functionName":"_listenToStream$1","ranges":[{"startOffset":674250,"endOffset":674687,"count":0}],"isBlockCoverage":false},{"functionName":"close$0","ranges":[{"startOffset":674702,"endOffset":675097,"count":0}],"isBlockCoverage":false},{"functionName":"set$_stream_group$_controller","ranges":[{"startOffset":675134,"endOffset":675263,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":675339,"endOffset":675376,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":675456,"endOffset":675530,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":675548,"endOffset":675630,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":675696,"endOffset":676010,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":676028,"endOffset":676124,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":676199,"endOffset":676545,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":676563,"endOffset":676659,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":676731,"endOffset":677110,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":677188,"endOffset":677231,"count":0}],"isBlockCoverage":false},{"functionName":"get$next","ranges":[{"startOffset":677281,"endOffset":677676,"count":1},{"startOffset":677618,"endOffset":677675,"count":0}],"isBlockCoverage":true},{"functionName":"_updateRequests$0","ranges":[{"startOffset":677701,"endOffset":678244,"count":1},{"startOffset":677901,"endOffset":677955,"count":0},{"startOffset":678019,"endOffset":678042,"count":0},{"startOffset":678120,"endOffset":678151,"count":0}],"isBlockCoverage":true},{"functionName":"_extractStream$0","ranges":[{"startOffset":678268,"endOffset":678938,"count":1},{"startOffset":678406,"endOffset":678470,"count":0},{"startOffset":678575,"endOffset":678610,"count":0}],"isBlockCoverage":true},{"functionName":"_ensureListening$0","ranges":[{"startOffset":678964,"endOffset":679408,"count":1},{"startOffset":679038,"endOffset":679045,"count":0},{"startOffset":679368,"endOffset":679402,"count":0}],"isBlockCoverage":true},{"functionName":"_addResult$1","ranges":[{"startOffset":679428,"endOffset":679693,"count":1}],"isBlockCoverage":true},{"functionName":"_failClosed$0","ranges":[{"startOffset":679714,"endOffset":679784,"count":0}],"isBlockCoverage":false},{"functionName":"_addRequest$1","ranges":[{"startOffset":679805,"endOffset":680179,"count":1}],"isBlockCoverage":true},{"functionName":"set$_stream_queue$_subscription","ranges":[{"startOffset":680218,"endOffset":680355,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":680428,"endOffset":680601,"count":1}],"isBlockCoverage":true},{"functionName":"$signature","ranges":[{"startOffset":680619,"endOffset":680685,"count":1}],"isBlockCoverage":true},{"functionName":"call$2","ranges":[{"startOffset":680759,"endOffset":680888,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":680981,"endOffset":681129,"count":0}],"isBlockCoverage":false},{"functionName":"update$2","ranges":[{"startOffset":681233,"endOffset":681629,"count":1},{"startOffset":681475,"endOffset":681603,"count":0}],"isBlockCoverage":true},{"functionName":"update$2","ranges":[{"startOffset":681705,"endOffset":683204,"count":1},{"startOffset":681986,"endOffset":682524,"count":0},{"startOffset":682592,"endOffset":683179,"count":0}],"isBlockCoverage":true},{"functionName":"get$_canSendDirectly","ranges":[{"startOffset":683334,"endOffset":683447,"count":0}],"isBlockCoverage":false},{"functionName":"get$done","ranges":[{"startOffset":683463,"endOffset":683878,"count":0}],"isBlockCoverage":false},{"functionName":"addStream$1","ranges":[{"startOffset":683897,"endOffset":684228,"count":0}],"isBlockCoverage":false},{"functionName":"close$0","ranges":[{"startOffset":684243,"endOffset":684519,"count":0}],"isBlockCoverage":false},{"functionName":"_ensureController$0","ranges":[{"startOffset":684546,"endOffset":684755,"count":0}],"isBlockCoverage":false},{"functionName":"_setDestinationSink$1","ranges":[{"startOffset":684784,"endOffset":685386,"count":1},{"startOffset":685061,"endOffset":685262,"count":0},{"startOffset":685349,"endOffset":685380,"count":0}],"isBlockCoverage":true},{"functionName":"set$_stream_sink_completer$_controller","ranges":[{"startOffset":685432,"endOffset":685570,"count":0}],"isBlockCoverage":false},{"functionName":"set$_destinationSink","ranges":[{"startOffset":685598,"endOffset":685722,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":685886,"endOffset":685905,"count":0}],"isBlockCoverage":false},{"functionName":"listen$4$cancelOnError$onDone$onError","ranges":[{"startOffset":686010,"endOffset":686754,"count":1},{"startOffset":686321,"endOffset":686398,"count":0},{"startOffset":686489,"endOffset":686590,"count":0}],"isBlockCoverage":true},{"functionName":"listen$3$onDone$onError","ranges":[{"startOffset":686785,"endOffset":686914,"count":0}],"isBlockCoverage":false},{"functionName":"listen$1","ranges":[{"startOffset":686930,"endOffset":687037,"count":0}],"isBlockCoverage":false},{"functionName":"set$_subscription_stream$_source","ranges":[{"startOffset":687077,"endOffset":687203,"count":1}],"isBlockCoverage":true},{"functionName":"onError$1","ranges":[{"startOffset":687276,"endOffset":687442,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":687528,"endOffset":688068,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":688174,"endOffset":688382,"count":0}],"isBlockCoverage":false},{"functionName":"evaluate$1","ranges":[{"startOffset":688481,"endOffset":688527,"count":1}],"isBlockCoverage":true},{"functionName":"intersection$1","ranges":[{"startOffset":688549,"endOffset":688592,"count":0}],"isBlockCoverage":false},{"functionName":"validate$1","ranges":[{"startOffset":688610,"endOffset":688689,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":688707,"endOffset":688748,"count":0}],"isBlockCoverage":false},{"functionName":"accept$1","ranges":[{"startOffset":688826,"endOffset":688895,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":688913,"endOffset":688956,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":688967,"endOffset":689113,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":689133,"endOffset":689193,"count":0}],"isBlockCoverage":false},{"functionName":"get$span","ranges":[{"startOffset":689225,"endOffset":689267,"count":0}],"isBlockCoverage":false},{"functionName":"accept$1","ranges":[{"startOffset":689313,"endOffset":689377,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":689395,"endOffset":689568,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":689579,"endOffset":689727,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":689747,"endOffset":689834,"count":0}],"isBlockCoverage":false},{"functionName":"get$span","ranges":[{"startOffset":689866,"endOffset":689908,"count":0}],"isBlockCoverage":false},{"functionName":"get$span","ranges":[{"startOffset":689953,"endOffset":690044,"count":0}],"isBlockCoverage":false},{"functionName":"accept$1","ranges":[{"startOffset":690060,"endOffset":690123,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":690141,"endOffset":690553,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":690564,"endOffset":690743,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":690763,"endOffset":690897,"count":0}],"isBlockCoverage":false},{"functionName":"get$span","ranges":[{"startOffset":690959,"endOffset":691050,"count":0}],"isBlockCoverage":false},{"functionName":"accept$1","ranges":[{"startOffset":691066,"endOffset":691130,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":691148,"endOffset":691558,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":691569,"endOffset":691749,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":691769,"endOffset":691903,"count":0}],"isBlockCoverage":false},{"functionName":"get$span","ranges":[{"startOffset":691973,"endOffset":692073,"count":0}],"isBlockCoverage":false},{"functionName":"accept$1","ranges":[{"startOffset":692089,"endOffset":692161,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":692179,"endOffset":692631,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":692642,"endOffset":692888,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":692908,"endOffset":693101,"count":0}],"isBlockCoverage":false},{"functionName":"visitVariable$1","ranges":[{"startOffset":693172,"endOffset":693242,"count":0}],"isBlockCoverage":false},{"functionName":"visitNot$1","ranges":[{"startOffset":693260,"endOffset":693346,"count":0}],"isBlockCoverage":false},{"functionName":"visitOr$1","ranges":[{"startOffset":693363,"endOffset":693499,"count":0}],"isBlockCoverage":false},{"functionName":"visitAnd$1","ranges":[{"startOffset":693517,"endOffset":693653,"count":0}],"isBlockCoverage":false},{"functionName":"visitConditional$1","ranges":[{"startOffset":693679,"endOffset":693831,"count":0}],"isBlockCoverage":false},{"functionName":"evaluate$1","ranges":[{"startOffset":693910,"endOffset":694228,"count":0}],"isBlockCoverage":false},{"functionName":"intersection$1","ranges":[{"startOffset":694250,"endOffset":694597,"count":0}],"isBlockCoverage":false},{"functionName":"validate$1","ranges":[{"startOffset":694615,"endOffset":694736,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":694754,"endOffset":694816,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":694827,"endOffset":694995,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":695015,"endOffset":695099,"count":0}],"isBlockCoverage":false},{"functionName":"evaluate$1","ranges":[{"startOffset":695187,"endOffset":695353,"count":0}],"isBlockCoverage":false},{"functionName":"intersection$1","ranges":[{"startOffset":695375,"endOffset":695452,"count":0}],"isBlockCoverage":false},{"functionName":"validate$1","ranges":[{"startOffset":695470,"endOffset":695639,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":695657,"endOffset":695766,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":695777,"endOffset":695993,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":696013,"endOffset":696141,"count":0}],"isBlockCoverage":false},{"functionName":"evaluate$1","ranges":[{"startOffset":696213,"endOffset":696260,"count":0}],"isBlockCoverage":false},{"functionName":"intersection$1","ranges":[{"startOffset":696282,"endOffset":696324,"count":0}],"isBlockCoverage":false},{"functionName":"validate$1","ranges":[{"startOffset":696342,"endOffset":696421,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":696439,"endOffset":696481,"count":0}],"isBlockCoverage":false},{"functionName":"parse$0","ranges":[{"startOffset":696552,"endOffset":696864,"count":0}],"isBlockCoverage":false},{"functionName":"_conditional$0","ranges":[{"startOffset":696886,"endOffset":697347,"count":0}],"isBlockCoverage":false},{"functionName":"_or$0","ranges":[{"startOffset":697360,"endOffset":697536,"count":0}],"isBlockCoverage":false},{"functionName":"_and$0","ranges":[{"startOffset":697550,"endOffset":697742,"count":0}],"isBlockCoverage":false},{"functionName":"_simpleExpression$0","ranges":[{"startOffset":697769,"endOffset":698600,"count":0}],"isBlockCoverage":false},{"functionName":"peek$0","ranges":[{"startOffset":698644,"endOffset":698770,"count":0}],"isBlockCoverage":false},{"functionName":"next$0","ranges":[{"startOffset":698784,"endOffset":699055,"count":0}],"isBlockCoverage":false},{"functionName":"scan$1","ranges":[{"startOffset":699069,"endOffset":699219,"count":0}],"isBlockCoverage":false},{"functionName":"_getNext$0","ranges":[{"startOffset":699237,"endOffset":700677,"count":0}],"isBlockCoverage":false},{"functionName":"_scanOperator$1","ranges":[{"startOffset":700700,"endOffset":701057,"count":0}],"isBlockCoverage":false},{"functionName":"_consumeWhitespace$0","ranges":[{"startOffset":701085,"endOffset":701439,"count":0}],"isBlockCoverage":false},{"functionName":"_multiLineComment$0","ranges":[{"startOffset":701466,"endOffset":701903,"count":0}],"isBlockCoverage":false},{"functionName":"get$type","ranges":[{"startOffset":701947,"endOffset":701997,"count":0}],"isBlockCoverage":false},{"functionName":"get$span","ranges":[{"startOffset":702013,"endOffset":702055,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":702111,"endOffset":702182,"count":0}],"isBlockCoverage":false},{"functionName":"get$type","ranges":[{"startOffset":702215,"endOffset":702270,"count":0}],"isBlockCoverage":false},{"functionName":"get$span","ranges":[{"startOffset":702286,"endOffset":702328,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":702378,"endOffset":702421,"count":0}],"isBlockCoverage":false},{"functionName":"visitVariable$1","ranges":[{"startOffset":702476,"endOffset":702681,"count":0}],"isBlockCoverage":false},{"functionName":"visitNot$1","ranges":[{"startOffset":702738,"endOffset":702793,"count":0}],"isBlockCoverage":false},{"functionName":"visitOr$1","ranges":[{"startOffset":702810,"endOffset":702897,"count":0}],"isBlockCoverage":false},{"functionName":"visitAnd$1","ranges":[{"startOffset":702915,"endOffset":703002,"count":0}],"isBlockCoverage":false},{"functionName":"visitConditional$1","ranges":[{"startOffset":703028,"endOffset":703160,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":703242,"endOffset":703293,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":703311,"endOffset":703346,"count":0}],"isBlockCoverage":false},{"functionName":"contains$1","ranges":[{"startOffset":703364,"endOffset":703412,"count":0}],"isBlockCoverage":false},{"functionName":"toSet$0","ranges":[{"startOffset":703427,"endOffset":703514,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":703615,"endOffset":703731,"count":1}],"isBlockCoverage":true},{"functionName":"$signature","ranges":[{"startOffset":703749,"endOffset":703857,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":703909,"endOffset":704161,"count":1}],"isBlockCoverage":true},{"functionName":"$signature","ranges":[{"startOffset":704179,"endOffset":704273,"count":1}],"isBlockCoverage":true},{"functionName":"call$2","ranges":[{"startOffset":704327,"endOffset":704582,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":704600,"endOffset":704692,"count":1}],"isBlockCoverage":true},{"functionName":"toString$0","ranges":[{"startOffset":704742,"endOffset":704827,"count":0}],"isBlockCoverage":false},{"functionName":"removeFirst$0","ranges":[{"startOffset":704848,"endOffset":705338,"count":1},{"startOffset":704985,"endOffset":705036,"count":0},{"startOffset":705109,"endOffset":705132,"count":0}],"isBlockCoverage":true},{"functionName":"get$length","ranges":[{"startOffset":705356,"endOffset":705482,"count":1}],"isBlockCoverage":true},{"functionName":"set$length","ranges":[{"startOffset":705500,"endOffset":706426,"count":0}],"isBlockCoverage":false},{"functionName":"$index","ranges":[{"startOffset":706440,"endOffset":706924,"count":0}],"isBlockCoverage":false},{"functionName":"$indexSet","ranges":[{"startOffset":706941,"endOffset":707471,"count":0}],"isBlockCoverage":false},{"functionName":"_queue_list$_add$1","ranges":[{"startOffset":707497,"endOffset":708514,"count":1},{"startOffset":707919,"endOffset":708508,"count":0}],"isBlockCoverage":true},{"functionName":"_writeToList$1","ranges":[{"startOffset":708536,"endOffset":709305,"count":0}],"isBlockCoverage":false},{"functionName":"_preGrow$1","ranges":[{"startOffset":709323,"endOffset":709960,"count":0}],"isBlockCoverage":false},{"functionName":"set$_queue_list$_table","ranges":[{"startOffset":709990,"endOffset":710090,"count":1}],"isBlockCoverage":true},{"functionName":"get$length","ranges":[{"startOffset":710275,"endOffset":710401,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":710421,"endOffset":710522,"count":0}],"isBlockCoverage":false},{"functionName":"get$_union_set$_iterable","ranges":[{"startOffset":710554,"endOffset":710878,"count":0}],"isBlockCoverage":false},{"functionName":"toSet$0","ranges":[{"startOffset":710893,"endOffset":711220,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":711280,"endOffset":711601,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":711619,"endOffset":711693,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":711756,"endOffset":711836,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":711854,"endOffset":711927,"count":0}],"isBlockCoverage":false},{"functionName":"set$_union_set_controller$_set","ranges":[{"startOffset":712065,"endOffset":712173,"count":0}],"isBlockCoverage":false},{"functionName":"contains$1","ranges":[{"startOffset":712394,"endOffset":712470,"count":0}],"isBlockCoverage":false},{"functionName":"every$1","ranges":[{"startOffset":712485,"endOffset":712601,"count":0}],"isBlockCoverage":false},{"functionName":"get$first","ranges":[{"startOffset":712618,"endOffset":712695,"count":0}],"isBlockCoverage":false},{"functionName":"get$isEmpty","ranges":[{"startOffset":712714,"endOffset":712793,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":712813,"endOffset":712893,"count":0}],"isBlockCoverage":false},{"functionName":"get$last","ranges":[{"startOffset":712909,"endOffset":712985,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":713003,"endOffset":713081,"count":0}],"isBlockCoverage":false},{"functionName":"map$1$1","ranges":[{"startOffset":713096,"endOffset":713223,"count":0}],"isBlockCoverage":false},{"functionName":"toList$1$growable","ranges":[{"startOffset":713248,"endOffset":713329,"count":1}],"isBlockCoverage":true},{"functionName":"toList$0","ranges":[{"startOffset":713345,"endOffset":713426,"count":1}],"isBlockCoverage":true},{"functionName":"toSet$0","ranges":[{"startOffset":713441,"endOffset":713496,"count":0}],"isBlockCoverage":false},{"functionName":"where$1","ranges":[{"startOffset":713511,"endOffset":713627,"count":1}],"isBlockCoverage":true},{"functionName":"toString$0","ranges":[{"startOffset":713645,"endOffset":713703,"count":0}],"isBlockCoverage":false},{"functionName":"union$1","ranges":[{"startOffset":713813,"endOffset":713967,"count":1}],"isBlockCoverage":true},{"functionName":"toSet$0","ranges":[{"startOffset":713982,"endOffset":714157,"count":0}],"isBlockCoverage":false},{"functionName":"matches$2","ranges":[{"startOffset":714254,"endOffset":714324,"count":1}],"isBlockCoverage":true},{"functionName":"describe$1","ranges":[{"startOffset":714342,"endOffset":714441,"count":0}],"isBlockCoverage":false},{"functionName":"typedMatches$2","ranges":[{"startOffset":714496,"endOffset":714602,"count":0}],"isBlockCoverage":false},{"functionName":"describe$1","ranges":[{"startOffset":714620,"endOffset":714745,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":714803,"endOffset":714863,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":714881,"endOffset":714982,"count":0}],"isBlockCoverage":false},{"functionName":"addDescriptionOf$1","ranges":[{"startOffset":715008,"endOffset":715192,"count":0}],"isBlockCoverage":false},{"functionName":"typedMatches$2","ranges":[{"startOffset":715280,"endOffset":715389,"count":0}],"isBlockCoverage":false},{"functionName":"describe$1","ranges":[{"startOffset":715407,"endOffset":715510,"count":0}],"isBlockCoverage":false},{"functionName":"describeTypedMismatch$4","ranges":[{"startOffset":715541,"endOffset":717567,"count":0}],"isBlockCoverage":false},{"functionName":"_compareIterables$5","ranges":[{"startOffset":717629,"endOffset":718839,"count":0}],"isBlockCoverage":false},{"functionName":"_compareSets$5","ranges":[{"startOffset":718861,"endOffset":720203,"count":0}],"isBlockCoverage":false},{"functionName":"_recursiveMatch$4","ranges":[{"startOffset":720228,"endOffset":723384,"count":0}],"isBlockCoverage":false},{"functionName":"_equals_matcher$_match$3","ranges":[{"startOffset":723416,"endOffset":724262,"count":0}],"isBlockCoverage":false},{"functionName":"matches$2","ranges":[{"startOffset":724279,"endOffset":724402,"count":0}],"isBlockCoverage":false},{"functionName":"describe$1","ranges":[{"startOffset":724420,"endOffset":724510,"count":0}],"isBlockCoverage":false},{"functionName":"describeMismatch$4","ranges":[{"startOffset":724536,"endOffset":725070,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":725140,"endOffset":725305,"count":0}],"isBlockCoverage":false},{"functionName":"matches$2","ranges":[{"startOffset":725378,"endOffset":725603,"count":0}],"isBlockCoverage":false},{"functionName":"describeMismatch$4","ranges":[{"startOffset":725629,"endOffset":725977,"count":0}],"isBlockCoverage":false},{"functionName":"describeTypedMismatch$4","ranges":[{"startOffset":726008,"endOffset":726176,"count":0}],"isBlockCoverage":false},{"functionName":"describeMismatch$4","ranges":[{"startOffset":726232,"endOffset":726330,"count":0}],"isBlockCoverage":false},{"functionName":"call$4","ranges":[{"startOffset":726391,"endOffset":730032,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":730116,"endOffset":730227,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":730316,"endOffset":730510,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":730599,"endOffset":730730,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":730820,"endOffset":731014,"count":0}],"isBlockCoverage":false},{"functionName":"describe$1","ranges":[{"startOffset":731085,"endOffset":731450,"count":0}],"isBlockCoverage":false},{"functionName":"matches$2","ranges":[{"startOffset":731467,"endOffset":731575,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":731631,"endOffset":731703,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":731773,"endOffset":731958,"count":0}],"isBlockCoverage":false},{"functionName":"get$packageRoot","ranges":[{"startOffset":732071,"endOffset":732108,"count":0}],"isBlockCoverage":false},{"functionName":"get$packageConfigMap","ranges":[{"startOffset":732136,"endOffset":732190,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":732270,"endOffset":732353,"count":1}],"isBlockCoverage":true},{"functionName":"get$packageConfigMap","ranges":[{"startOffset":732469,"endOffset":732506,"count":0}],"isBlockCoverage":false},{"functionName":"get$packageRoot","ranges":[{"startOffset":732529,"endOffset":732578,"count":0}],"isBlockCoverage":false},{"functionName":"absolute$7","ranges":[{"startOffset":732626,"endOffset":733114,"count":0}],"isBlockCoverage":false},{"functionName":"absolute$1","ranges":[{"startOffset":733132,"endOffset":733250,"count":0}],"isBlockCoverage":false},{"functionName":"join$8","ranges":[{"startOffset":733264,"endOffset":733650,"count":0}],"isBlockCoverage":false},{"functionName":"join$2","ranges":[{"startOffset":733664,"endOffset":733792,"count":0}],"isBlockCoverage":false},{"functionName":"joinAll$1","ranges":[{"startOffset":733809,"endOffset":735362,"count":0}],"isBlockCoverage":false},{"functionName":"split$1","ranges":[{"startOffset":735377,"endOffset":735875,"count":0}],"isBlockCoverage":false},{"functionName":"normalize$1","ranges":[{"startOffset":735894,"endOffset":736127,"count":0}],"isBlockCoverage":false},{"functionName":"_needsNormalization$1","ranges":[{"startOffset":736156,"endOffset":737652,"count":0}],"isBlockCoverage":false},{"functionName":"relative$2$from","ranges":[{"startOffset":737675,"endOffset":741067,"count":0}],"isBlockCoverage":false},{"functionName":"relative$1","ranges":[{"startOffset":741085,"endOffset":741154,"count":0}],"isBlockCoverage":false},{"functionName":"_isWithinOrEquals$2","ranges":[{"startOffset":741181,"endOffset":743129,"count":0}],"isBlockCoverage":false},{"functionName":"_isWithinOrEqualsFast$2","ranges":[{"startOffset":743160,"endOffset":747690,"count":0}],"isBlockCoverage":false},{"functionName":"_pathDirection$2","ranges":[{"startOffset":747714,"endOffset":748939,"count":0}],"isBlockCoverage":false},{"functionName":"toUri$1","ranges":[{"startOffset":748954,"endOffset":749248,"count":0}],"isBlockCoverage":false},{"functionName":"prettyUri$1","ranges":[{"startOffset":749267,"endOffset":749843,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":749900,"endOffset":749973,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":750052,"endOffset":750124,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":750201,"endOffset":750279,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":750359,"endOffset":750468,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":750542,"endOffset":750585,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":750639,"endOffset":750682,"count":0}],"isBlockCoverage":false},{"functionName":"getRoot$1","ranges":[{"startOffset":750735,"endOffset":751064,"count":0}],"isBlockCoverage":false},{"functionName":"relativePathToUri$1","ranges":[{"startOffset":751091,"endOffset":751348,"count":0}],"isBlockCoverage":false},{"functionName":"codeUnitsEqual$2","ranges":[{"startOffset":751372,"endOffset":751448,"count":0}],"isBlockCoverage":false},{"functionName":"pathsEqual$2","ranges":[{"startOffset":751468,"endOffset":751527,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasTrailingSeparator","ranges":[{"startOffset":751592,"endOffset":751829,"count":0}],"isBlockCoverage":false},{"functionName":"removeTrailingSeparators$0","ranges":[{"startOffset":751863,"endOffset":752298,"count":0}],"isBlockCoverage":false},{"functionName":"normalize$0","ranges":[{"startOffset":752317,"endOffset":753935,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":753953,"endOffset":754466,"count":0}],"isBlockCoverage":false},{"functionName":"set$parts","ranges":[{"startOffset":754483,"endOffset":754558,"count":0}],"isBlockCoverage":false},{"functionName":"set$separators","ranges":[{"startOffset":754580,"endOffset":754670,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":754735,"endOffset":754801,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":754875,"endOffset":754941,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":754981,"endOffset":755034,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":755080,"endOffset":755133,"count":0}],"isBlockCoverage":false},{"functionName":"containsSeparator$1","ranges":[{"startOffset":755193,"endOffset":755270,"count":0}],"isBlockCoverage":false},{"functionName":"isSeparator$1","ranges":[{"startOffset":755291,"endOffset":755347,"count":0}],"isBlockCoverage":false},{"functionName":"needsSeparator$1","ranges":[{"startOffset":755371,"endOffset":755500,"count":0}],"isBlockCoverage":false},{"functionName":"rootLength$2$withDrive","ranges":[{"startOffset":755530,"endOffset":755678,"count":0}],"isBlockCoverage":false},{"functionName":"rootLength$1","ranges":[{"startOffset":755698,"endOffset":755775,"count":0}],"isBlockCoverage":false},{"functionName":"isRootRelative$1","ranges":[{"startOffset":755799,"endOffset":755841,"count":0}],"isBlockCoverage":false},{"functionName":"pathFromUri$1","ranges":[{"startOffset":755862,"endOffset":756185,"count":0}],"isBlockCoverage":false},{"functionName":"absolutePathToUri$1","ranges":[{"startOffset":756212,"endOffset":756605,"count":0}],"isBlockCoverage":false},{"functionName":"get$name","ranges":[{"startOffset":756621,"endOffset":756661,"count":0}],"isBlockCoverage":false},{"functionName":"get$separator","ranges":[{"startOffset":756682,"endOffset":756718,"count":0}],"isBlockCoverage":false},{"functionName":"containsSeparator$1","ranges":[{"startOffset":756776,"endOffset":756853,"count":0}],"isBlockCoverage":false},{"functionName":"isSeparator$1","ranges":[{"startOffset":756874,"endOffset":756930,"count":0}],"isBlockCoverage":false},{"functionName":"needsSeparator$1","ranges":[{"startOffset":756954,"endOffset":757222,"count":0}],"isBlockCoverage":false},{"functionName":"rootLength$2$withDrive","ranges":[{"startOffset":757252,"endOffset":758194,"count":0}],"isBlockCoverage":false},{"functionName":"rootLength$1","ranges":[{"startOffset":758214,"endOffset":758291,"count":0}],"isBlockCoverage":false},{"functionName":"isRootRelative$1","ranges":[{"startOffset":758315,"endOffset":758421,"count":0}],"isBlockCoverage":false},{"functionName":"pathFromUri$1","ranges":[{"startOffset":758442,"endOffset":758496,"count":0}],"isBlockCoverage":false},{"functionName":"relativePathToUri$1","ranges":[{"startOffset":758523,"endOffset":758577,"count":0}],"isBlockCoverage":false},{"functionName":"absolutePathToUri$1","ranges":[{"startOffset":758604,"endOffset":758658,"count":0}],"isBlockCoverage":false},{"functionName":"get$name","ranges":[{"startOffset":758674,"endOffset":758712,"count":0}],"isBlockCoverage":false},{"functionName":"get$separator","ranges":[{"startOffset":758733,"endOffset":758769,"count":0}],"isBlockCoverage":false},{"functionName":"containsSeparator$1","ranges":[{"startOffset":758831,"endOffset":758908,"count":0}],"isBlockCoverage":false},{"functionName":"isSeparator$1","ranges":[{"startOffset":758929,"endOffset":759004,"count":0}],"isBlockCoverage":false},{"functionName":"needsSeparator$1","ranges":[{"startOffset":759028,"endOffset":759218,"count":0}],"isBlockCoverage":false},{"functionName":"rootLength$2$withDrive","ranges":[{"startOffset":759248,"endOffset":760107,"count":0}],"isBlockCoverage":false},{"functionName":"rootLength$1","ranges":[{"startOffset":760127,"endOffset":760204,"count":0}],"isBlockCoverage":false},{"functionName":"isRootRelative$1","ranges":[{"startOffset":760228,"endOffset":760294,"count":0}],"isBlockCoverage":false},{"functionName":"pathFromUri$1","ranges":[{"startOffset":760315,"endOffset":760968,"count":0}],"isBlockCoverage":false},{"functionName":"absolutePathToUri$1","ranges":[{"startOffset":760995,"endOffset":762083,"count":0}],"isBlockCoverage":false},{"functionName":"codeUnitsEqual$2","ranges":[{"startOffset":762107,"endOffset":762496,"count":0}],"isBlockCoverage":false},{"functionName":"pathsEqual$2","ranges":[{"startOffset":762516,"endOffset":762906,"count":0}],"isBlockCoverage":false},{"functionName":"get$name","ranges":[{"startOffset":762922,"endOffset":762964,"count":0}],"isBlockCoverage":false},{"functionName":"get$separator","ranges":[{"startOffset":762985,"endOffset":763022,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":763097,"endOffset":763169,"count":0}],"isBlockCoverage":false},{"functionName":"request$0","ranges":[{"startOffset":763232,"endOffset":764213,"count":0}],"isBlockCoverage":false},{"functionName":"withResource$1$1","ranges":[{"startOffset":764237,"endOffset":764370,"count":0}],"isBlockCoverage":false},{"functionName":"withResource$body$Pool","ranges":[{"startOffset":764400,"endOffset":766633,"count":0}],"isBlockCoverage":false},{"functionName":"close$0","ranges":[{"startOffset":766648,"endOffset":766745,"count":0}],"isBlockCoverage":false},{"functionName":"_onResourceReleaseAllowed$1","ranges":[{"startOffset":766780,"endOffset":767623,"count":0}],"isBlockCoverage":false},{"functionName":"_runOnRelease$1","ranges":[{"startOffset":767646,"endOffset":768136,"count":0}],"isBlockCoverage":false},{"functionName":"_resetTimer$0","ranges":[{"startOffset":768157,"endOffset":768543,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":768598,"endOffset":769521,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":769616,"endOffset":769695,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":769777,"endOffset":769909,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":769992,"endOffset":770160,"count":0}],"isBlockCoverage":false},{"functionName":"release$0","ranges":[{"startOffset":770231,"endOffset":770780,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":770838,"endOffset":771040,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":771119,"endOffset":773479,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":773558,"endOffset":773629,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":773709,"endOffset":773806,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":773887,"endOffset":773961,"count":0}],"isBlockCoverage":false},{"functionName":"MultiSectionMapping$fromJson$3$mapUrl","ranges":[{"startOffset":774096,"endOffset":775955,"count":0}],"isBlockCoverage":false},{"functionName":"_indexFor$2","ranges":[{"startOffset":775974,"endOffset":776437,"count":0}],"isBlockCoverage":false},{"functionName":"spanFor$4$files$uri","ranges":[{"startOffset":776464,"endOffset":777052,"count":0}],"isBlockCoverage":false},{"functionName":"spanFor$3$uri","ranges":[{"startOffset":777073,"endOffset":777172,"count":0}],"isBlockCoverage":false},{"functionName":"spanFor$3$files","ranges":[{"startOffset":777195,"endOffset":777298,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":777316,"endOffset":777847,"count":0}],"isBlockCoverage":false},{"functionName":"MappingBundle$fromJson$2$mapUrl","ranges":[{"startOffset":777922,"endOffset":778250,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":778268,"endOffset":778496,"count":0}],"isBlockCoverage":false},{"functionName":"spanFor$4$files$uri","ranges":[{"startOffset":778523,"endOffset":779530,"count":0}],"isBlockCoverage":false},{"functionName":"spanFor$3$uri","ranges":[{"startOffset":779551,"endOffset":779650,"count":0}],"isBlockCoverage":false},{"functionName":"SingleMapping$fromJson$2$mapUrl","ranges":[{"startOffset":779725,"endOffset":783823,"count":0}],"isBlockCoverage":false},{"functionName":"_segmentError$2","ranges":[{"startOffset":783846,"endOffset":784041,"count":0}],"isBlockCoverage":false},{"functionName":"_findLine$1","ranges":[{"startOffset":784060,"endOffset":784406,"count":0}],"isBlockCoverage":false},{"functionName":"_findColumn$3","ranges":[{"startOffset":784427,"endOffset":785004,"count":0}],"isBlockCoverage":false},{"functionName":"spanFor$4$files$uri","ranges":[{"startOffset":785031,"endOffset":786224,"count":0}],"isBlockCoverage":false},{"functionName":"spanFor$3$uri","ranges":[{"startOffset":786245,"endOffset":786344,"count":0}],"isBlockCoverage":false},{"functionName":"spanFor$3$files","ranges":[{"startOffset":786367,"endOffset":786470,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":786488,"endOffset":786852,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":786919,"endOffset":787072,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":787159,"endOffset":787217,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":787306,"endOffset":787368,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":787443,"endOffset":787558,"count":0}],"isBlockCoverage":false},{"functionName":"get$line","ranges":[{"startOffset":787574,"endOffset":787616,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":787668,"endOffset":787921,"count":0}],"isBlockCoverage":false},{"functionName":"get$column","ranges":[{"startOffset":787939,"endOffset":787983,"count":0}],"isBlockCoverage":false},{"functionName":"moveNext$0","ranges":[{"startOffset":788041,"endOffset":788109,"count":0}],"isBlockCoverage":false},{"functionName":"get$current","ranges":[{"startOffset":788128,"endOffset":788407,"count":0}],"isBlockCoverage":false},{"functionName":"get$hasTokens","ranges":[{"startOffset":788428,"endOffset":788527,"count":0}],"isBlockCoverage":false},{"functionName":"get$nextKind","ranges":[{"startOffset":788547,"endOffset":788997,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":789015,"endOffset":789583,"count":0}],"isBlockCoverage":false},{"functionName":"get$isIdentifier","ranges":[{"startOffset":789694,"endOffset":789744,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":789788,"endOffset":790045,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":790116,"endOffset":790175,"count":0}],"isBlockCoverage":false},{"functionName":"get$lines","ranges":[{"startOffset":790192,"endOffset":790248,"count":0}],"isBlockCoverage":false},{"functionName":"SourceFile$decoded$2$url","ranges":[{"startOffset":790280,"endOffset":790792,"count":0}],"isBlockCoverage":false},{"functionName":"span$2","ranges":[{"startOffset":790806,"endOffset":790879,"count":0}],"isBlockCoverage":false},{"functionName":"getLine$1","ranges":[{"startOffset":790896,"endOffset":791616,"count":0}],"isBlockCoverage":false},{"functionName":"_isNearCachedLine$1","ranges":[{"startOffset":791643,"endOffset":792548,"count":0}],"isBlockCoverage":false},{"functionName":"_binarySearch$1","ranges":[{"startOffset":792571,"endOffset":792981,"count":0}],"isBlockCoverage":false},{"functionName":"getColumn$1","ranges":[{"startOffset":793000,"endOffset":793683,"count":0}],"isBlockCoverage":false},{"functionName":"getOffset$2","ranges":[{"startOffset":793702,"endOffset":794481,"count":0}],"isBlockCoverage":false},{"functionName":"getOffset$1","ranges":[{"startOffset":794500,"endOffset":794565,"count":0}],"isBlockCoverage":false},{"functionName":"get$sourceUrl","ranges":[{"startOffset":794621,"endOffset":794667,"count":0}],"isBlockCoverage":false},{"functionName":"get$line","ranges":[{"startOffset":794683,"endOffset":794748,"count":0}],"isBlockCoverage":false},{"functionName":"get$column","ranges":[{"startOffset":794766,"endOffset":794833,"count":0}],"isBlockCoverage":false},{"functionName":"get$offset","ranges":[{"startOffset":794851,"endOffset":794903,"count":0}],"isBlockCoverage":false},{"functionName":"get$sourceUrl","ranges":[{"startOffset":794956,"endOffset":795002,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":795020,"endOffset":795089,"count":0}],"isBlockCoverage":false},{"functionName":"get$start","ranges":[{"startOffset":795106,"endOffset":795185,"count":0}],"isBlockCoverage":false},{"functionName":"get$end","ranges":[{"startOffset":795200,"endOffset":795277,"count":0}],"isBlockCoverage":false},{"functionName":"get$text","ranges":[{"startOffset":795293,"endOffset":795463,"count":0}],"isBlockCoverage":false},{"functionName":"get$context","ranges":[{"startOffset":795482,"endOffset":796567,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":796578,"endOffset":797060,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":797080,"endOffset":797171,"count":0}],"isBlockCoverage":false},{"functionName":"expand$1","ranges":[{"startOffset":797187,"endOffset":797617,"count":0}],"isBlockCoverage":false},{"functionName":"highlight$0","ranges":[{"startOffset":797723,"endOffset":800062,"count":0}],"isBlockCoverage":false},{"functionName":"_writeFirstLine$1","ranges":[{"startOffset":800087,"endOffset":801960,"count":0}],"isBlockCoverage":false},{"functionName":"_writeIntermediateLines$1","ranges":[{"startOffset":801993,"endOffset":802716,"count":0}],"isBlockCoverage":false},{"functionName":"_writeLastLine$1","ranges":[{"startOffset":802740,"endOffset":803867,"count":0}],"isBlockCoverage":false},{"functionName":"_writeTrailingLines$1","ranges":[{"startOffset":803896,"endOffset":804584,"count":0}],"isBlockCoverage":false},{"functionName":"_writeText$1","ranges":[{"startOffset":804604,"endOffset":805084,"count":0}],"isBlockCoverage":false},{"functionName":"_writeSidebar$2$end$line","ranges":[{"startOffset":805116,"endOffset":805243,"count":0}],"isBlockCoverage":false},{"functionName":"_writeSidebar$1$end","ranges":[{"startOffset":805270,"endOffset":805346,"count":0}],"isBlockCoverage":false},{"functionName":"_writeSidebar$1$line","ranges":[{"startOffset":805374,"endOffset":805452,"count":0}],"isBlockCoverage":false},{"functionName":"_writeSidebar$0","ranges":[{"startOffset":805475,"endOffset":805549,"count":0}],"isBlockCoverage":false},{"functionName":"_countTabs$1","ranges":[{"startOffset":805569,"endOffset":805863,"count":0}],"isBlockCoverage":false},{"functionName":"_isOnlyWhitespace$1","ranges":[{"startOffset":805890,"endOffset":806214,"count":0}],"isBlockCoverage":false},{"functionName":"_colorize$2$color","ranges":[{"startOffset":806239,"endOffset":806594,"count":0}],"isBlockCoverage":false},{"functionName":"_colorize$1","ranges":[{"startOffset":806613,"endOffset":806692,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":806764,"endOffset":806982,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":807074,"endOffset":807147,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":807239,"endOffset":807514,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":807606,"endOffset":807796,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":807895,"endOffset":808102,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":808192,"endOffset":808411,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":808502,"endOffset":808715,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":808806,"endOffset":809078,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":809167,"endOffset":809588,"count":0}],"isBlockCoverage":false},{"functionName":"distance$1","ranges":[{"startOffset":809662,"endOffset":809961,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":809972,"endOffset":810183,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":810203,"endOffset":810282,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":810300,"endOffset":810590,"count":0}],"isBlockCoverage":false},{"functionName":"get$sourceUrl","ranges":[{"startOffset":810611,"endOffset":810658,"count":0}],"isBlockCoverage":false},{"functionName":"get$offset","ranges":[{"startOffset":810676,"endOffset":810728,"count":0}],"isBlockCoverage":false},{"functionName":"get$line","ranges":[{"startOffset":810744,"endOffset":810786,"count":0}],"isBlockCoverage":false},{"functionName":"get$column","ranges":[{"startOffset":810804,"endOffset":810848,"count":0}],"isBlockCoverage":false},{"functionName":"distance$1","ranges":[{"startOffset":810908,"endOffset":811205,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":811216,"endOffset":811426,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":811446,"endOffset":811524,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":811542,"endOffset":811946,"count":0}],"isBlockCoverage":false},{"functionName":"SourceSpanBase$3","ranges":[{"startOffset":812064,"endOffset":812766,"count":0}],"isBlockCoverage":false},{"functionName":"get$start","ranges":[{"startOffset":812783,"endOffset":812826,"count":0}],"isBlockCoverage":false},{"functionName":"get$end","ranges":[{"startOffset":812841,"endOffset":812882,"count":0}],"isBlockCoverage":false},{"functionName":"get$text","ranges":[{"startOffset":812898,"endOffset":812940,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":813001,"endOffset":813064,"count":0}],"isBlockCoverage":false},{"functionName":"toString$1$color","ranges":[{"startOffset":813088,"endOffset":813313,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":813331,"endOffset":813411,"count":0}],"isBlockCoverage":false},{"functionName":"get$sourceUrl","ranges":[{"startOffset":813558,"endOffset":813623,"count":0}],"isBlockCoverage":false},{"functionName":"get$length","ranges":[{"startOffset":813641,"endOffset":813799,"count":0}],"isBlockCoverage":false},{"functionName":"message$2$color","ranges":[{"startOffset":813822,"endOffset":814454,"count":0}],"isBlockCoverage":false},{"functionName":"message$1","ranges":[{"startOffset":814471,"endOffset":814568,"count":0}],"isBlockCoverage":false},{"functionName":"highlight$1$color","ranges":[{"startOffset":814593,"endOffset":815709,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":815720,"endOffset":815923,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":815943,"endOffset":816110,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":816128,"endOffset":816349,"count":0}],"isBlockCoverage":false},{"functionName":"get$context","ranges":[{"startOffset":816434,"endOffset":816480,"count":0}],"isBlockCoverage":false},{"functionName":"foldFrames$2$terse","ranges":[{"startOffset":816534,"endOffset":817349,"count":0}],"isBlockCoverage":false},{"functionName":"toTrace$0","ranges":[{"startOffset":817366,"endOffset":817684,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":817702,"endOffset":818222,"count":0}],"isBlockCoverage":false},{"functionName":"get$traces","ranges":[{"startOffset":818262,"endOffset":818306,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":818364,"endOffset":818720,"count":1},{"startOffset":818496,"endOffset":818714,"count":0}],"isBlockCoverage":true},{"functionName":"$signature","ranges":[{"startOffset":818738,"endOffset":818792,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":818856,"endOffset":819515,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":819600,"endOffset":819679,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":819761,"endOffset":819943,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":820026,"endOffset":820116,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":820197,"endOffset":820307,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":820389,"endOffset":820699,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":820777,"endOffset":820853,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":820933,"endOffset":821283,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":821364,"endOffset":821467,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":821546,"endOffset":821837,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":821917,"endOffset":822083,"count":0}],"isBlockCoverage":false},{"functionName":"get$isCore","ranges":[{"startOffset":822149,"endOffset":822214,"count":0}],"isBlockCoverage":false},{"functionName":"get$library","ranges":[{"startOffset":822233,"endOffset":822388,"count":0}],"isBlockCoverage":false},{"functionName":"get$$package","ranges":[{"startOffset":822408,"endOffset":822583,"count":0}],"isBlockCoverage":false},{"functionName":"get$location","ranges":[{"startOffset":822603,"endOffset":822908,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":822926,"endOffset":823016,"count":0}],"isBlockCoverage":false},{"functionName":"get$uri","ranges":[{"startOffset":823031,"endOffset":823072,"count":0}],"isBlockCoverage":false},{"functionName":"get$line","ranges":[{"startOffset":823088,"endOffset":823130,"count":0}],"isBlockCoverage":false},{"functionName":"get$column","ranges":[{"startOffset":823148,"endOffset":823192,"count":0}],"isBlockCoverage":false},{"functionName":"get$member","ranges":[{"startOffset":823210,"endOffset":823254,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":823318,"endOffset":824399,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":824483,"endOffset":825317,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":825415,"endOffset":826447,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":826536,"endOffset":827780,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":827870,"endOffset":829445,"count":0}],"isBlockCoverage":false},{"functionName":"get$_chain","ranges":[{"startOffset":829515,"endOffset":829701,"count":0}],"isBlockCoverage":false},{"functionName":"get$traces","ranges":[{"startOffset":829719,"endOffset":829782,"count":0}],"isBlockCoverage":false},{"functionName":"foldFrames$2$terse","ranges":[{"startOffset":829808,"endOffset":829965,"count":0}],"isBlockCoverage":false},{"functionName":"toTrace$0","ranges":[{"startOffset":829982,"endOffset":830069,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":830087,"endOffset":830153,"count":0}],"isBlockCoverage":false},{"functionName":"set$_lazy_chain$_inner","ranges":[{"startOffset":830183,"endOffset":830267,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":830371,"endOffset":830474,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":830556,"endOffset":830624,"count":0}],"isBlockCoverage":false},{"functionName":"get$_lazy_trace$_trace","ranges":[{"startOffset":830705,"endOffset":830903,"count":0}],"isBlockCoverage":false},{"functionName":"get$frames","ranges":[{"startOffset":830921,"endOffset":830996,"count":0}],"isBlockCoverage":false},{"functionName":"get$original","ranges":[{"startOffset":831016,"endOffset":831093,"count":0}],"isBlockCoverage":false},{"functionName":"foldFrames$2$terse","ranges":[{"startOffset":831119,"endOffset":831276,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":831294,"endOffset":831372,"count":0}],"isBlockCoverage":false},{"functionName":"set$_lazy_trace$_inner","ranges":[{"startOffset":831402,"endOffset":831486,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":831590,"endOffset":831705,"count":0}],"isBlockCoverage":false},{"functionName":"chainFor$1","ranges":[{"startOffset":831787,"endOffset":832653,"count":0}],"isBlockCoverage":false},{"functionName":"_stack_zone_specification$_registerCallback$1$4","ranges":[{"startOffset":832708,"endOffset":833201,"count":1},{"startOffset":832917,"endOffset":832966,"count":0}],"isBlockCoverage":true},{"functionName":"_stack_zone_specification$_registerCallback$4","ranges":[{"startOffset":833254,"endOffset":833402,"count":0}],"isBlockCoverage":false},{"functionName":"_stack_zone_specification$_registerUnaryCallback$2$4","ranges":[{"startOffset":833462,"endOffset":834015,"count":1},{"startOffset":833704,"endOffset":833762,"count":0}],"isBlockCoverage":true},{"functionName":"_stack_zone_specification$_registerUnaryCallback$4","ranges":[{"startOffset":834073,"endOffset":834241,"count":0}],"isBlockCoverage":false},{"functionName":"_stack_zone_specification$_registerBinaryCallback$3$4","ranges":[{"startOffset":834302,"endOffset":834911,"count":1},{"startOffset":834516,"endOffset":834648,"count":0}],"isBlockCoverage":true},{"functionName":"_stack_zone_specification$_registerBinaryCallback$4","ranges":[{"startOffset":834970,"endOffset":835154,"count":0}],"isBlockCoverage":false},{"functionName":"_stack_zone_specification$_errorCallback$5","ranges":[{"startOffset":835204,"endOffset":836108,"count":0}],"isBlockCoverage":false},{"functionName":"_stack_zone_specification$_run$1$2","ranges":[{"startOffset":836150,"endOffset":836761,"count":1},{"startOffset":836415,"endOffset":836692,"count":0}],"isBlockCoverage":true},{"functionName":"_currentTrace$1","ranges":[{"startOffset":836784,"endOffset":836966,"count":1}],"isBlockCoverage":true},{"functionName":"_trimVMChain$1","ranges":[{"startOffset":836988,"endOffset":837222,"count":0}],"isBlockCoverage":false},{"functionName":"set$_currentNode","ranges":[{"startOffset":837246,"endOffset":837336,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":837412,"endOffset":837498,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":837595,"endOffset":837689,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":837793,"endOffset":837926,"count":1}],"isBlockCoverage":true},{"functionName":"$signature","ranges":[{"startOffset":837944,"endOffset":837998,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":838088,"endOffset":838328,"count":1}],"isBlockCoverage":true},{"functionName":"$signature","ranges":[{"startOffset":838346,"endOffset":838433,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":838524,"endOffset":838580,"count":1}],"isBlockCoverage":true},{"functionName":"$signature","ranges":[{"startOffset":838598,"endOffset":838652,"count":1}],"isBlockCoverage":true},{"functionName":"call$2","ranges":[{"startOffset":838743,"endOffset":839016,"count":1}],"isBlockCoverage":true},{"functionName":"$signature","ranges":[{"startOffset":839034,"endOffset":839141,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":839233,"endOffset":839344,"count":1}],"isBlockCoverage":true},{"functionName":"$signature","ranges":[{"startOffset":839362,"endOffset":839416,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":839497,"endOffset":839889,"count":0}],"isBlockCoverage":false},{"functionName":"toChain$0","ranges":[{"startOffset":839953,"endOffset":840253,"count":0}],"isBlockCoverage":false},{"functionName":"foldFrames$2$terse","ranges":[{"startOffset":840307,"endOffset":841859,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":841877,"endOffset":842341,"count":0}],"isBlockCoverage":false},{"functionName":"get$frames","ranges":[{"startOffset":842381,"endOffset":842425,"count":0}],"isBlockCoverage":false},{"functionName":"get$original","ranges":[{"startOffset":842445,"endOffset":842491,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":842555,"endOffset":842867,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":842947,"endOffset":843025,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":843103,"endOffset":843191,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":843269,"endOffset":843376,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":843454,"endOffset":843542,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":843624,"endOffset":843701,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":843783,"endOffset":843871,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":843954,"endOffset":844072,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":844155,"endOffset":844248,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":844332,"endOffset":844425,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":844509,"endOffset":844603,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":844684,"endOffset":845037,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":845119,"endOffset":845519,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":845599,"endOffset":845702,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":845781,"endOffset":846034,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":846108,"endOffset":846153,"count":0}],"isBlockCoverage":false},{"functionName":"get$uri","ranges":[{"startOffset":846185,"endOffset":846226,"count":0}],"isBlockCoverage":false},{"functionName":"get$line","ranges":[{"startOffset":846242,"endOffset":846279,"count":0}],"isBlockCoverage":false},{"functionName":"get$column","ranges":[{"startOffset":846297,"endOffset":846334,"count":0}],"isBlockCoverage":false},{"functionName":"get$isCore","ranges":[{"startOffset":846352,"endOffset":846390,"count":0}],"isBlockCoverage":false},{"functionName":"get$library","ranges":[{"startOffset":846409,"endOffset":846452,"count":0}],"isBlockCoverage":false},{"functionName":"get$$package","ranges":[{"startOffset":846472,"endOffset":846509,"count":0}],"isBlockCoverage":false},{"functionName":"get$location","ranges":[{"startOffset":846529,"endOffset":846572,"count":0}],"isBlockCoverage":false},{"functionName":"get$member","ranges":[{"startOffset":846590,"endOffset":846634,"count":0}],"isBlockCoverage":false},{"functionName":"get$stream","ranges":[{"startOffset":846691,"endOffset":846863,"count":1}],"isBlockCoverage":true},{"functionName":"get$sink","ranges":[{"startOffset":846879,"endOffset":846922,"count":1}],"isBlockCoverage":true},{"functionName":"GuaranteeChannel$3$allowSinkErrors","ranges":[{"startOffset":846964,"endOffset":847401,"count":1}],"isBlockCoverage":true},{"functionName":"_onSinkDisconnected$0","ranges":[{"startOffset":847430,"endOffset":847602,"count":0}],"isBlockCoverage":false},{"functionName":"set$_sink","ranges":[{"startOffset":847619,"endOffset":847714,"count":1}],"isBlockCoverage":true},{"functionName":"set$_streamController","ranges":[{"startOffset":847743,"endOffset":847876,"count":1}],"isBlockCoverage":true},{"functionName":"set$_subscription","ranges":[{"startOffset":847901,"endOffset":848024,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":848085,"endOffset":848387,"count":1},{"startOffset":848177,"endOffset":848184,"count":0}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":848468,"endOffset":848594,"count":0}],"isBlockCoverage":false},{"functionName":"get$done","ranges":[{"startOffset":848666,"endOffset":848725,"count":0}],"isBlockCoverage":false},{"functionName":"add$1","ranges":[{"startOffset":848738,"endOffset":849217,"count":1},{"startOffset":848863,"endOffset":848935,"count":0},{"startOffset":848992,"endOffset":849070,"count":0},{"startOffset":849110,"endOffset":849117,"count":0}],"isBlockCoverage":true},{"functionName":"addError$2","ranges":[{"startOffset":849235,"endOffset":849669,"count":0}],"isBlockCoverage":false},{"functionName":"addError$1","ranges":[{"startOffset":849687,"endOffset":849753,"count":0}],"isBlockCoverage":false},{"functionName":"_addError$2","ranges":[{"startOffset":849772,"endOffset":850246,"count":0}],"isBlockCoverage":false},{"functionName":"_addError$1","ranges":[{"startOffset":850265,"endOffset":850332,"count":0}],"isBlockCoverage":false},{"functionName":"addStream$1","ranges":[{"startOffset":850351,"endOffset":851289,"count":1},{"startOffset":850488,"endOffset":850561,"count":0},{"startOffset":850618,"endOffset":850697,"count":0},{"startOffset":850729,"endOffset":850857,"count":0}],"isBlockCoverage":true},{"functionName":"close$0","ranges":[{"startOffset":851304,"endOffset":851793,"count":0}],"isBlockCoverage":false},{"functionName":"_onStreamDisconnected$0","ranges":[{"startOffset":851824,"endOffset":852220,"count":0}],"isBlockCoverage":false},{"functionName":"set$_addStreamSubscription","ranges":[{"startOffset":852254,"endOffset":852404,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":852558,"endOffset":852577,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":852665,"endOffset":852791,"count":0}],"isBlockCoverage":false},{"functionName":"_MultiChannel$1","ranges":[{"startOffset":852869,"endOffset":853574,"count":1}],"isBlockCoverage":true},{"functionName":"virtualChannel$1","ranges":[{"startOffset":853598,"endOffset":855403,"count":1},{"startOffset":854008,"endOffset":854335,"count":0},{"startOffset":854389,"endOffset":854435,"count":0},{"startOffset":854564,"endOffset":854665,"count":0}],"isBlockCoverage":true},{"functionName":"virtualChannel$0","ranges":[{"startOffset":855427,"endOffset":855487,"count":1}],"isBlockCoverage":true},{"functionName":"_closeChannel$2","ranges":[{"startOffset":855510,"endOffset":855929,"count":0}],"isBlockCoverage":false},{"functionName":"_closeInnerChannel$0","ranges":[{"startOffset":855957,"endOffset":856432,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":856514,"endOffset":856645,"count":1}],"isBlockCoverage":true},{"functionName":"$signature","ranges":[{"startOffset":856663,"endOffset":856718,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":856777,"endOffset":856842,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":856920,"endOffset":857524,"count":1},{"startOffset":857122,"endOffset":857129,"count":0},{"startOffset":857353,"endOffset":857369,"count":0},{"startOffset":857463,"endOffset":857518,"count":0}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":857602,"endOffset":857750,"count":0}],"isBlockCoverage":false},{"functionName":"$signature","ranges":[{"startOffset":857768,"endOffset":857847,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":857920,"endOffset":858103,"count":1}],"isBlockCoverage":true},{"functionName":"$signature","ranges":[{"startOffset":858121,"endOffset":858184,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":858258,"endOffset":858370,"count":0}],"isBlockCoverage":false},{"functionName":"get$stream","ranges":[{"startOffset":858463,"endOffset":858515,"count":0}],"isBlockCoverage":false},{"functionName":"set$_stream_channel_completer$_channel","ranges":[{"startOffset":858606,"endOffset":858735,"count":1}],"isBlockCoverage":true},{"functionName":"get$local","ranges":[{"startOffset":858798,"endOffset":858842,"count":0}],"isBlockCoverage":false},{"functionName":"set$_local","ranges":[{"startOffset":858860,"endOffset":858957,"count":1}],"isBlockCoverage":true},{"functionName":"set$_foreign","ranges":[{"startOffset":858977,"endOffset":859080,"count":1}],"isBlockCoverage":true},{"functionName":"get$stream","ranges":[{"startOffset":859169,"endOffset":859221,"count":1}],"isBlockCoverage":true},{"functionName":"spanFrom$1","ranges":[{"startOffset":859374,"endOffset":859530,"count":0}],"isBlockCoverage":false},{"functionName":"matches$1","ranges":[{"startOffset":859547,"endOffset":859856,"count":0}],"isBlockCoverage":false},{"functionName":"error$3$length$position","ranges":[{"startOffset":859887,"endOffset":860142,"count":0}],"isBlockCoverage":false},{"functionName":"get$lastMatch","ranges":[{"startOffset":860259,"endOffset":860437,"count":0}],"isBlockCoverage":false},{"functionName":"peekChar$0","ranges":[{"startOffset":860455,"endOffset":860647,"count":0}],"isBlockCoverage":false},{"functionName":"scan$1","ranges":[{"startOffset":860661,"endOffset":860895,"count":0}],"isBlockCoverage":false},{"functionName":"expect$2$name","ranges":[{"startOffset":860916,"endOffset":861423,"count":0}],"isBlockCoverage":false},{"functionName":"expect$1","ranges":[{"startOffset":861439,"endOffset":861512,"count":0}],"isBlockCoverage":false},{"functionName":"matches$1","ranges":[{"startOffset":861529,"endOffset":861791,"count":0}],"isBlockCoverage":false},{"functionName":"glyphOrAscii$2","ranges":[{"startOffset":861849,"endOffset":861911,"count":0}],"isBlockCoverage":false},{"functionName":"get$horizontalLine","ranges":[{"startOffset":861937,"endOffset":861973,"count":0}],"isBlockCoverage":false},{"functionName":"get$verticalLine","ranges":[{"startOffset":861997,"endOffset":862033,"count":0}],"isBlockCoverage":false},{"functionName":"get$topLeftCorner","ranges":[{"startOffset":862058,"endOffset":862094,"count":0}],"isBlockCoverage":false},{"functionName":"get$bottomLeftCorner","ranges":[{"startOffset":862122,"endOffset":862158,"count":0}],"isBlockCoverage":false},{"functionName":"get$upEnd","ranges":[{"startOffset":862175,"endOffset":862211,"count":0}],"isBlockCoverage":false},{"functionName":"get$downEnd","ranges":[{"startOffset":862230,"endOffset":862266,"count":0}],"isBlockCoverage":false},{"functionName":"glyphOrAscii$2","ranges":[{"startOffset":862326,"endOffset":862382,"count":0}],"isBlockCoverage":false},{"functionName":"get$horizontalLine","ranges":[{"startOffset":862408,"endOffset":862449,"count":0}],"isBlockCoverage":false},{"functionName":"get$verticalLine","ranges":[{"startOffset":862473,"endOffset":862514,"count":0}],"isBlockCoverage":false},{"functionName":"get$topLeftCorner","ranges":[{"startOffset":862539,"endOffset":862580,"count":0}],"isBlockCoverage":false},{"functionName":"get$bottomLeftCorner","ranges":[{"startOffset":862608,"endOffset":862649,"count":0}],"isBlockCoverage":false},{"functionName":"get$upEnd","ranges":[{"startOffset":862666,"endOffset":862707,"count":0}],"isBlockCoverage":false},{"functionName":"get$downEnd","ranges":[{"startOffset":862726,"endOffset":862767,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":862840,"endOffset":864682,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":863077,"endOffset":864609,"count":1},{"startOffset":863167,"endOffset":863223,"count":0},{"startOffset":863485,"endOffset":863577,"count":0},{"startOffset":863993,"endOffset":864097,"count":0},{"startOffset":864323,"endOffset":864422,"count":0}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":864764,"endOffset":865103,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":865187,"endOffset":865869,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":865953,"endOffset":866183,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":866268,"endOffset":866429,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":866513,"endOffset":866721,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":866796,"endOffset":866858,"count":0}],"isBlockCoverage":false},{"functionName":"test$9$onPlatform$retry$skip$solo$tags$testOn$timeout","ranges":[{"startOffset":866971,"endOffset":867811,"count":1},{"startOffset":867323,"endOffset":867326,"count":0},{"startOffset":867550,"endOffset":867557,"count":0},{"startOffset":867633,"endOffset":867659,"count":0}],"isBlockCoverage":true},{"functionName":"group$9$onPlatform$retry$skip$solo$tags$testOn$timeout","ranges":[{"startOffset":867873,"endOffset":869608,"count":1},{"startOffset":868325,"endOffset":868328,"count":0},{"startOffset":868584,"endOffset":868610,"count":0},{"startOffset":868684,"endOffset":868702,"count":0},{"startOffset":869525,"endOffset":869602,"count":0}],"isBlockCoverage":true},{"functionName":"build$0","ranges":[{"startOffset":869623,"endOffset":870102,"count":1}],"isBlockCoverage":true},{"functionName":"_checkNotBuilt$1","ranges":[{"startOffset":870126,"endOffset":870294,"count":1},{"startOffset":870183,"endOffset":870293,"count":0}],"isBlockCoverage":true},{"functionName":"_runSetUps$0","ranges":[{"startOffset":870314,"endOffset":871575,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":870514,"endOffset":871496,"count":1},{"startOffset":870604,"endOffset":870660,"count":0}],"isBlockCoverage":true},{"functionName":"get$_setUpAll","ranges":[{"startOffset":871596,"endOffset":871633,"count":1}],"isBlockCoverage":true},{"functionName":"get$_tearDownAll","ranges":[{"startOffset":871657,"endOffset":872027,"count":1},{"startOffset":871775,"endOffset":871849,"count":0},{"startOffset":871850,"endOffset":871873,"count":0}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":872085,"endOffset":874867,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":872360,"endOffset":874794,"count":1},{"startOffset":872450,"endOffset":872506,"count":0},{"startOffset":873288,"endOffset":874287,"count":0}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":874945,"endOffset":875120,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":875200,"endOffset":876169,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":875387,"endOffset":876096,"count":1},{"startOffset":875477,"endOffset":875533,"count":0}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":876247,"endOffset":876413,"count":1},{"startOffset":876332,"endOffset":876412,"count":0}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":876491,"endOffset":876827,"count":1},{"startOffset":876626,"endOffset":876669,"count":0},{"startOffset":876670,"endOffset":876812,"count":0}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":876911,"endOffset":876963,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":877049,"endOffset":877288,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":877374,"endOffset":877550,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":877637,"endOffset":879068,"count":0}],"isBlockCoverage":false},{"functionName":"forPlatform$1","ranges":[{"startOffset":879136,"endOffset":879644,"count":1},{"startOffset":879307,"endOffset":879319,"count":0},{"startOffset":879481,"endOffset":879510,"count":0},{"startOffset":879520,"endOffset":879532,"count":0}],"isBlockCoverage":true},{"functionName":"_group$_map$1","ranges":[{"startOffset":879665,"endOffset":880149,"count":1}],"isBlockCoverage":true},{"functionName":"get$name","ranges":[{"startOffset":880187,"endOffset":880237,"count":0}],"isBlockCoverage":false},{"functionName":"get$metadata","ranges":[{"startOffset":880257,"endOffset":880303,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":880365,"endOffset":880437,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":880512,"endOffset":880602,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":880678,"endOffset":880754,"count":1}],"isBlockCoverage":true},{"functionName":"load$2$groups","ranges":[{"startOffset":880858,"endOffset":881479,"count":1}],"isBlockCoverage":true},{"functionName":"forPlatform$1","ranges":[{"startOffset":881500,"endOffset":881799,"count":1},{"startOffset":881648,"endOffset":881660,"count":0}],"isBlockCoverage":true},{"functionName":"get$name","ranges":[{"startOffset":881815,"endOffset":881865,"count":0}],"isBlockCoverage":false},{"functionName":"get$metadata","ranges":[{"startOffset":881885,"endOffset":881931,"count":0}],"isBlockCoverage":false},{"functionName":"get$_outstandingCallbacks","ranges":[{"startOffset":881994,"endOffset":882266,"count":1},{"startOffset":882147,"endOffset":882265,"count":0}],"isBlockCoverage":true},{"functionName":"addOutstandingCallback$0","ranges":[{"startOffset":882298,"endOffset":882562,"count":0}],"isBlockCoverage":false},{"functionName":"waitForOutstandingCallbacks$1","ranges":[{"startOffset":882599,"endOffset":883243,"count":1}],"isBlockCoverage":true},{"functionName":"unclosable$1$1","ranges":[{"startOffset":883265,"endOffset":883512,"count":1}],"isBlockCoverage":true},{"functionName":"heartbeat$0","ranges":[{"startOffset":883531,"endOffset":884164,"count":1},{"startOffset":883729,"endOffset":883736,"count":0},{"startOffset":883989,"endOffset":883996,"count":0}],"isBlockCoverage":true},{"functionName":"_handleError$3","ranges":[{"startOffset":884186,"endOffset":885992,"count":0}],"isBlockCoverage":false},{"functionName":"_handleError$2","ranges":[{"startOffset":886014,"endOffset":886096,"count":0}],"isBlockCoverage":false},{"functionName":"_invoker$_onRun$0","ranges":[{"startOffset":886121,"endOffset":886628,"count":1}],"isBlockCoverage":true},{"functionName":"_runTearDowns$0","ranges":[{"startOffset":886651,"endOffset":888109,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":886875,"endOffset":888027,"count":1},{"startOffset":886965,"endOffset":887021,"count":0},{"startOffset":887385,"endOffset":887694,"count":0},{"startOffset":887707,"endOffset":887841,"count":0}],"isBlockCoverage":true},{"functionName":"call$5","ranges":[{"startOffset":888167,"endOffset":888558,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":888637,"endOffset":888765,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":888865,"endOffset":889886,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":889058,"endOffset":889813,"count":1},{"startOffset":889148,"endOffset":889204,"count":0}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":889986,"endOffset":890094,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":890175,"endOffset":890978,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":891060,"endOffset":891255,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":891337,"endOffset":891638,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":891722,"endOffset":891930,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":892015,"endOffset":892186,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":892264,"endOffset":892515,"count":1},{"startOffset":892445,"endOffset":892477,"count":0}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":892594,"endOffset":893102,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":893182,"endOffset":895232,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":893413,"endOffset":895159,"count":1},{"startOffset":893503,"endOffset":893559,"count":0},{"startOffset":894440,"endOffset":894592,"count":0},{"startOffset":894648,"endOffset":894893,"count":0}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":895313,"endOffset":896507,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":895504,"endOffset":896434,"count":1},{"startOffset":895594,"endOffset":895650,"count":0}],"isBlockCoverage":true},{"functionName":"call$4","ranges":[{"startOffset":896588,"endOffset":896759,"count":0}],"isBlockCoverage":false},{"functionName":"decrement$0","ranges":[{"startOffset":896834,"endOffset":897013,"count":1},{"startOffset":896886,"endOffset":896893,"count":0},{"startOffset":896977,"endOffset":896984,"count":0}],"isBlockCoverage":true},{"functionName":"run$0","ranges":[{"startOffset":897087,"endOffset":897565,"count":0}],"isBlockCoverage":false},{"functionName":"addError$2","ranges":[{"startOffset":897624,"endOffset":897936,"count":0}],"isBlockCoverage":false},{"functionName":"setState$1","ranges":[{"startOffset":897954,"endOffset":898264,"count":1},{"startOffset":898062,"endOffset":898069,"count":0},{"startOffset":898141,"endOffset":898148,"count":0}],"isBlockCoverage":true},{"functionName":"message$1","ranges":[{"startOffset":898281,"endOffset":898470,"count":0}],"isBlockCoverage":false},{"functionName":"_live_test_controller$_run$0","ranges":[{"startOffset":898506,"endOffset":898976,"count":1},{"startOffset":898579,"endOffset":898668,"count":0},{"startOffset":898737,"endOffset":898829,"count":0}],"isBlockCoverage":true},{"functionName":"_live_test_controller$_close$0","ranges":[{"startOffset":899014,"endOffset":899384,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":899464,"endOffset":899507,"count":0}],"isBlockCoverage":false},{"functionName":"_validateTags$0","ranges":[{"startOffset":899561,"endOffset":900156,"count":1},{"startOffset":899966,"endOffset":900155,"count":0}],"isBlockCoverage":true},{"functionName":"validatePlatformSelectors$1","ranges":[{"startOffset":900191,"endOffset":900418,"count":1}],"isBlockCoverage":true},{"functionName":"merge$1","ranges":[{"startOffset":900433,"endOffset":901393,"count":1}],"isBlockCoverage":true},{"functionName":"change$4$onPlatform$skip$skipReason$timeout","ranges":[{"startOffset":901444,"endOffset":902100,"count":0}],"isBlockCoverage":false},{"functionName":"change$1$onPlatform","ranges":[{"startOffset":902127,"endOffset":902248,"count":0}],"isBlockCoverage":false},{"functionName":"change$1$timeout","ranges":[{"startOffset":902272,"endOffset":902387,"count":0}],"isBlockCoverage":false},{"functionName":"change$2$skip$skipReason","ranges":[{"startOffset":902419,"endOffset":902546,"count":0}],"isBlockCoverage":false},{"functionName":"forPlatform$1","ranges":[{"startOffset":902567,"endOffset":902916,"count":1},{"startOffset":902687,"endOffset":902915,"count":0}],"isBlockCoverage":true},{"functionName":"serialize$0","ranges":[{"startOffset":902935,"endOffset":903762,"count":1},{"startOffset":903242,"endOffset":903261,"count":0}],"isBlockCoverage":true},{"functionName":"_serializeTimeout$1","ranges":[{"startOffset":903789,"endOffset":904104,"count":1},{"startOffset":903878,"endOffset":903892,"count":0},{"startOffset":903951,"endOffset":903965,"count":0}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":904170,"endOffset":904437,"count":1}],"isBlockCoverage":true},{"functionName":"call$2","ranges":[{"startOffset":904519,"endOffset":904859,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":904944,"endOffset":905183,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":905270,"endOffset":905391,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":905478,"endOffset":905558,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":905656,"endOffset":905903,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":905982,"endOffset":906116,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":906196,"endOffset":906330,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":906415,"endOffset":906760,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":906843,"endOffset":907050,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":907134,"endOffset":907382,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":907458,"endOffset":907501,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":907566,"endOffset":907676,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":907762,"endOffset":907799,"count":1}],"isBlockCoverage":true},{"functionName":"validate$1","ranges":[{"startOffset":907875,"endOffset":908141,"count":1},{"startOffset":908007,"endOffset":908140,"count":0}],"isBlockCoverage":true},{"functionName":"evaluate$1","ranges":[{"startOffset":908159,"endOffset":908292,"count":1}],"isBlockCoverage":true},{"functionName":"intersection$1","ranges":[{"startOffset":908314,"endOffset":908542,"count":1},{"startOffset":908448,"endOffset":908541,"count":0}],"isBlockCoverage":true},{"functionName":"toString$0","ranges":[{"startOffset":908560,"endOffset":908639,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":908650,"endOffset":908848,"count":0}],"isBlockCoverage":false},{"functionName":"get$hashCode","ranges":[{"startOffset":908868,"endOffset":908949,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":909016,"endOffset":909144,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":909234,"endOffset":909377,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":909467,"endOffset":909603,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":909692,"endOffset":910518,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":910585,"endOffset":910628,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":910700,"endOffset":910802,"count":1}],"isBlockCoverage":true},{"functionName":"configure$3$except$mapper$only","ranges":[{"startOffset":910902,"endOffset":911192,"count":1},{"startOffset":911107,"endOffset":911132,"count":0},{"startOffset":911165,"endOffset":911186,"count":0}],"isBlockCoverage":true},{"functionName":"configure$2$except$only","ranges":[{"startOffset":911223,"endOffset":911323,"count":1}],"isBlockCoverage":true},{"functionName":"configure$1$mapper","ranges":[{"startOffset":911349,"endOffset":911443,"count":1}],"isBlockCoverage":true},{"functionName":"formatStackTrace$2$verbose","ranges":[{"startOffset":911477,"endOffset":912169,"count":0}],"isBlockCoverage":false},{"functionName":"set$_except","ranges":[{"startOffset":912188,"endOffset":912268,"count":0}],"isBlockCoverage":false},{"functionName":"set$_only","ranges":[{"startOffset":912285,"endOffset":912359,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":912440,"endOffset":912670,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":912729,"endOffset":912905,"count":1},{"startOffset":912783,"endOffset":912796,"count":0},{"startOffset":912867,"endOffset":912898,"count":0}],"isBlockCoverage":true},{"functionName":"get$hashCode","ranges":[{"startOffset":912925,"endOffset":913054,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":913072,"endOffset":913383,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":913430,"endOffset":913473,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":913521,"endOffset":913564,"count":0}],"isBlockCoverage":false},{"functionName":"toString$0","ranges":[{"startOffset":913717,"endOffset":913763,"count":0}],"isBlockCoverage":false},{"functionName":"get$message","ranges":[{"startOffset":913782,"endOffset":913835,"count":0}],"isBlockCoverage":false},{"functionName":"call$5","ranges":[{"startOffset":913888,"endOffset":914188,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":914260,"endOffset":914278,"count":1}],"isBlockCoverage":true},{"functionName":"merge$1","ranges":[{"startOffset":914342,"endOffset":915081,"count":1},{"startOffset":914467,"endOffset":914494,"count":0},{"startOffset":914552,"endOffset":914583,"count":0},{"startOffset":914632,"endOffset":914853,"count":0},{"startOffset":914955,"endOffset":914972,"count":0},{"startOffset":915015,"endOffset":915032,"count":0}],"isBlockCoverage":true},{"functionName":"apply$1","ranges":[{"startOffset":915096,"endOffset":915445,"count":1},{"startOffset":915179,"endOffset":915191,"count":0},{"startOffset":915319,"endOffset":915336,"count":0}],"isBlockCoverage":true},{"functionName":"get$hashCode","ranges":[{"startOffset":915465,"endOffset":915577,"count":0}],"isBlockCoverage":false},{"functionName":"$eq","ranges":[{"startOffset":915588,"endOffset":915784,"count":1},{"startOffset":915642,"endOffset":915655,"count":0}],"isBlockCoverage":true},{"functionName":"toString$0","ranges":[{"startOffset":915802,"endOffset":916008,"count":0}],"isBlockCoverage":false},{"functionName":"_serializeGroup$3","ranges":[{"startOffset":916070,"endOffset":917084,"count":1},{"startOffset":916473,"endOffset":916517,"count":0}],"isBlockCoverage":true},{"functionName":"_serializeTest$3","ranges":[{"startOffset":917108,"endOffset":917764,"count":1},{"startOffset":917540,"endOffset":917584,"count":0}],"isBlockCoverage":true},{"functionName":"_runLiveTest$2","ranges":[{"startOffset":917786,"endOffset":918752,"count":1}],"isBlockCoverage":true},{"functionName":"call$4","ranges":[{"startOffset":918817,"endOffset":919145,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":919231,"endOffset":919250,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":919335,"endOffset":919891,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":919976,"endOffset":920289,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":920375,"endOffset":925739,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":920701,"endOffset":925666,"count":1},{"startOffset":920791,"endOffset":920847,"count":0},{"startOffset":921070,"endOffset":921774,"count":0},{"startOffset":921820,"endOffset":922042,"count":0},{"startOffset":922087,"endOffset":922311,"count":0},{"startOffset":923050,"endOffset":923091,"count":0},{"startOffset":923567,"endOffset":923597,"count":0}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":925826,"endOffset":927365,"count":1},{"startOffset":925967,"endOffset":926041,"count":0},{"startOffset":926601,"endOffset":926671,"count":0},{"startOffset":927004,"endOffset":927069,"count":0},{"startOffset":927115,"endOffset":927359,"count":0}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":927453,"endOffset":927588,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":927676,"endOffset":928035,"count":1}],"isBlockCoverage":true},{"functionName":"call$2","ranges":[{"startOffset":928122,"endOffset":928276,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":928370,"endOffset":928663,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":928757,"endOffset":929103,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":929194,"endOffset":929380,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":929472,"endOffset":929733,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":929826,"endOffset":930378,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":930471,"endOffset":930825,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":930918,"endOffset":931101,"count":1}],"isBlockCoverage":true},{"functionName":"call$1","ranges":[{"startOffset":931193,"endOffset":931352,"count":1}],"isBlockCoverage":true},{"functionName":"connectOut$1","ranges":[{"startOffset":931434,"endOffset":932439,"count":1},{"startOffset":931560,"endOffset":931587,"count":0},{"startOffset":931674,"endOffset":931767,"count":0}],"isBlockCoverage":true},{"functionName":"get$length","ranges":[{"startOffset":932491,"endOffset":932603,"count":0}],"isBlockCoverage":false},{"functionName":"get$iterator","ranges":[{"startOffset":932623,"endOffset":932784,"count":0}],"isBlockCoverage":false},{"functionName":"toSet$0","ranges":[{"startOffset":932799,"endOffset":932888,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":933051,"endOffset":933169,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":933252,"endOffset":933441,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":933506,"endOffset":933888,"count":0}],"isBlockCoverage":false},{"functionName":"get$_onUnpaused","ranges":[{"startOffset":933961,"endOffset":934099,"count":0}],"isBlockCoverage":false},{"functionName":"get$success","ranges":[{"startOffset":934118,"endOffset":935569,"count":0}],"isBlockCoverage":false},{"functionName":"get$liveTests","ranges":[{"startOffset":935590,"endOffset":936069,"count":0}],"isBlockCoverage":false},{"functionName":"Engine$3$concurrency$coverage$maxSuites","ranges":[{"startOffset":936116,"endOffset":936304,"count":0}],"isBlockCoverage":false},{"functionName":"run$0","ranges":[{"startOffset":936317,"endOffset":936943,"count":0}],"isBlockCoverage":false},{"functionName":"_runGroup$3","ranges":[{"startOffset":936962,"endOffset":937125,"count":0}],"isBlockCoverage":false},{"functionName":"_runGroup$body$Engine","ranges":[{"startOffset":937154,"endOffset":945098,"count":0}],"isBlockCoverage":false},{"functionName":"_engine$_runLiveTest$3$countSuccess","ranges":[{"startOffset":945141,"endOffset":945283,"count":0}],"isBlockCoverage":false},{"functionName":"_engine$_runLiveTest$2","ranges":[{"startOffset":945313,"endOffset":945444,"count":0}],"isBlockCoverage":false},{"functionName":"_runLiveTest$body$Engine","ranges":[{"startOffset":945476,"endOffset":948266,"count":0}],"isBlockCoverage":false},{"functionName":"_runSkippedTest$3","ranges":[{"startOffset":948291,"endOffset":948443,"count":0}],"isBlockCoverage":false},{"functionName":"_runSkippedTest$body$Engine","ranges":[{"startOffset":948478,"endOffset":950257,"count":0}],"isBlockCoverage":false},{"functionName":"_addLiveSuite$1","ranges":[{"startOffset":950280,"endOffset":951177,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":951236,"endOffset":951499,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":951570,"endOffset":951828,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":951900,"endOffset":951919,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":951993,"endOffset":952254,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":952330,"endOffset":952400,"count":0}],"isBlockCoverage":false},{"functionName":"$call$body$Engine_run__closure","ranges":[{"startOffset":952438,"endOffset":953809,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":953885,"endOffset":955623,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":955700,"endOffset":955766,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":955842,"endOffset":956062,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":956145,"endOffset":956558,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":956643,"endOffset":956740,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":956824,"endOffset":956842,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":956928,"endOffset":956946,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":957033,"endOffset":957502,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":957589,"endOffset":957607,"count":0}],"isBlockCoverage":false},{"functionName":"LiveSuiteController$1","ranges":[{"startOffset":957758,"endOffset":958027,"count":0}],"isBlockCoverage":false},{"functionName":"reportLiveTest$2$countSuccess","ranges":[{"startOffset":958064,"endOffset":958889,"count":0}],"isBlockCoverage":false},{"functionName":"close$0","ranges":[{"startOffset":958904,"endOffset":959033,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":959097,"endOffset":959152,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":959237,"endOffset":959256,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":959354,"endOffset":959967,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":960057,"endOffset":961699,"count":0}],"isBlockCoverage":false},{"functionName":"_onTestStarted$1","ranges":[{"startOffset":961781,"endOffset":963251,"count":0}],"isBlockCoverage":false},{"functionName":"_onStateChange$2","ranges":[{"startOffset":963275,"endOffset":963683,"count":0}],"isBlockCoverage":false},{"functionName":"_expanded$_onError$3","ranges":[{"startOffset":963711,"endOffset":964186,"count":0}],"isBlockCoverage":false},{"functionName":"_expanded$_onDone$1","ranges":[{"startOffset":964213,"endOffset":965237,"count":0}],"isBlockCoverage":false},{"functionName":"_progressLine$3$color$suffix","ranges":[{"startOffset":965273,"endOffset":967686,"count":0}],"isBlockCoverage":false},{"functionName":"_progressLine$2$suffix","ranges":[{"startOffset":967716,"endOffset":967820,"count":0}],"isBlockCoverage":false},{"functionName":"_progressLine$2$color","ranges":[{"startOffset":967849,"endOffset":967951,"count":0}],"isBlockCoverage":false},{"functionName":"_progressLine$1","ranges":[{"startOffset":967974,"endOffset":968068,"count":0}],"isBlockCoverage":false},{"functionName":"_description$1","ranges":[{"startOffset":968090,"endOffset":968203,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":968279,"endOffset":968386,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":968484,"endOffset":968637,"count":0}],"isBlockCoverage":false},{"functionName":"call$1","ranges":[{"startOffset":968735,"endOffset":969071,"count":0}],"isBlockCoverage":false},{"functionName":"_runner_suite$_close$0","ranges":[{"startOffset":969197,"endOffset":969305,"count":0}],"isBlockCoverage":false},{"functionName":"set$_runner_suite$_suite","ranges":[{"startOffset":969337,"endOffset":969408,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":969481,"endOffset":970301,"count":0}],"isBlockCoverage":false},{"functionName":"writeln$1","ranges":[{"startOffset":970445,"endOffset":970545,"count":0}],"isBlockCoverage":false},{"functionName":"_flush$0","ranges":[{"startOffset":970561,"endOffset":970743,"count":0}],"isBlockCoverage":false},{"functionName":"call$2","ranges":[{"startOffset":970896,"endOffset":971053,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":971128,"endOffset":974564,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":974638,"endOffset":974728,"count":0}],"isBlockCoverage":false},{"functionName":"call$0","ranges":[{"startOffset":974798,"endOffset":974868,"count":1}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":974937,"endOffset":975688,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":975109,"endOffset":975615,"count":1},{"startOffset":975199,"endOffset":975255,"count":0},{"startOffset":975440,"endOffset":975452,"count":0}],"isBlockCoverage":true},{"functionName":"call$0","ranges":[{"startOffset":975756,"endOffset":975816,"count":1}],"isBlockCoverage":true},{"functionName":"aliases","ranges":[{"startOffset":975846,"endOffset":976773,"count":1}],"isBlockCoverage":true},{"functionName":"installTearOffs","ranges":[{"startOffset":976781,"endOffset":984996,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":978155,"endOffset":978225,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":978518,"endOffset":978624,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":978734,"endOffset":978870,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":979096,"endOffset":979215,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":979350,"endOffset":979489,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":979626,"endOffset":979781,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":984923,"endOffset":984982,"count":0}],"isBlockCoverage":false},{"functionName":"inheritance","ranges":[{"startOffset":985004,"endOffset":1007745,"count":1}],"isBlockCoverage":true},{"functionName":"rtii","ranges":[{"startOffset":1029633,"endOffset":1042848,"count":1},{"startOffset":1042844,"endOffset":1042847,"count":0}],"isBlockCoverage":true},{"functionName":"constants","ranges":[{"startOffset":1042856,"endOffset":1058765,"count":1}],"isBlockCoverage":true},{"functionName":"getTagFallback","ranges":[{"startOffset":1044143,"endOffset":1044257,"count":0}],"isBlockCoverage":false},{"functionName":"C.C_JS_CONST0","ranges":[{"startOffset":1044279,"endOffset":1045394,"count":1},{"startOffset":1045302,"endOffset":1045317,"count":0}],"isBlockCoverage":true},{"functionName":"getTag","ranges":[{"startOffset":1044346,"endOffset":1044449,"count":0}],"isBlockCoverage":false},{"functionName":"getUnknownTag","ranges":[{"startOffset":1044452,"endOffset":1044669,"count":0}],"isBlockCoverage":false},{"functionName":"getUnknownTagGenericBrowser","ranges":[{"startOffset":1044672,"endOffset":1044847,"count":0}],"isBlockCoverage":false},{"functionName":"prototypeForTag","ranges":[{"startOffset":1044850,"endOffset":1045116,"count":1},{"startOffset":1044920,"endOffset":1044932,"count":0},{"startOffset":1045066,"endOffset":1045078,"count":0}],"isBlockCoverage":true},{"functionName":"discriminator","ranges":[{"startOffset":1045119,"endOffset":1045163,"count":0}],"isBlockCoverage":false},{"functionName":"C.C_JS_CONST6","ranges":[{"startOffset":1045416,"endOffset":1045880,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1045452,"endOffset":1045877,"count":1},{"startOffset":1045508,"endOffset":1045521,"count":0},{"startOffset":1045599,"endOffset":1045612,"count":0},{"startOffset":1045838,"endOffset":1045876,"count":0}],"isBlockCoverage":true},{"functionName":"confirm","ranges":[{"startOffset":1045656,"endOffset":1045763,"count":1}],"isBlockCoverage":true},{"functionName":"C.C_JS_CONST1","ranges":[{"startOffset":1045902,"endOffset":1046051,"count":1},{"startOffset":1045989,"endOffset":1046050,"count":0}],"isBlockCoverage":true},{"functionName":"C.C_JS_CONST2","ranges":[{"startOffset":1046073,"endOffset":1046546,"count":1}],"isBlockCoverage":true},{"functionName":"getTagFixed","ranges":[{"startOffset":1046169,"endOffset":1046350,"count":0}],"isBlockCoverage":false},{"functionName":"prototypeForTagFixed","ranges":[{"startOffset":1046353,"endOffset":1046466,"count":1},{"startOffset":1046417,"endOffset":1046429,"count":0}],"isBlockCoverage":true},{"functionName":"C.C_JS_CONST5","ranges":[{"startOffset":1046568,"endOffset":1047098,"count":1},{"startOffset":1046655,"endOffset":1046659,"count":0},{"startOffset":1046716,"endOffset":1047097,"count":0}],"isBlockCoverage":true},{"functionName":"getTagFirefox","ranges":[{"startOffset":1046975,"endOffset":1047064,"count":0}],"isBlockCoverage":false},{"functionName":"C.C_JS_CONST4","ranges":[{"startOffset":1047120,"endOffset":1048002,"count":1},{"startOffset":1047207,"endOffset":1047211,"count":0},{"startOffset":1047269,"endOffset":1048001,"count":0}],"isBlockCoverage":true},{"functionName":"getTagIE","ranges":[{"startOffset":1047534,"endOffset":1047777,"count":0}],"isBlockCoverage":false},{"functionName":"prototypeForTagIE","ranges":[{"startOffset":1047780,"endOffset":1047928,"count":0}],"isBlockCoverage":false},{"functionName":"C.C_JS_CONST3","ranges":[{"startOffset":1048024,"endOffset":1048057,"count":1}],"isBlockCoverage":true},{"functionName":"staticFields","ranges":[{"startOffset":1058773,"endOffset":1059835,"count":1}],"isBlockCoverage":true},{"functionName":"lazyInitializers","ranges":[{"startOffset":1059843,"endOffset":1071865,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1059985,"endOffset":1060063,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1060144,"endOffset":1060213,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1060314,"endOffset":1060502,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1060599,"endOffset":1060802,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1060895,"endOffset":1061006,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1061113,"endOffset":1061364,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1061467,"endOffset":1061580,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1061697,"endOffset":1061952,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1062053,"endOffset":1062168,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1062283,"endOffset":1062472,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1062583,"endOffset":1062700,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1062825,"endOffset":1063018,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1063117,"endOffset":1063192,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1063257,"endOffset":1063342,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1063407,"endOffset":1063495,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1063564,"endOffset":1063625,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1063716,"endOffset":1064340,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1064411,"endOffset":1064569,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1064640,"endOffset":1064721,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1064794,"endOffset":1064854,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1064911,"endOffset":1064961,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1065054,"endOffset":1065143,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1065214,"endOffset":1065295,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1065367,"endOffset":1065450,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1065513,"endOffset":1065593,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1065648,"endOffset":1065830,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1065873,"endOffset":1065947,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1065982,"endOffset":1066052,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1066095,"endOffset":1066172,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1066223,"endOffset":1066364,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1066419,"endOffset":1066666,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1066713,"endOffset":1066941,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1066998,"endOffset":1067058,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1067101,"endOffset":1067158,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1067205,"endOffset":1067275,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1067322,"endOffset":1067389,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1067434,"endOffset":1067481,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1067526,"endOffset":1067631,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1067676,"endOffset":1067794,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1067851,"endOffset":1067937,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1067996,"endOffset":1068106,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1068173,"endOffset":1068312,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1068369,"endOffset":1068474,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1068523,"endOffset":1068622,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1068673,"endOffset":1068736,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1068797,"endOffset":1068883,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1068952,"endOffset":1069039,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1069134,"endOffset":1069181,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1069234,"endOffset":1069315,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1069360,"endOffset":1069430,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1069483,"endOffset":1069550,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1069617,"endOffset":1069721,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1069778,"endOffset":1069882,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1069939,"endOffset":1070078,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1070155,"endOffset":1070594,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1070646,"endOffset":1070693,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1070745,"endOffset":1070792,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1070849,"endOffset":1070907,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1070979,"endOffset":1071062,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1071147,"endOffset":1071254,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1071331,"endOffset":1071859,"count":0}],"isBlockCoverage":false},{"functionName":"nativeSupport","ranges":[{"startOffset":1071873,"endOffset":1079153,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1071905,"endOffset":1072690,"count":1},{"startOffset":1072593,"endOffset":1072689,"count":0}],"isBlockCoverage":true},{"functionName":"intern","ranges":[{"startOffset":1071937,"endOffset":1072063,"count":1}],"isBlockCoverage":true},{"functionName":"init.getIsolateTag","ranges":[{"startOffset":1072092,"endOffset":1072176,"count":1}],"isBlockCoverage":true},{"functionName":"Function.call$0","ranges":[{"startOffset":1079188,"endOffset":1079223,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$1","ranges":[{"startOffset":1079255,"endOffset":1079292,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$2","ranges":[{"startOffset":1079324,"endOffset":1079367,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$3$3","ranges":[{"startOffset":1079401,"endOffset":1079450,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$2$2","ranges":[{"startOffset":1079484,"endOffset":1079527,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$1$1","ranges":[{"startOffset":1079561,"endOffset":1079598,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$2$1","ranges":[{"startOffset":1079632,"endOffset":1079669,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$3","ranges":[{"startOffset":1079701,"endOffset":1079750,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$4","ranges":[{"startOffset":1079782,"endOffset":1079837,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$3$1","ranges":[{"startOffset":1079871,"endOffset":1079908,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$2$3","ranges":[{"startOffset":1079942,"endOffset":1079991,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$1$2","ranges":[{"startOffset":1080025,"endOffset":1080068,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$5","ranges":[{"startOffset":1080100,"endOffset":1080161,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$3$4","ranges":[{"startOffset":1080195,"endOffset":1080250,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$2$4","ranges":[{"startOffset":1080284,"endOffset":1080339,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$1$4","ranges":[{"startOffset":1080373,"endOffset":1080428,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$3$6","ranges":[{"startOffset":1080462,"endOffset":1080529,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$2$5","ranges":[{"startOffset":1080563,"endOffset":1080624,"count":0}],"isBlockCoverage":false},{"functionName":"Function.call$2$0","ranges":[{"startOffset":1080658,"endOffset":1080693,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1080759,"endOffset":1081298,"count":1},{"startOffset":1080821,"endOffset":1080919,"count":0},{"startOffset":1080974,"endOffset":1081297,"count":0}],"isBlockCoverage":true},{"functionName":"onLoad","ranges":[{"startOffset":1081021,"endOffset":1081191,"count":0}],"isBlockCoverage":false},{"functionName":"","ranges":[{"startOffset":1081300,"endOffset":1081476,"count":1},{"startOffset":1081418,"endOffset":1081445,"count":0}],"isBlockCoverage":true}]},{"scriptId":"32","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":284,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":283,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_startsWith$20","ranges":[{"startOffset":82,"endOffset":281,"count":0}],"isBlockCoverage":false}]},{"scriptId":"33","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":271,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":270,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__onPause$01","ranges":[{"startOffset":82,"endOffset":268,"count":0}],"isBlockCoverage":false}]},{"scriptId":"34","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":272,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":271,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__onResume$02","ranges":[{"startOffset":82,"endOffset":269,"count":0}],"isBlockCoverage":false}]},{"scriptId":"35","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":277,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":276,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_add$13","ranges":[{"startOffset":82,"endOffset":274,"count":0}],"isBlockCoverage":false}]},{"scriptId":"36","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":271,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":270,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_addError$24","ranges":[{"startOffset":82,"endOffset":268,"count":0}],"isBlockCoverage":false}]},{"scriptId":"37","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":271,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":270,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_complete$15","ranges":[{"startOffset":82,"endOffset":268,"count":1}],"isBlockCoverage":true}]},{"scriptId":"38","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":271,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":270,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_complete$16","ranges":[{"startOffset":82,"endOffset":268,"count":1}],"isBlockCoverage":true}]},{"scriptId":"39","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":277,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":276,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__completeError$27","ranges":[{"startOffset":82,"endOffset":274,"count":1}],"isBlockCoverage":true}]},{"scriptId":"40","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":277,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":276,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_add$18","ranges":[{"startOffset":82,"endOffset":274,"count":1}],"isBlockCoverage":true}]},{"scriptId":"41","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":271,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":270,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_addError$29","ranges":[{"startOffset":82,"endOffset":268,"count":1}],"isBlockCoverage":true}]},{"scriptId":"42","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":280,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":279,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_close$010","ranges":[{"startOffset":82,"endOffset":277,"count":1}],"isBlockCoverage":true}]},{"scriptId":"43","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":268,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":267,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__add$111","ranges":[{"startOffset":82,"endOffset":265,"count":1}],"isBlockCoverage":true}]},{"scriptId":"44","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":280,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":279,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__async$_addError$212","ranges":[{"startOffset":82,"endOffset":277,"count":1}],"isBlockCoverage":true}]},{"scriptId":"45","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":270,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":269,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__close$013","ranges":[{"startOffset":82,"endOffset":267,"count":1}],"isBlockCoverage":true}]},{"scriptId":"46","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":272,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":271,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__onPause$014","ranges":[{"startOffset":82,"endOffset":269,"count":0}],"isBlockCoverage":false}]},{"scriptId":"47","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":273,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":272,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__onResume$015","ranges":[{"startOffset":82,"endOffset":270,"count":1}],"isBlockCoverage":true}]},{"scriptId":"48","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":278,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":277,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_add$116","ranges":[{"startOffset":82,"endOffset":275,"count":1}],"isBlockCoverage":true}]},{"scriptId":"49","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":272,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":271,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__onPause$017","ranges":[{"startOffset":82,"endOffset":269,"count":0}],"isBlockCoverage":false}]},{"scriptId":"50","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":273,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":272,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__onResume$018","ranges":[{"startOffset":82,"endOffset":270,"count":0}],"isBlockCoverage":false}]},{"scriptId":"51","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":273,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":272,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__sendDone$019","ranges":[{"startOffset":82,"endOffset":270,"count":0}],"isBlockCoverage":false}]},{"scriptId":"52","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":283,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":282,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_contains$120","ranges":[{"startOffset":82,"endOffset":280,"count":0}],"isBlockCoverage":false}]},{"scriptId":"53","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":280,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":279,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_close$021","ranges":[{"startOffset":82,"endOffset":277,"count":0}],"isBlockCoverage":false}]},{"scriptId":"54","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":273,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":272,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__onListen$022","ranges":[{"startOffset":82,"endOffset":270,"count":0}],"isBlockCoverage":false}]},{"scriptId":"55","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":282,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":281,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__onCancelBroadcast$023","ranges":[{"startOffset":82,"endOffset":279,"count":0}],"isBlockCoverage":false}]},{"scriptId":"56","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":283,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":282,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_contains$124","ranges":[{"startOffset":82,"endOffset":280,"count":0}],"isBlockCoverage":false}]},{"scriptId":"57","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":279,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":278,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__recursiveMatch$425","ranges":[{"startOffset":82,"endOffset":276,"count":0}],"isBlockCoverage":false}]},{"scriptId":"58","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":288,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":287,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_message$2$color26","ranges":[{"startOffset":82,"endOffset":285,"count":0}],"isBlockCoverage":false}]},{"scriptId":"59","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":309,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":308,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__stack_zone_specification$_registerCallback$1$427","ranges":[{"startOffset":82,"endOffset":306,"count":1}],"isBlockCoverage":true}]},{"scriptId":"60","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":314,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":313,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__stack_zone_specification$_registerUnaryCallback$2$428","ranges":[{"startOffset":82,"endOffset":311,"count":1}],"isBlockCoverage":true}]},{"scriptId":"61","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":315,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":314,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__stack_zone_specification$_registerBinaryCallback$3$429","ranges":[{"startOffset":82,"endOffset":312,"count":1}],"isBlockCoverage":true}]},{"scriptId":"62","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":304,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":303,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__stack_zone_specification$_errorCallback$530","ranges":[{"startOffset":82,"endOffset":301,"count":1}],"isBlockCoverage":true}]},{"scriptId":"63","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":272,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":271,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_addError$231","ranges":[{"startOffset":82,"endOffset":269,"count":1}],"isBlockCoverage":true}]},{"scriptId":"64","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":273,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":272,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__addError$232","ranges":[{"startOffset":82,"endOffset":270,"count":1}],"isBlockCoverage":true}]},{"scriptId":"65","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":280,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":279,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_close$033","ranges":[{"startOffset":82,"endOffset":277,"count":0}],"isBlockCoverage":false}]},{"scriptId":"66","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":282,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":281,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__closeInnerChannel$034","ranges":[{"startOffset":82,"endOffset":279,"count":1}],"isBlockCoverage":true}]},{"scriptId":"67","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":279,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":278,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__invoker$_onRun$035","ranges":[{"startOffset":82,"endOffset":276,"count":1}],"isBlockCoverage":true}]},{"scriptId":"68","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":277,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":276,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__runTearDowns$036","ranges":[{"startOffset":82,"endOffset":274,"count":1}],"isBlockCoverage":true}]},{"scriptId":"69","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":267,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":266,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_run$037","ranges":[{"startOffset":82,"endOffset":264,"count":0}],"isBlockCoverage":false}]},{"scriptId":"70","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":282,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":281,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_message$138","ranges":[{"startOffset":82,"endOffset":279,"count":0}],"isBlockCoverage":false}]},{"scriptId":"71","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":267,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":266,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff_run$039","ranges":[{"startOffset":82,"endOffset":264,"count":0}],"isBlockCoverage":false}]},{"scriptId":"72","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":278,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":277,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__onTestStarted$140","ranges":[{"startOffset":82,"endOffset":275,"count":0}],"isBlockCoverage":false}]},{"scriptId":"73","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":281,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":280,"count":1}],"isBlockCoverage":true},{"functionName":"tearOff__expanded$_onDone$141","ranges":[{"startOffset":82,"endOffset":278,"count":0}],"isBlockCoverage":false}]},{"scriptId":"74","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":62,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":61,"count":1}],"isBlockCoverage":true}]},{"scriptId":"75","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":92,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":91,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":89,"count":1},{"startOffset":87,"endOffset":88,"count":0}],"isBlockCoverage":true}]},{"scriptId":"76","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":62,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":61,"count":1}],"isBlockCoverage":true}]},{"scriptId":"77","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":86,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":85,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":83,"count":0}],"isBlockCoverage":false}]},{"scriptId":"78","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":62,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":61,"count":1}],"isBlockCoverage":true}]},{"scriptId":"79","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":106,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":105,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":103,"count":0}],"isBlockCoverage":false}]},{"scriptId":"80","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":62,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":61,"count":1}],"isBlockCoverage":true}]},{"scriptId":"81","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":86,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":85,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":83,"count":0}],"isBlockCoverage":false}]},{"scriptId":"82","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":62,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":61,"count":1}],"isBlockCoverage":true}]},{"scriptId":"83","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":92,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":91,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":89,"count":0}],"isBlockCoverage":false}]},{"scriptId":"84","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":64,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":63,"count":1}],"isBlockCoverage":true}]},{"scriptId":"85","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":93,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":92,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":90,"count":1},{"startOffset":87,"endOffset":89,"count":0}],"isBlockCoverage":true}]},{"scriptId":"86","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":64,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":63,"count":1}],"isBlockCoverage":true}]},{"scriptId":"87","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":84,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":83,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":81,"count":0}],"isBlockCoverage":false}]},{"scriptId":"88","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":64,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":63,"count":1}],"isBlockCoverage":true}]},{"scriptId":"89","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":89,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":88,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":86,"count":0}],"isBlockCoverage":false}]},{"scriptId":"90","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":64,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":63,"count":1}],"isBlockCoverage":true}]},{"scriptId":"91","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":99,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":98,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":96,"count":1}],"isBlockCoverage":true}]},{"scriptId":"92","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":64,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":63,"count":1}],"isBlockCoverage":true}]},{"scriptId":"93","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":96,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":95,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":93,"count":0}],"isBlockCoverage":false}]},{"scriptId":"94","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":64,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":63,"count":1}],"isBlockCoverage":true}]},{"scriptId":"95","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":80,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":79,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":77,"count":1}],"isBlockCoverage":true}]},{"scriptId":"96","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":64,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":63,"count":1}],"isBlockCoverage":true}]},{"scriptId":"97","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":96,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":95,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":93,"count":0}],"isBlockCoverage":false}]},{"scriptId":"98","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":64,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":63,"count":1}],"isBlockCoverage":true}]},{"scriptId":"99","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":91,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":90,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":88,"count":1},{"startOffset":85,"endOffset":87,"count":0}],"isBlockCoverage":true}]},{"scriptId":"100","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":64,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":63,"count":1}],"isBlockCoverage":true}]},{"scriptId":"101","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":105,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":104,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":102,"count":1}],"isBlockCoverage":true}]},{"scriptId":"102","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":64,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":63,"count":1}],"isBlockCoverage":true}]},{"scriptId":"103","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":84,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":83,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":81,"count":0}],"isBlockCoverage":false}]},{"scriptId":"104","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":64,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":63,"count":1}],"isBlockCoverage":true}]},{"scriptId":"105","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":132,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":131,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":129,"count":0}],"isBlockCoverage":false}]},{"scriptId":"106","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":64,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":63,"count":1}],"isBlockCoverage":true}]},{"scriptId":"107","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":151,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":150,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":148,"count":1}],"isBlockCoverage":true}]},{"scriptId":"108","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":64,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":63,"count":1}],"isBlockCoverage":true}]},{"scriptId":"109","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":137,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":136,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":134,"count":1}],"isBlockCoverage":true}]},{"scriptId":"110","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":64,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":63,"count":1}],"isBlockCoverage":true}]},{"scriptId":"111","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":146,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":145,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":143,"count":1}],"isBlockCoverage":true}]},{"scriptId":"112","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":64,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":63,"count":1}],"isBlockCoverage":true}]},{"scriptId":"113","url":"","functions":[{"functionName":"","ranges":[{"startOffset":0,"endOffset":103,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":1,"endOffset":102,"count":1}],"isBlockCoverage":true},{"functionName":"","ranges":[{"startOffset":32,"endOffset":100,"count":1}],"isBlockCoverage":true}]}]
\ No newline at end of file
diff --git a/pkgs/coverage/test/test_files/function_coverage_app.dart b/pkgs/coverage/test/test_files/function_coverage_app.dart
new file mode 100644
index 0000000..c4868f9
--- /dev/null
+++ b/pkgs/coverage/test/test_files/function_coverage_app.dart
@@ -0,0 +1,58 @@
+// Copyright (c) 2022, 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.
+
+import 'test_library.dart';
+
+int normalFunction() {
+  return 123;
+}
+
+abstract class BaseClass {
+  int abstractMethod();
+}
+
+class SomeClass extends BaseClass {
+  SomeClass() : x = 123;
+
+  // Creates an implicit getter and setter that should be ignored.
+  int x;
+
+  int normalMethod() {
+    return 123;
+  }
+
+  static int staticMethod() {
+    return 123;
+  }
+
+  @override
+  int abstractMethod() {
+    return 123;
+  }
+}
+
+extension SomeExtension on SomeClass {
+  int extensionMethod() {
+    return 123;
+  }
+}
+
+class OtherClass {
+  int otherMethod() {
+    return 123;
+  }
+}
+
+void main() {
+  print(normalFunction());
+  print(SomeClass().normalMethod());
+  print(SomeClass.staticMethod());
+  print(SomeClass().extensionMethod());
+  print(SomeClass().abstractMethod());
+  print(OtherClass().otherMethod());
+  print(libraryFunction());
+  print(otherLibraryFunction());
+}
+
+// ignore_for_file: unreachable_from_main
diff --git a/pkgs/coverage/test/test_files/main_test.js b/pkgs/coverage/test/test_files/main_test.js
new file mode 100644
index 0000000..4c4fb3e
--- /dev/null
+++ b/pkgs/coverage/test/test_files/main_test.js
@@ -0,0 +1,26570 @@
+// Generated by dart2js (fast startup emitter, strong), the Dart to JavaScript compiler version: 2.8.0-292505767.
+// The code supports the following hooks:
+// dartPrint(message):
+//    if this function is defined it is called instead of the Dart [print]
+//    method.
+//
+// dartMainRunner(main, args):
+//    if this function is defined, the Dart [main] method will not be invoked
+//    directly. Instead, a closure that will invoke [main], and its arguments
+//    [args] is passed to [dartMainRunner].
+//
+// dartDeferredLibraryLoader(uri, successCallback, errorCallback):
+//    if this function is defined, it will be called when a deferred library
+//    is loaded. It should load and eval the javascript of `uri`, and call
+//    successCallback. If it fails to do so, it should call errorCallback with
+//    an error.
+//
+// dartCallInstrumentation(id, qualifiedName):
+//    if this function is defined, it will be called at each entry of a
+//    method or constructor. Used only when compiling programs with
+//    --experiment-call-instrumentation.
+(function dartProgram() {
+  function copyProperties(from, to) {
+    var keys = Object.keys(from);
+    for (var i = 0; i < keys.length; i++) {
+      var key = keys[i];
+      to[key] = from[key];
+    }
+  }
+  var supportsDirectProtoAccess = function() {
+    var cls = function() {
+    };
+    cls.prototype = {p: {}};
+    var object = new cls();
+    if (!(object.__proto__ && object.__proto__.p === cls.prototype.p))
+      return false;
+    try {
+      if (typeof navigator != "undefined" && typeof navigator.userAgent == "string" && navigator.userAgent.indexOf("Chrome/") >= 0)
+        return true;
+      if (typeof version == "function" && version.length == 0) {
+        var v = version();
+        if (/^\d+\.\d+\.\d+\.\d+$/.test(v))
+          return true;
+      }
+    } catch (_) {
+    }
+    return false;
+  }();
+  function setFunctionNamesIfNecessary(holders) {
+    function t() {
+    }
+    ;
+    if (typeof t.name == "string")
+      return;
+    for (var i = 0; i < holders.length; i++) {
+      var holder = holders[i];
+      var keys = Object.keys(holder);
+      for (var j = 0; j < keys.length; j++) {
+        var key = keys[j];
+        var f = holder[key];
+        if (typeof f == 'function')
+          f.name = key;
+      }
+    }
+  }
+  function inherit(cls, sup) {
+    cls.prototype.constructor = cls;
+    cls.prototype["$is" + cls.name] = cls;
+    if (sup != null) {
+      if (supportsDirectProtoAccess) {
+        cls.prototype.__proto__ = sup.prototype;
+        return;
+      }
+      var clsPrototype = Object.create(sup.prototype);
+      copyProperties(cls.prototype, clsPrototype);
+      cls.prototype = clsPrototype;
+    }
+  }
+  function inheritMany(sup, classes) {
+    for (var i = 0; i < classes.length; i++)
+      inherit(classes[i], sup);
+  }
+  function mixin(cls, mixin) {
+    copyProperties(mixin.prototype, cls.prototype);
+    cls.prototype.constructor = cls;
+  }
+  function lazy(holder, name, getterName, initializer) {
+    var uninitializedSentinel = holder;
+    holder[name] = uninitializedSentinel;
+    holder[getterName] = function() {
+      holder[getterName] = function() {
+        H.throwCyclicInit(name);
+      };
+      var result;
+      var sentinelInProgress = initializer;
+      try {
+        if (holder[name] === uninitializedSentinel) {
+          result = holder[name] = sentinelInProgress;
+          result = holder[name] = initializer();
+        } else
+          result = holder[name];
+      } finally {
+        if (result === sentinelInProgress)
+          holder[name] = null;
+        holder[getterName] = function() {
+          return this[name];
+        };
+      }
+      return result;
+    };
+  }
+  function makeConstList(list) {
+    list.immutable$list = Array;
+    list.fixed$length = Array;
+    return list;
+  }
+  function convertToFastObject(properties) {
+    function t() {
+    }
+    t.prototype = properties;
+    new t();
+    return properties;
+  }
+  function convertAllToFastObject(arrayOfObjects) {
+    for (var i = 0; i < arrayOfObjects.length; ++i)
+      convertToFastObject(arrayOfObjects[i]);
+  }
+  var functionCounter = 0;
+  function tearOffGetter(funcs, applyTrampolineIndex, reflectionInfo, name, isIntercepted) {
+    return isIntercepted ? new Function("funcs", "applyTrampolineIndex", "reflectionInfo", "name", "H", "c", "return function tearOff_" + name + functionCounter++ + "(receiver) {" + "if (c === null) c = " + "H.closureFromTearOff" + "(" + "this, funcs, applyTrampolineIndex, reflectionInfo, false, true, name);" + "return new c(this, funcs[0], receiver, name);" + "}")(funcs, applyTrampolineIndex, reflectionInfo, name, H, null) : new Function("funcs", "applyTrampolineIndex", "reflectionInfo", "name", "H", "c", "return function tearOff_" + name + functionCounter++ + "() {" + "if (c === null) c = " + "H.closureFromTearOff" + "(" + "this, funcs, applyTrampolineIndex, reflectionInfo, false, false, name);" + "return new c(this, funcs[0], null, name);" + "}")(funcs, applyTrampolineIndex, reflectionInfo, name, H, null);
+  }
+  function tearOff(funcs, applyTrampolineIndex, reflectionInfo, isStatic, name, isIntercepted) {
+    var cache = null;
+    return isStatic ? function() {
+      if (cache === null)
+        cache = H.closureFromTearOff(this, funcs, applyTrampolineIndex, reflectionInfo, true, false, name).prototype;
+      return cache;
+    } : tearOffGetter(funcs, applyTrampolineIndex, reflectionInfo, name, isIntercepted);
+  }
+  var typesOffset = 0;
+  function installTearOff(container, getterName, isStatic, isIntercepted, requiredParameterCount, optionalParameterDefaultValues, callNames, funsOrNames, funType, applyIndex) {
+    var funs = [];
+    for (var i = 0; i < funsOrNames.length; i++) {
+      var fun = funsOrNames[i];
+      if (typeof fun == 'string')
+        fun = container[fun];
+      fun.$callName = callNames[i];
+      funs.push(fun);
+    }
+    var fun = funs[0];
+    fun.$requiredArgCount = requiredParameterCount;
+    fun.$defaultValues = optionalParameterDefaultValues;
+    var reflectionInfo = funType;
+    if (typeof reflectionInfo == "number")
+      reflectionInfo += typesOffset;
+    var name = funsOrNames[0];
+    fun.$stubName = name;
+    var getterFunction = tearOff(funs, applyIndex || 0, reflectionInfo, isStatic, name, isIntercepted);
+    container[getterName] = getterFunction;
+    if (isStatic)
+      fun.$tearOff = getterFunction;
+  }
+  function installStaticTearOff(container, getterName, requiredParameterCount, optionalParameterDefaultValues, callNames, funsOrNames, funType, applyIndex) {
+    return installTearOff(container, getterName, true, false, requiredParameterCount, optionalParameterDefaultValues, callNames, funsOrNames, funType, applyIndex);
+  }
+  function installInstanceTearOff(container, getterName, isIntercepted, requiredParameterCount, optionalParameterDefaultValues, callNames, funsOrNames, funType, applyIndex) {
+    return installTearOff(container, getterName, false, isIntercepted, requiredParameterCount, optionalParameterDefaultValues, callNames, funsOrNames, funType, applyIndex);
+  }
+  function setOrUpdateInterceptorsByTag(newTags) {
+    var tags = init.interceptorsByTag;
+    if (!tags) {
+      init.interceptorsByTag = newTags;
+      return;
+    }
+    copyProperties(newTags, tags);
+  }
+  function setOrUpdateLeafTags(newTags) {
+    var tags = init.leafTags;
+    if (!tags) {
+      init.leafTags = newTags;
+      return;
+    }
+    copyProperties(newTags, tags);
+  }
+  function updateTypes(newTypes) {
+    var types = init.types;
+    var length = types.length;
+    types.push.apply(types, newTypes);
+    return length;
+  }
+  function updateHolder(holder, newHolder) {
+    copyProperties(newHolder, holder);
+    return holder;
+  }
+  var hunkHelpers = function() {
+    var mkInstance = function(isIntercepted, requiredParameterCount, optionalParameterDefaultValues, callNames, applyIndex) {
+        return function(container, getterName, name, funType) {
+          return installInstanceTearOff(container, getterName, isIntercepted, requiredParameterCount, optionalParameterDefaultValues, callNames, [name], funType, applyIndex);
+        };
+      },
+      mkStatic = function(requiredParameterCount, optionalParameterDefaultValues, callNames, applyIndex) {
+        return function(container, getterName, name, funType) {
+          return installStaticTearOff(container, getterName, requiredParameterCount, optionalParameterDefaultValues, callNames, [name], funType, applyIndex);
+        };
+      };
+    return {inherit: inherit, inheritMany: inheritMany, mixin: mixin, installStaticTearOff: installStaticTearOff, installInstanceTearOff: installInstanceTearOff, _instance_0u: mkInstance(0, 0, null, ["call$0"], 0), _instance_1u: mkInstance(0, 1, null, ["call$1"], 0), _instance_2u: mkInstance(0, 2, null, ["call$2"], 0), _instance_0i: mkInstance(1, 0, null, ["call$0"], 0), _instance_1i: mkInstance(1, 1, null, ["call$1"], 0), _instance_2i: mkInstance(1, 2, null, ["call$2"], 0), _static_0: mkStatic(0, null, ["call$0"], 0), _static_1: mkStatic(1, null, ["call$1"], 0), _static_2: mkStatic(2, null, ["call$2"], 0), makeConstList: makeConstList, lazy: lazy, updateHolder: updateHolder, convertToFastObject: convertToFastObject, setFunctionNamesIfNecessary: setFunctionNamesIfNecessary, updateTypes: updateTypes, setOrUpdateInterceptorsByTag: setOrUpdateInterceptorsByTag, setOrUpdateLeafTags: setOrUpdateLeafTags};
+  }();
+  function initializeDeferredHunk(hunk) {
+    typesOffset = init.types.length;
+    hunk(hunkHelpers, init, holders, $);
+  }
+  function getGlobalFromName(name) {
+    for (var i = 0; i < holders.length; i++) {
+      if (holders[i] == C)
+        continue;
+      if (holders[i][name])
+        return holders[i][name];
+    }
+  }
+  var C = {},
+  H = {JS_CONST: function JS_CONST() {
+    },
+    CastIterable_CastIterable: function(source, $S, $T) {
+      if ($S._eval$1("EfficientLengthIterable<0>")._is(source))
+        return new H._EfficientLengthCastIterable(source, $S._eval$1("@<0>")._bind$1($T)._eval$1("_EfficientLengthCastIterable<1,2>"));
+      return new H.CastIterable(source, $S._eval$1("@<0>")._bind$1($T)._eval$1("CastIterable<1,2>"));
+    },
+    hexDigitValue: function(char) {
+      var digit, letter;
+      H.assertHelper(char <= 65535);
+      digit = char ^ 48;
+      if (digit <= 9)
+        return digit;
+      letter = char | 32;
+      if (97 <= letter && letter <= 102)
+        return letter - 87;
+      return -1;
+    },
+    SubListIterable$: function(_iterable, _start, _endOrLength, $E) {
+      P.RangeError_checkNotNegative(_start, "start");
+      if (_endOrLength != null) {
+        P.RangeError_checkNotNegative(_endOrLength, "end");
+        if (_start > _endOrLength)
+          H.throwExpression(P.RangeError$range(_start, 0, _endOrLength, "start", null));
+      }
+      return new H.SubListIterable(_iterable, _start, _endOrLength, $E._eval$1("SubListIterable<0>"));
+    },
+    MappedIterable_MappedIterable: function(iterable, $function, $S, $T) {
+      if (type$.EfficientLengthIterable_dynamic._is(iterable))
+        return new H.EfficientLengthMappedIterable(iterable, $function, $S._eval$1("@<0>")._bind$1($T)._eval$1("EfficientLengthMappedIterable<1,2>"));
+      return new H.MappedIterable(iterable, $function, $S._eval$1("@<0>")._bind$1($T)._eval$1("MappedIterable<1,2>"));
+    },
+    IterableElementError_noElement: function() {
+      return new P.StateError("No element");
+    },
+    IterableElementError_tooMany: function() {
+      return new P.StateError("Too many elements");
+    },
+    IterableElementError_tooFew: function() {
+      return new P.StateError("Too few elements");
+    },
+    _CastIterableBase: function _CastIterableBase() {
+    },
+    CastIterator: function CastIterator(t0, t1) {
+      this._source = t0;
+      this.$ti = t1;
+    },
+    CastIterable: function CastIterable(t0, t1) {
+      this._source = t0;
+      this.$ti = t1;
+    },
+    _EfficientLengthCastIterable: function _EfficientLengthCastIterable(t0, t1) {
+      this._source = t0;
+      this.$ti = t1;
+    },
+    CastMap: function CastMap(t0, t1) {
+      this._source = t0;
+      this.$ti = t1;
+    },
+    CastMap_forEach_closure: function CastMap_forEach_closure(t0, t1) {
+      this.$this = t0;
+      this.f = t1;
+    },
+    CodeUnits: function CodeUnits(t0) {
+      this._string = t0;
+    },
+    EfficientLengthIterable: function EfficientLengthIterable() {
+    },
+    ListIterable: function ListIterable() {
+    },
+    SubListIterable: function SubListIterable(t0, t1, t2, t3) {
+      var _ = this;
+      _.__internal$_iterable = t0;
+      _.__internal$_start = t1;
+      _._endOrLength = t2;
+      _.$ti = t3;
+    },
+    ListIterator: function ListIterator(t0, t1, t2) {
+      var _ = this;
+      _.__internal$_iterable = t0;
+      _.__internal$_length = t1;
+      _.__internal$_index = 0;
+      _.__internal$_current = null;
+      _.$ti = t2;
+    },
+    MappedIterable: function MappedIterable(t0, t1, t2) {
+      this.__internal$_iterable = t0;
+      this._f = t1;
+      this.$ti = t2;
+    },
+    EfficientLengthMappedIterable: function EfficientLengthMappedIterable(t0, t1, t2) {
+      this.__internal$_iterable = t0;
+      this._f = t1;
+      this.$ti = t2;
+    },
+    MappedIterator: function MappedIterator(t0, t1, t2) {
+      var _ = this;
+      _.__internal$_current = null;
+      _._iterator = t0;
+      _._f = t1;
+      _.$ti = t2;
+    },
+    MappedListIterable: function MappedListIterable(t0, t1, t2) {
+      this._source = t0;
+      this._f = t1;
+      this.$ti = t2;
+    },
+    WhereIterable: function WhereIterable(t0, t1, t2) {
+      this.__internal$_iterable = t0;
+      this._f = t1;
+      this.$ti = t2;
+    },
+    WhereIterator: function WhereIterator(t0, t1, t2) {
+      this._iterator = t0;
+      this._f = t1;
+      this.$ti = t2;
+    },
+    ExpandIterable: function ExpandIterable(t0, t1, t2) {
+      this.__internal$_iterable = t0;
+      this._f = t1;
+      this.$ti = t2;
+    },
+    ExpandIterator: function ExpandIterator(t0, t1, t2, t3) {
+      var _ = this;
+      _._iterator = t0;
+      _._f = t1;
+      _._currentExpansion = t2;
+      _.__internal$_current = null;
+      _.$ti = t3;
+    },
+    SkipWhileIterable: function SkipWhileIterable(t0, t1, t2) {
+      this.__internal$_iterable = t0;
+      this._f = t1;
+      this.$ti = t2;
+    },
+    SkipWhileIterator: function SkipWhileIterator(t0, t1, t2) {
+      var _ = this;
+      _._iterator = t0;
+      _._f = t1;
+      _._hasSkipped = false;
+      _.$ti = t2;
+    },
+    EmptyIterator: function EmptyIterator(t0) {
+      this.$ti = t0;
+    },
+    FixedLengthListMixin: function FixedLengthListMixin() {
+    },
+    UnmodifiableListMixin: function UnmodifiableListMixin() {
+    },
+    UnmodifiableListBase: function UnmodifiableListBase() {
+    },
+    ReversedListIterable: function ReversedListIterable(t0, t1) {
+      this._source = t0;
+      this.$ti = t1;
+    },
+    Symbol: function Symbol(t0) {
+      this.__internal$_name = t0;
+    },
+    ConstantMap__throwUnmodifiable: function() {
+      throw H.wrapException(P.UnsupportedError$("Cannot modify unmodifiable Map"));
+    },
+    instantiate1: function(f, T1) {
+      var t1 = new H.Instantiation1(f, T1._eval$1("Instantiation1<0>"));
+      t1.Instantiation$1(f);
+      return t1;
+    },
+    unminifyOrTag: function(rawClassName) {
+      var preserved = H.unmangleGlobalNameIfPreservedAnyways(rawClassName);
+      if (typeof preserved == "string")
+        return preserved;
+      return rawClassName;
+    },
+    isJsIndexable: function(object, record) {
+      var result;
+      if (record != null) {
+        result = record.x;
+        if (result != null)
+          return result;
+      }
+      return type$.JavaScriptIndexingBehavior_dynamic._is(object);
+    },
+    S: function(value) {
+      var res;
+      if (typeof value == "string")
+        return value;
+      if (typeof value == "number") {
+        if (value !== 0)
+          return "" + value;
+      } else if (true === value)
+        return "true";
+      else if (false === value)
+        return "false";
+      else if (value == null)
+        return "null";
+      res = J.toString$0$(value);
+      if (typeof res != "string")
+        throw H.wrapException(H.argumentErrorValue(value));
+      return res;
+    },
+    Primitives_objectHashCode: function(object) {
+      var hash = object.$identityHash;
+      if (hash == null) {
+        hash = Math.random() * 0x3fffffff | 0;
+        object.$identityHash = hash;
+      }
+      return hash;
+    },
+    Primitives_parseInt: function(source, radix) {
+      var match, decimalMatch, maxCharCode, digitsPart, t1, i, _null = null;
+      if (typeof source != "string")
+        H.throwExpression(H.argumentErrorValue(source));
+      match = /^\s*[+-]?((0x[a-f0-9]+)|(\d+)|([a-z0-9]+))\s*$/i.exec(source);
+      if (match == null)
+        return _null;
+      if (3 >= match.length)
+        return H.ioore(match, 3);
+      decimalMatch = H._checkStringNullable(match[3]);
+      if (radix == null) {
+        if (decimalMatch != null)
+          return parseInt(source, 10);
+        if (match[2] != null)
+          return parseInt(source, 16);
+        return _null;
+      }
+      if (radix < 2 || radix > 36)
+        throw H.wrapException(P.RangeError$range(radix, 2, 36, "radix", _null));
+      if (radix === 10 && decimalMatch != null)
+        return parseInt(source, 10);
+      if (radix < 10 || decimalMatch == null) {
+        maxCharCode = radix <= 10 ? 47 + radix : 86 + radix;
+        H.assertHelper(typeof match[1] == "string");
+        digitsPart = match[1];
+        for (t1 = digitsPart.length, i = 0; i < t1; ++i)
+          if ((C.JSString_methods._codeUnitAt$1(digitsPart, i) | 32) > maxCharCode)
+            return _null;
+      }
+      return parseInt(source, radix);
+    },
+    Primitives_objectTypeName: function(object) {
+      var t1 = H.Primitives__objectTypeNameNewRti(object);
+      return t1;
+    },
+    Primitives__objectTypeNameNewRti: function(object) {
+      var dispatchName, $constructor, constructorName;
+      if (object instanceof P.Object)
+        return H._rtiToString(H.instanceType(object), null);
+      if (J.getInterceptor$(object) === C.Interceptor_methods || type$.UnknownJavaScriptObject._is(object)) {
+        dispatchName = C.C_JS_CONST(object);
+        if (H.Primitives__saneNativeClassName(dispatchName))
+          return dispatchName;
+        $constructor = object.constructor;
+        if (typeof $constructor == "function") {
+          constructorName = $constructor.name;
+          if (typeof constructorName == "string" && H.Primitives__saneNativeClassName(constructorName))
+            return constructorName;
+        }
+      }
+      return H._rtiToString(H.instanceType(object), null);
+    },
+    Primitives__saneNativeClassName: function($name) {
+      var t1 = $name !== "Object" && $name !== "";
+      return t1;
+    },
+    Primitives_dateNow: function() {
+      return Date.now();
+    },
+    Primitives_initTicker: function() {
+      var $window, performance;
+      if ($.Primitives_timerFrequency != null)
+        return;
+      $.Primitives_timerFrequency = 1000;
+      $.Primitives_timerTicks = H._js_helper_Primitives_dateNow$closure();
+      if (typeof window == "undefined")
+        return;
+      $window = window;
+      if ($window == null)
+        return;
+      performance = $window.performance;
+      if (performance == null)
+        return;
+      if (typeof performance.now != "function")
+        return;
+      $.Primitives_timerFrequency = 1000000;
+      $.Primitives_timerTicks = new H.Primitives_initTicker_closure(performance);
+    },
+    Primitives_currentUri: function() {
+      if (!!self.location)
+        return self.location.href;
+      return null;
+    },
+    Primitives__fromCharCodeApply: function(array) {
+      var result, i, i0, chunkEnd,
+        end = J.get$length$asx(array);
+      if (end <= 500)
+        return String.fromCharCode.apply(null, array);
+      for (result = "", i = 0; i < end; i = i0) {
+        i0 = i + 500;
+        chunkEnd = i0 < end ? i0 : end;
+        result += String.fromCharCode.apply(null, array.slice(i, chunkEnd));
+      }
+      return result;
+    },
+    Primitives_stringFromCodePoints: function(codePoints) {
+      var t1, i,
+        a = H.setRuntimeTypeInfo([], type$.JSArray_int);
+      for (t1 = J.get$iterator$ax(type$.Iterable_dynamic._check(codePoints)); t1.moveNext$0();) {
+        i = t1.get$current();
+        if (!H._isInt(i))
+          throw H.wrapException(H.argumentErrorValue(i));
+        if (i <= 65535)
+          C.JSArray_methods.add$1(a, i);
+        else if (i <= 1114111) {
+          C.JSArray_methods.add$1(a, 55296 + (C.JSInt_methods._shrOtherPositive$1(i - 65536, 10) & 1023));
+          C.JSArray_methods.add$1(a, 56320 + (i & 1023));
+        } else
+          throw H.wrapException(H.argumentErrorValue(i));
+      }
+      return H.Primitives__fromCharCodeApply(a);
+    },
+    Primitives_stringFromCharCodes: function(charCodes) {
+      var t1, i;
+      for (type$.Iterable_dynamic._check(charCodes), t1 = J.get$iterator$ax(charCodes); t1.moveNext$0();) {
+        i = t1.get$current();
+        if (!H._isInt(i))
+          throw H.wrapException(H.argumentErrorValue(i));
+        if (i < 0)
+          throw H.wrapException(H.argumentErrorValue(i));
+        if (i > 65535)
+          return H.Primitives_stringFromCodePoints(charCodes);
+      }
+      return H.Primitives__fromCharCodeApply(type$.List_dynamic._check(charCodes));
+    },
+    Primitives_stringFromNativeUint8List: function(charCodes, start, end) {
+      var i, result, i0, chunkEnd;
+      if (end <= 500 && start === 0 && end === charCodes.length)
+        return String.fromCharCode.apply(null, charCodes);
+      for (i = start, result = ""; i < end; i = i0) {
+        i0 = i + 500;
+        chunkEnd = i0 < end ? i0 : end;
+        result += String.fromCharCode.apply(null, charCodes.subarray(i, chunkEnd));
+      }
+      return result;
+    },
+    Primitives_stringFromCharCode: function(charCode) {
+      var bits;
+      if (typeof charCode !== "number")
+        return H.iae(charCode);
+      if (0 <= charCode) {
+        if (charCode <= 65535)
+          return String.fromCharCode(charCode);
+        if (charCode <= 1114111) {
+          bits = charCode - 65536;
+          return String.fromCharCode((55296 | C.JSInt_methods._shrOtherPositive$1(bits, 10)) >>> 0, 56320 | bits & 1023);
+        }
+      }
+      throw H.wrapException(P.RangeError$range(charCode, 0, 1114111, null, null));
+    },
+    Primitives_lazyAsJsDate: function(receiver) {
+      if (receiver.date === void 0)
+        receiver.date = new Date(receiver._value);
+      return receiver.date;
+    },
+    Primitives_getYear: function(receiver) {
+      var t1 = H.Primitives_lazyAsJsDate(receiver).getUTCFullYear() + 0;
+      return t1;
+    },
+    Primitives_getMonth: function(receiver) {
+      var t1 = H.Primitives_lazyAsJsDate(receiver).getUTCMonth() + 1;
+      return t1;
+    },
+    Primitives_getDay: function(receiver) {
+      var t1 = H.Primitives_lazyAsJsDate(receiver).getUTCDate() + 0;
+      return t1;
+    },
+    Primitives_getHours: function(receiver) {
+      var t1 = H.Primitives_lazyAsJsDate(receiver).getUTCHours() + 0;
+      return t1;
+    },
+    Primitives_getMinutes: function(receiver) {
+      var t1 = H.Primitives_lazyAsJsDate(receiver).getUTCMinutes() + 0;
+      return t1;
+    },
+    Primitives_getSeconds: function(receiver) {
+      var t1 = H.Primitives_lazyAsJsDate(receiver).getUTCSeconds() + 0;
+      return t1;
+    },
+    Primitives_getMilliseconds: function(receiver) {
+      var t1 = H.Primitives_lazyAsJsDate(receiver).getUTCMilliseconds() + 0;
+      return t1;
+    },
+    Primitives_getProperty: function(object, key) {
+      if (object == null || H._isBool(object) || typeof object == "number" || typeof object == "string")
+        throw H.wrapException(H.argumentErrorValue(object));
+      return object[key];
+    },
+    Primitives_setProperty: function(object, key, value) {
+      if (object == null || H._isBool(object) || typeof object == "number" || typeof object == "string")
+        throw H.wrapException(H.argumentErrorValue(object));
+      object[key] = value;
+    },
+    iae: function(argument) {
+      throw H.wrapException(H.argumentErrorValue(argument));
+    },
+    ioore: function(receiver, index) {
+      if (receiver == null)
+        J.get$length$asx(receiver);
+      throw H.wrapException(H.diagnoseIndexError(receiver, index));
+    },
+    diagnoseIndexError: function(indexable, index) {
+      var $length, t1, _s5_ = "index";
+      if (!H._isInt(index))
+        return new P.ArgumentError(true, index, _s5_, null);
+      $length = H._checkIntNullable(J.get$length$asx(indexable));
+      if (!(index < 0)) {
+        if (typeof $length !== "number")
+          return H.iae($length);
+        t1 = index >= $length;
+      } else
+        t1 = true;
+      if (t1)
+        return P.IndexError$(index, indexable, _s5_, null, $length);
+      return P.RangeError$value(index, _s5_);
+    },
+    diagnoseRangeError: function(start, end, $length) {
+      var _s13_ = "Invalid value";
+      if (start < 0 || start > $length)
+        return new P.RangeError(0, $length, true, start, "start", _s13_);
+      if (end != null)
+        if (end < start || end > $length)
+          return new P.RangeError(start, $length, true, end, "end", _s13_);
+      return new P.ArgumentError(true, end, "end", null);
+    },
+    argumentErrorValue: function(object) {
+      return new P.ArgumentError(true, object, null, null);
+    },
+    checkNum: function(value) {
+      if (typeof value != "number")
+        throw H.wrapException(H.argumentErrorValue(value));
+      return value;
+    },
+    wrapException: function(ex) {
+      var wrapper;
+      if (ex == null)
+        ex = new P.NullThrownError();
+      wrapper = new Error();
+      wrapper.dartException = ex;
+      if ("defineProperty" in Object) {
+        Object.defineProperty(wrapper, "message", {get: H.toStringWrapper});
+        wrapper.name = "";
+      } else
+        wrapper.toString = H.toStringWrapper;
+      return wrapper;
+    },
+    toStringWrapper: function() {
+      return J.toString$0$(this.dartException);
+    },
+    throwExpression: function(ex) {
+      throw H.wrapException(ex);
+    },
+    throwConcurrentModificationError: function(collection) {
+      throw H.wrapException(P.ConcurrentModificationError$(collection));
+    },
+    TypeErrorDecoder_extractPattern: function(message) {
+      var match, $arguments, argumentsExpr, expr, method, receiver;
+      message = H.quoteStringForRegExp(message.replace(String({}), '$receiver$'));
+      match = message.match(/\\\$[a-zA-Z]+\\\$/g);
+      if (match == null)
+        match = H.setRuntimeTypeInfo([], type$.JSArray_String);
+      $arguments = match.indexOf("\\$arguments\\$");
+      argumentsExpr = match.indexOf("\\$argumentsExpr\\$");
+      expr = match.indexOf("\\$expr\\$");
+      method = match.indexOf("\\$method\\$");
+      receiver = match.indexOf("\\$receiver\\$");
+      return new H.TypeErrorDecoder(message.replace(new RegExp('\\\\\\$arguments\\\\\\$', 'g'), '((?:x|[^x])*)').replace(new RegExp('\\\\\\$argumentsExpr\\\\\\$', 'g'), '((?:x|[^x])*)').replace(new RegExp('\\\\\\$expr\\\\\\$', 'g'), '((?:x|[^x])*)').replace(new RegExp('\\\\\\$method\\\\\\$', 'g'), '((?:x|[^x])*)').replace(new RegExp('\\\\\\$receiver\\\\\\$', 'g'), '((?:x|[^x])*)'), $arguments, argumentsExpr, expr, method, receiver);
+    },
+    TypeErrorDecoder_provokeCallErrorOn: function(expression) {
+      return function($expr$) {
+        var $argumentsExpr$ = '$arguments$';
+        try {
+          $expr$.$method$($argumentsExpr$);
+        } catch (e) {
+          return e.message;
+        }
+      }(expression);
+    },
+    TypeErrorDecoder_provokePropertyErrorOn: function(expression) {
+      return function($expr$) {
+        try {
+          $expr$.$method$;
+        } catch (e) {
+          return e.message;
+        }
+      }(expression);
+    },
+    NullError$: function(_message, match) {
+      return new H.NullError(_message, match == null ? null : match.method);
+    },
+    JsNoSuchMethodError$: function(_message, match) {
+      var t1 = match == null,
+        t2 = t1 ? null : match.method;
+      return new H.JsNoSuchMethodError(_message, t2, t1 ? null : match.receiver);
+    },
+    unwrapException: function(ex) {
+      var message, number, ieErrorCode, nsme, notClosure, nullCall, nullLiteralCall, undefCall, undefLiteralCall, nullProperty, undefProperty, undefLiteralProperty, match, t2, _null = null,
+        t1 = new H.unwrapException_saveStackTrace(ex);
+      if (ex == null)
+        return _null;
+      if (ex instanceof H.ExceptionAndStackTrace)
+        return t1.call$1(ex.dartException);
+      if (typeof ex !== "object")
+        return ex;
+      if ("dartException" in ex)
+        return t1.call$1(ex.dartException);
+      else if (!("message" in ex))
+        return ex;
+      message = ex.message;
+      if ("number" in ex && typeof ex.number == "number") {
+        number = ex.number;
+        ieErrorCode = number & 65535;
+        if ((C.JSInt_methods._shrOtherPositive$1(number, 16) & 8191) === 10)
+          switch (ieErrorCode) {
+            case 438:
+              return t1.call$1(H.JsNoSuchMethodError$(H.S(message) + " (Error " + ieErrorCode + ")", _null));
+            case 445:
+            case 5007:
+              return t1.call$1(H.NullError$(H.S(message) + " (Error " + ieErrorCode + ")", _null));
+          }
+      }
+      if (ex instanceof TypeError) {
+        nsme = $.$get$TypeErrorDecoder_noSuchMethodPattern();
+        notClosure = $.$get$TypeErrorDecoder_notClosurePattern();
+        nullCall = $.$get$TypeErrorDecoder_nullCallPattern();
+        nullLiteralCall = $.$get$TypeErrorDecoder_nullLiteralCallPattern();
+        undefCall = $.$get$TypeErrorDecoder_undefinedCallPattern();
+        undefLiteralCall = $.$get$TypeErrorDecoder_undefinedLiteralCallPattern();
+        nullProperty = $.$get$TypeErrorDecoder_nullPropertyPattern();
+        $.$get$TypeErrorDecoder_nullLiteralPropertyPattern();
+        undefProperty = $.$get$TypeErrorDecoder_undefinedPropertyPattern();
+        undefLiteralProperty = $.$get$TypeErrorDecoder_undefinedLiteralPropertyPattern();
+        match = nsme.matchTypeError$1(message);
+        if (match != null)
+          return t1.call$1(H.JsNoSuchMethodError$(H._checkStringNullable(message), match));
+        else {
+          match = notClosure.matchTypeError$1(message);
+          if (match != null) {
+            match.method = "call";
+            return t1.call$1(H.JsNoSuchMethodError$(H._checkStringNullable(message), match));
+          } else {
+            match = nullCall.matchTypeError$1(message);
+            if (match == null) {
+              match = nullLiteralCall.matchTypeError$1(message);
+              if (match == null) {
+                match = undefCall.matchTypeError$1(message);
+                if (match == null) {
+                  match = undefLiteralCall.matchTypeError$1(message);
+                  if (match == null) {
+                    match = nullProperty.matchTypeError$1(message);
+                    if (match == null) {
+                      match = nullLiteralCall.matchTypeError$1(message);
+                      if (match == null) {
+                        match = undefProperty.matchTypeError$1(message);
+                        if (match == null) {
+                          match = undefLiteralProperty.matchTypeError$1(message);
+                          t2 = match != null;
+                        } else
+                          t2 = true;
+                      } else
+                        t2 = true;
+                    } else
+                      t2 = true;
+                  } else
+                    t2 = true;
+                } else
+                  t2 = true;
+              } else
+                t2 = true;
+            } else
+              t2 = true;
+            if (t2)
+              return t1.call$1(H.NullError$(H._checkStringNullable(message), match));
+          }
+        }
+        return t1.call$1(new H.UnknownJsTypeError(typeof message == "string" ? message : ""));
+      }
+      if (ex instanceof RangeError) {
+        if (typeof message == "string" && message.indexOf("call stack") !== -1)
+          return new P.StackOverflowError();
+        message = function(ex) {
+          try {
+            return String(ex);
+          } catch (e) {
+          }
+          return null;
+        }(ex);
+        return t1.call$1(new P.ArgumentError(false, _null, _null, typeof message == "string" ? message.replace(/^RangeError:\s*/, "") : message));
+      }
+      if (typeof InternalError == "function" && ex instanceof InternalError)
+        if (typeof message == "string" && message === "too much recursion")
+          return new P.StackOverflowError();
+      return ex;
+    },
+    getTraceFromException: function(exception) {
+      var trace;
+      if (exception instanceof H.ExceptionAndStackTrace)
+        return exception.stackTrace;
+      if (exception == null)
+        return new H._StackTrace(exception);
+      trace = exception.$cachedTrace;
+      if (trace != null)
+        return trace;
+      return exception.$cachedTrace = new H._StackTrace(exception);
+    },
+    objectHashCode: function(object) {
+      if (object == null || typeof object != 'object')
+        return J.get$hashCode$(object);
+      else
+        return H.Primitives_objectHashCode(object);
+    },
+    fillLiteralMap: function(keyValuePairs, result) {
+      var $length, index, index0, key,
+        t1 = Array.isArray(keyValuePairs);
+      H.assertHelper(t1);
+      $length = keyValuePairs.length;
+      for (index = 0; index < $length;) {
+        index0 = index + 1;
+        H.assertHelper(t1);
+        key = keyValuePairs[index];
+        index = index0 + 1;
+        H.assertHelper(t1);
+        result.$indexSet(0, key, keyValuePairs[index0]);
+      }
+      return result;
+    },
+    fillLiteralSet: function(values, result) {
+      var $length, index,
+        t1 = Array.isArray(values);
+      H.assertHelper(t1);
+      $length = values.length;
+      for (index = 0; index < $length; ++index) {
+        H.assertHelper(t1);
+        result.add$1(0, values[index]);
+      }
+      return result;
+    },
+    invokeClosure: function(closure, numberOfArguments, arg1, arg2, arg3, arg4) {
+      type$.Function._check(closure);
+      switch (H._checkIntNullable(numberOfArguments)) {
+        case 0:
+          return closure.call$0();
+        case 1:
+          return closure.call$1(arg1);
+        case 2:
+          return closure.call$2(arg1, arg2);
+        case 3:
+          return closure.call$3(arg1, arg2, arg3);
+        case 4:
+          return closure.call$4(arg1, arg2, arg3, arg4);
+      }
+      throw H.wrapException(new P._Exception("Unsupported number of arguments for wrapped closure"));
+    },
+    convertDartClosureToJS: function(closure, arity) {
+      var $function;
+      if (closure == null)
+        return null;
+      $function = closure.$identity;
+      if (!!$function)
+        return $function;
+      $function = function(closure, arity, invoke) {
+        return function(a1, a2, a3, a4) {
+          return invoke(closure, arity, a1, a2, a3, a4);
+        };
+      }(closure, arity, H.invokeClosure);
+      closure.$identity = $function;
+      return $function;
+    },
+    Closure_fromTearOff: function(receiver, functions, applyTrampolineIndex, reflectionInfo, isStatic, isIntercepted, propertyName) {
+      var $constructor, t1, trampoline, signatureFunction, applyTrampoline, i, stub, stubCallName, _null = null,
+        $function = functions[0],
+        callName = $function.$callName,
+        $prototype = isStatic ? Object.create(new H.StaticClosure().constructor.prototype) : Object.create(new H.BoundClosure(_null, _null, _null, _null).constructor.prototype);
+      $prototype.$initialize = $prototype.constructor;
+      if (isStatic)
+        $constructor = function static_tear_off() {
+          this.$initialize();
+        };
+      else {
+        t1 = $.Closure_functionCounter;
+        if (typeof t1 !== "number")
+          return t1.$add();
+        $.Closure_functionCounter = t1 + 1;
+        t1 = new Function("a,b,c,d" + t1, "this.$initialize(a,b,c,d" + t1 + ")");
+        $constructor = t1;
+      }
+      $prototype.constructor = $constructor;
+      $constructor.prototype = $prototype;
+      if (!isStatic) {
+        trampoline = H.Closure_forwardCallTo(receiver, $function, isIntercepted);
+        trampoline.$reflectionInfo = reflectionInfo;
+      } else {
+        $prototype.$static_name = propertyName;
+        trampoline = $function;
+      }
+      signatureFunction = H.Closure__computeSignatureFunctionNewRti(reflectionInfo, isStatic, isIntercepted);
+      $prototype.$signature = signatureFunction;
+      $prototype[callName] = trampoline;
+      for (applyTrampoline = trampoline, i = 1; i < functions.length; ++i) {
+        stub = functions[i];
+        stubCallName = stub.$callName;
+        if (stubCallName != null) {
+          stub = isStatic ? stub : H.Closure_forwardCallTo(receiver, stub, isIntercepted);
+          $prototype[stubCallName] = stub;
+        }
+        if (i === applyTrampolineIndex) {
+          stub.$reflectionInfo = reflectionInfo;
+          applyTrampoline = stub;
+        }
+      }
+      $prototype["call*"] = applyTrampoline;
+      $prototype.$requiredArgCount = $function.$requiredArgCount;
+      $prototype.$defaultValues = $function.$defaultValues;
+      return $constructor;
+    },
+    Closure__computeSignatureFunctionNewRti: function(functionType, isStatic, isIntercepted) {
+      var typeEvalMethod;
+      if (typeof functionType == "number")
+        return function(getType, t) {
+          return function() {
+            return getType(t);
+          };
+        }(H.getTypeFromTypesTable, functionType);
+      if (typeof functionType == "string") {
+        if (isStatic)
+          throw H.wrapException("Cannot compute signature for static tearoff.");
+        typeEvalMethod = isIntercepted ? H.BoundClosure_evalRecipeIntercepted : H.BoundClosure_evalRecipe;
+        return function(recipe, evalOnReceiver) {
+          return function() {
+            return evalOnReceiver(this, recipe);
+          };
+        }(functionType, typeEvalMethod);
+      }
+      throw H.wrapException("Error in functionType of tearoff");
+    },
+    Closure_cspForwardCall: function(arity, isSuperCall, stubName, $function) {
+      var getSelf = H.BoundClosure_selfOf;
+      switch (isSuperCall ? -1 : arity) {
+        case 0:
+          return function(n, S) {
+            return function() {
+              return S(this)[n]();
+            };
+          }(stubName, getSelf);
+        case 1:
+          return function(n, S) {
+            return function(a) {
+              return S(this)[n](a);
+            };
+          }(stubName, getSelf);
+        case 2:
+          return function(n, S) {
+            return function(a, b) {
+              return S(this)[n](a, b);
+            };
+          }(stubName, getSelf);
+        case 3:
+          return function(n, S) {
+            return function(a, b, c) {
+              return S(this)[n](a, b, c);
+            };
+          }(stubName, getSelf);
+        case 4:
+          return function(n, S) {
+            return function(a, b, c, d) {
+              return S(this)[n](a, b, c, d);
+            };
+          }(stubName, getSelf);
+        case 5:
+          return function(n, S) {
+            return function(a, b, c, d, e) {
+              return S(this)[n](a, b, c, d, e);
+            };
+          }(stubName, getSelf);
+        default:
+          return function(f, s) {
+            return function() {
+              return f.apply(s(this), arguments);
+            };
+          }($function, getSelf);
+      }
+    },
+    Closure_forwardCallTo: function(receiver, $function, isIntercepted) {
+      var stubName, arity, lookedUpFunction, t1, t2, selfName, $arguments;
+      if (isIntercepted)
+        return H.Closure_forwardInterceptedCallTo(receiver, $function);
+      stubName = $function.$stubName;
+      arity = $function.length;
+      lookedUpFunction = receiver[stubName];
+      t1 = $function == null ? lookedUpFunction == null : $function === lookedUpFunction;
+      t2 = !t1 || arity >= 27;
+      if (t2)
+        return H.Closure_cspForwardCall(arity, !t1, stubName, $function);
+      if (arity === 0) {
+        t1 = $.Closure_functionCounter;
+        if (typeof t1 !== "number")
+          return t1.$add();
+        $.Closure_functionCounter = t1 + 1;
+        selfName = "self" + t1;
+        t1 = "return function(){var " + selfName + " = this.";
+        t2 = $.BoundClosure_selfFieldNameCache;
+        return new Function(t1 + H.S(t2 == null ? $.BoundClosure_selfFieldNameCache = H.BoundClosure_computeFieldNamed("self") : t2) + ";return " + selfName + "." + H.S(stubName) + "();}")();
+      }
+      H.assertHelper(1 <= arity && arity < 27);
+      $arguments = "abcdefghijklmnopqrstuvwxyz".split("").splice(0, arity).join(",");
+      t1 = $.Closure_functionCounter;
+      if (typeof t1 !== "number")
+        return t1.$add();
+      $.Closure_functionCounter = t1 + 1;
+      $arguments += t1;
+      t1 = "return function(" + $arguments + "){return this.";
+      t2 = $.BoundClosure_selfFieldNameCache;
+      return new Function(t1 + H.S(t2 == null ? $.BoundClosure_selfFieldNameCache = H.BoundClosure_computeFieldNamed("self") : t2) + "." + H.S(stubName) + "(" + $arguments + ");}")();
+    },
+    Closure_cspForwardInterceptedCall: function(arity, isSuperCall, $name, $function) {
+      var getSelf = H.BoundClosure_selfOf,
+        getReceiver = H.BoundClosure_receiverOf;
+      switch (isSuperCall ? -1 : arity) {
+        case 0:
+          throw H.wrapException(H.RuntimeError$("Intercepted function with no arguments."));
+        case 1:
+          return function(n, s, r) {
+            return function() {
+              return s(this)[n](r(this));
+            };
+          }($name, getSelf, getReceiver);
+        case 2:
+          return function(n, s, r) {
+            return function(a) {
+              return s(this)[n](r(this), a);
+            };
+          }($name, getSelf, getReceiver);
+        case 3:
+          return function(n, s, r) {
+            return function(a, b) {
+              return s(this)[n](r(this), a, b);
+            };
+          }($name, getSelf, getReceiver);
+        case 4:
+          return function(n, s, r) {
+            return function(a, b, c) {
+              return s(this)[n](r(this), a, b, c);
+            };
+          }($name, getSelf, getReceiver);
+        case 5:
+          return function(n, s, r) {
+            return function(a, b, c, d) {
+              return s(this)[n](r(this), a, b, c, d);
+            };
+          }($name, getSelf, getReceiver);
+        case 6:
+          return function(n, s, r) {
+            return function(a, b, c, d, e) {
+              return s(this)[n](r(this), a, b, c, d, e);
+            };
+          }($name, getSelf, getReceiver);
+        default:
+          return function(f, s, r, a) {
+            return function() {
+              a = [r(this)];
+              Array.prototype.push.apply(a, arguments);
+              return f.apply(s(this), a);
+            };
+          }($function, getSelf, getReceiver);
+      }
+    },
+    Closure_forwardInterceptedCallTo: function(receiver, $function) {
+      var t2, stubName, arity, lookedUpFunction, t3, t4, $arguments,
+        t1 = $.BoundClosure_selfFieldNameCache;
+      if (t1 == null)
+        t1 = $.BoundClosure_selfFieldNameCache = H.BoundClosure_computeFieldNamed("self");
+      t2 = $.BoundClosure_receiverFieldNameCache;
+      if (t2 == null)
+        t2 = $.BoundClosure_receiverFieldNameCache = H.BoundClosure_computeFieldNamed("receiver");
+      stubName = $function.$stubName;
+      arity = $function.length;
+      lookedUpFunction = receiver[stubName];
+      t3 = $function == null ? lookedUpFunction == null : $function === lookedUpFunction;
+      t4 = !t3 || arity >= 28;
+      if (t4)
+        return H.Closure_cspForwardInterceptedCall(arity, !t3, stubName, $function);
+      if (arity === 1) {
+        t1 = "return function(){return this." + H.S(t1) + "." + H.S(stubName) + "(this." + H.S(t2) + ");";
+        t2 = $.Closure_functionCounter;
+        if (typeof t2 !== "number")
+          return t2.$add();
+        $.Closure_functionCounter = t2 + 1;
+        return new Function(t1 + t2 + "}")();
+      }
+      H.assertHelper(1 < arity && arity < 28);
+      $arguments = "abcdefghijklmnopqrstuvwxyz".split("").splice(0, arity - 1).join(",");
+      t1 = "return function(" + $arguments + "){return this." + H.S(t1) + "." + H.S(stubName) + "(this." + H.S(t2) + ", " + $arguments + ");";
+      t2 = $.Closure_functionCounter;
+      if (typeof t2 !== "number")
+        return t2.$add();
+      $.Closure_functionCounter = t2 + 1;
+      return new Function(t1 + t2 + "}")();
+    },
+    closureFromTearOff: function(receiver, functions, applyTrampolineIndex, reflectionInfo, isStatic, isIntercepted, $name) {
+      return H.Closure_fromTearOff(receiver, functions, applyTrampolineIndex, reflectionInfo, !!isStatic, !!isIntercepted, $name);
+    },
+    BoundClosure_evalRecipe: function(closure, recipe) {
+      return H._Universe_evalInEnvironment(init.typeUniverse, H.instanceType(closure._self), recipe);
+    },
+    BoundClosure_evalRecipeIntercepted: function(closure, recipe) {
+      return H._Universe_evalInEnvironment(init.typeUniverse, H.instanceType(closure._receiver), recipe);
+    },
+    BoundClosure_selfOf: function(closure) {
+      return closure._self;
+    },
+    BoundClosure_receiverOf: function(closure) {
+      return closure._receiver;
+    },
+    BoundClosure_computeFieldNamed: function(fieldName) {
+      var t1, i, $name,
+        template = new H.BoundClosure("self", "target", "receiver", "name"),
+        names = J.JSArray_markFixedList(Object.getOwnPropertyNames(template));
+      for (t1 = names.length, i = 0; i < t1; ++i) {
+        $name = names[i];
+        if (template[$name] === fieldName)
+          return $name;
+      }
+    },
+    boolConversionCheck: function(value) {
+      if (value == null)
+        H.assertThrow("boolean expression must not be null");
+      return value;
+    },
+    extractFunctionTypeObjectFromInternal: function(o) {
+      var signature;
+      if ("$signature" in o) {
+        signature = o.$signature;
+        if (typeof signature == "number")
+          return init.types[H._checkIntNullable(signature)];
+        else
+          return o.$signature();
+      }
+      return null;
+    },
+    TypeErrorImplementation$: function(value, type) {
+      return new H.TypeErrorImplementation("TypeError: " + P.Error_safeToString(value) + ": type '" + H.S(H._typeDescription(value)) + "' is not a subtype of type '" + type + "'");
+    },
+    _typeDescription: function(value) {
+      var functionTypeObject;
+      if (value instanceof H.Closure) {
+        functionTypeObject = H.extractFunctionTypeObjectFromInternal(J.getInterceptor$(value));
+        if (functionTypeObject != null)
+          return H.runtimeTypeToString(functionTypeObject);
+        return "Closure";
+      }
+      return H.Primitives_objectTypeName(value);
+    },
+    assertTest: function(condition) {
+      if (true === condition)
+        return false;
+      if (H._isBool(condition))
+        return !condition;
+      throw H.wrapException(H.TypeErrorImplementation$(condition, "bool"));
+    },
+    assertThrow: function(message) {
+      throw H.wrapException(new H._AssertionError(message));
+    },
+    assertHelper: function(condition) {
+      if (H.assertTest(condition))
+        throw H.wrapException(P.AssertionError$(null));
+    },
+    throwCyclicInit: function(staticName) {
+      throw H.wrapException(new P.CyclicInitializationError(staticName));
+    },
+    RuntimeError$: function(message) {
+      return new H.RuntimeError(message);
+    },
+    getIsolateAffinityTag: function($name) {
+      return init.getIsolateTag($name);
+    },
+    setRuntimeTypeInfo: function(target, rti) {
+      H.assertHelper(rti != null);
+      target.$ti = rti;
+      return target;
+    },
+    getRuntimeTypeInfo: function(target) {
+      if (target == null)
+        return null;
+      return target.$ti;
+    },
+    getRuntimeTypeArguments: function(interceptor, object, substitutionName) {
+      return H.substitute(interceptor["$as" + H.S(substitutionName)], H.getRuntimeTypeInfo(object));
+    },
+    runtimeTypeToString: function(rti) {
+      return H._runtimeTypeToString(rti, null);
+    },
+    _runtimeTypeToString: function(rti, genericContext) {
+      var t1, t2;
+      if (rti == null)
+        return "dynamic";
+      if (rti === -1)
+        return "void";
+      if (Array.isArray(rti))
+        return H.unminifyOrTag(rti[0].name) + H._joinArguments(rti, 1, genericContext);
+      if (typeof rti == "function")
+        return H.unminifyOrTag(rti.name);
+      if (rti === -2)
+        return "dynamic";
+      H.assertHelper(!(rti === -1));
+      if (typeof rti == "number") {
+        H._checkIntNullable(rti);
+        if (genericContext == null || rti < 0 || rti >= genericContext.length)
+          return "unexpected-generic-index:" + rti;
+        t1 = genericContext.length;
+        t2 = t1 - rti - 1;
+        if (t2 < 0 || t2 >= t1)
+          return H.ioore(genericContext, t2);
+        return H.S(genericContext[t2]);
+      }
+      t1 = rti != null;
+      if (t1)
+        t2 = typeof rti == "string";
+      else
+        t2 = true;
+      H.assertHelper(!t2);
+      if ('func' in rti)
+        return H._functionRtiToString0(rti, genericContext);
+      if (t1)
+        t2 = typeof rti == "string";
+      else
+        t2 = true;
+      H.assertHelper(!t2);
+      if ('futureOr' in rti) {
+        if (t1)
+          t1 = typeof rti == "string";
+        else
+          t1 = true;
+        H.assertHelper(!t1);
+        H.assertHelper('futureOr' in rti);
+        return "FutureOr<" + H._runtimeTypeToString("type" in rti ? rti.type : null, genericContext) + ">";
+      }
+      return "unknown-reified-type";
+    },
+    _functionRtiToString0: function(rti, genericContext) {
+      var boundsRti, outerContextLength, offset, i, i0, typeParameters, typeSep, t1, t2, boundRti, returnTypeText, $arguments, argumentsText, sep, _i, argument, optionalArguments, namedArguments, $name, _s2_ = ", ";
+      if ("bounds" in rti) {
+        boundsRti = rti.bounds;
+        if (genericContext == null) {
+          genericContext = H.setRuntimeTypeInfo([], type$.JSArray_String);
+          outerContextLength = null;
+        } else
+          outerContextLength = genericContext.length;
+        offset = genericContext.length;
+        for (i = boundsRti.length, i0 = i; i0 > 0; --i0)
+          C.JSArray_methods.add$1(genericContext, "T" + (offset + i0));
+        for (typeParameters = "<", typeSep = "", i0 = 0; i0 < i; ++i0, typeSep = _s2_) {
+          typeParameters += typeSep;
+          t1 = genericContext.length;
+          t2 = t1 - i0 - 1;
+          if (t2 < 0)
+            return H.ioore(genericContext, t2);
+          typeParameters = C.JSString_methods.$add(typeParameters, genericContext[t2]);
+          boundRti = boundsRti[i0];
+          if (boundRti != null && boundRti !== P.Object)
+            typeParameters += " extends " + H._runtimeTypeToString(boundRti, genericContext);
+        }
+        typeParameters += ">";
+      } else {
+        typeParameters = "";
+        outerContextLength = null;
+      }
+      returnTypeText = !!rti.v ? "void" : H._runtimeTypeToString(rti.ret, genericContext);
+      if ("args" in rti) {
+        $arguments = rti.args;
+        for (t1 = $arguments.length, argumentsText = "", sep = "", _i = 0; _i < t1; ++_i, sep = _s2_) {
+          argument = $arguments[_i];
+          argumentsText = argumentsText + sep + H._runtimeTypeToString(argument, genericContext);
+        }
+      } else {
+        argumentsText = "";
+        sep = "";
+      }
+      if ("opt" in rti) {
+        optionalArguments = rti.opt;
+        argumentsText += sep + "[";
+        for (t1 = optionalArguments.length, sep = "", _i = 0; _i < t1; ++_i, sep = _s2_) {
+          argument = optionalArguments[_i];
+          argumentsText = argumentsText + sep + H._runtimeTypeToString(argument, genericContext);
+        }
+        argumentsText += "]";
+      }
+      if ("named" in rti) {
+        namedArguments = rti.named;
+        argumentsText += sep + "{";
+        for (t1 = H.extractKeys(namedArguments), t2 = t1.length, sep = "", _i = 0; _i < t2; ++_i, sep = _s2_) {
+          $name = H._checkStringNullable(t1[_i]);
+          argumentsText = argumentsText + sep + H._runtimeTypeToString(namedArguments[$name], genericContext) + (" " + H.S($name));
+        }
+        argumentsText += "}";
+      }
+      if (outerContextLength != null)
+        genericContext.length = outerContextLength;
+      return typeParameters + "(" + argumentsText + ") => " + returnTypeText;
+    },
+    _joinArguments: function(types, startIndex, genericContext) {
+      var t1, buffer, index, separator, allDynamic, argument;
+      if (types == null)
+        return "";
+      t1 = Array.isArray(types);
+      H.assertHelper(t1);
+      buffer = new P.StringBuffer("");
+      for (index = startIndex, separator = "", allDynamic = true; H.assertHelper(t1), index < types.length; ++index, separator = ", ") {
+        buffer._contents += separator;
+        H.assertHelper(t1);
+        argument = types[index];
+        if (argument != null)
+          allDynamic = false;
+        buffer._contents += H._runtimeTypeToString(argument, genericContext);
+      }
+      return "<" + buffer.toString$0(0) + ">";
+    },
+    getRuntimeType: function(object) {
+      var rti = object instanceof H.Closure ? H.closureFunctionType(object) : null;
+      return H.createRuntimeType(rti == null ? H.instanceType(object) : rti);
+    },
+    substitute: function(substitution, $arguments) {
+      if (substitution == null)
+        return $arguments;
+      H.assertHelper(typeof substitution == "function");
+      H.assertHelper($arguments == null || Array.isArray($arguments));
+      substitution = H.invokeOn(substitution, null, $arguments);
+      if (substitution == null)
+        return null;
+      if (Array.isArray(substitution))
+        return substitution;
+      if (typeof substitution == "function")
+        return H.invokeOn(substitution, null, $arguments);
+      return $arguments;
+    },
+    computeSignature: function(signature, context, contextName) {
+      return H.invokeOn(signature, context, H.substitute(J.getInterceptor$(context)["$as" + H.S(contextName)], H.getRuntimeTypeInfo(context)));
+    },
+    invokeOn: function($function, receiver, $arguments) {
+      H.assertHelper(typeof $function == "function");
+      H.assertHelper($arguments == null || Array.isArray($arguments));
+      return $function.apply(receiver, $arguments);
+    },
+    defineProperty: function(obj, property, value) {
+      Object.defineProperty(obj, property, {value: value, enumerable: false, writable: true, configurable: true});
+    },
+    lookupAndCacheInterceptor: function(obj) {
+      var tag, record, interceptor, interceptorClass, mark, t1;
+      H.assertHelper(!(obj instanceof P.Object));
+      tag = H._checkStringNullable($.getTagFunction.call$1(obj));
+      record = $.dispatchRecordsForInstanceTags[tag];
+      if (record != null) {
+        Object.defineProperty(obj, init.dispatchPropertyName, {value: record, enumerable: false, writable: true, configurable: true});
+        return record.i;
+      }
+      interceptor = $.interceptorsForUncacheableTags[tag];
+      if (interceptor != null)
+        return interceptor;
+      interceptorClass = init.interceptorsByTag[tag];
+      if (interceptorClass == null) {
+        tag = H._checkStringNullable($.alternateTagFunction.call$2(obj, tag));
+        if (tag != null) {
+          record = $.dispatchRecordsForInstanceTags[tag];
+          if (record != null) {
+            Object.defineProperty(obj, init.dispatchPropertyName, {value: record, enumerable: false, writable: true, configurable: true});
+            return record.i;
+          }
+          interceptor = $.interceptorsForUncacheableTags[tag];
+          if (interceptor != null)
+            return interceptor;
+          interceptorClass = init.interceptorsByTag[tag];
+        }
+      }
+      if (interceptorClass == null)
+        return null;
+      interceptor = interceptorClass.prototype;
+      mark = tag[0];
+      if (mark === "!") {
+        record = H.makeLeafDispatchRecord(interceptor);
+        $.dispatchRecordsForInstanceTags[tag] = record;
+        Object.defineProperty(obj, init.dispatchPropertyName, {value: record, enumerable: false, writable: true, configurable: true});
+        return record.i;
+      }
+      if (mark === "~") {
+        $.interceptorsForUncacheableTags[tag] = interceptor;
+        return interceptor;
+      }
+      if (mark === "-") {
+        t1 = H.makeLeafDispatchRecord(interceptor);
+        Object.defineProperty(Object.getPrototypeOf(obj), init.dispatchPropertyName, {value: t1, enumerable: false, writable: true, configurable: true});
+        return t1.i;
+      }
+      if (mark === "+")
+        return H.patchInteriorProto(obj, interceptor);
+      if (mark === "*")
+        throw H.wrapException(P.UnimplementedError$(tag));
+      if (init.leafTags[tag] === true) {
+        t1 = H.makeLeafDispatchRecord(interceptor);
+        Object.defineProperty(Object.getPrototypeOf(obj), init.dispatchPropertyName, {value: t1, enumerable: false, writable: true, configurable: true});
+        return t1.i;
+      } else
+        return H.patchInteriorProto(obj, interceptor);
+    },
+    patchInteriorProto: function(obj, interceptor) {
+      var proto = Object.getPrototypeOf(obj);
+      Object.defineProperty(proto, init.dispatchPropertyName, {value: J.makeDispatchRecord(interceptor, proto, null, null), enumerable: false, writable: true, configurable: true});
+      return interceptor;
+    },
+    makeLeafDispatchRecord: function(interceptor) {
+      return J.makeDispatchRecord(interceptor, false, null, !!interceptor.$isJavaScriptIndexingBehavior);
+    },
+    makeDefaultDispatchRecord: function(tag, interceptorClass, proto) {
+      var interceptor = interceptorClass.prototype;
+      if (init.leafTags[tag] === true)
+        return H.makeLeafDispatchRecord(interceptor);
+      else
+        return J.makeDispatchRecord(interceptor, proto, null, null);
+    },
+    initNativeDispatch: function() {
+      if (true === $.initNativeDispatchFlag)
+        return;
+      $.initNativeDispatchFlag = true;
+      H.initNativeDispatchContinue();
+    },
+    initNativeDispatchContinue: function() {
+      var map, tags, fun, i, tag, proto, record, interceptorClass;
+      $.dispatchRecordsForInstanceTags = Object.create(null);
+      $.interceptorsForUncacheableTags = Object.create(null);
+      H.initHooks();
+      map = init.interceptorsByTag;
+      tags = Object.getOwnPropertyNames(map);
+      if (typeof window != "undefined") {
+        window;
+        fun = function() {
+        };
+        for (i = 0; i < tags.length; ++i) {
+          tag = tags[i];
+          proto = $.prototypeForTagFunction.call$1(tag);
+          if (proto != null) {
+            record = H.makeDefaultDispatchRecord(tag, map[tag], proto);
+            if (record != null) {
+              Object.defineProperty(proto, init.dispatchPropertyName, {value: record, enumerable: false, writable: true, configurable: true});
+              fun.prototype = proto;
+            }
+          }
+        }
+      }
+      for (i = 0; i < tags.length; ++i) {
+        tag = tags[i];
+        if (/^[A-Za-z_]/.test(tag)) {
+          interceptorClass = map[tag];
+          map["!" + tag] = interceptorClass;
+          map["~" + tag] = interceptorClass;
+          map["-" + tag] = interceptorClass;
+          map["+" + tag] = interceptorClass;
+          map["*" + tag] = interceptorClass;
+        }
+      }
+    },
+    initHooks: function() {
+      var transformers, i, transformer, getTag, getUnknownTag, prototypeForTag,
+        hooks = C.C_JS_CONST0();
+      hooks = H.applyHooksTransformer(C.C_JS_CONST1, H.applyHooksTransformer(C.C_JS_CONST2, H.applyHooksTransformer(C.C_JS_CONST3, H.applyHooksTransformer(C.C_JS_CONST3, H.applyHooksTransformer(C.C_JS_CONST4, H.applyHooksTransformer(C.C_JS_CONST5, H.applyHooksTransformer(C.C_JS_CONST6(C.C_JS_CONST), hooks)))))));
+      if (typeof dartNativeDispatchHooksTransformer != "undefined") {
+        transformers = dartNativeDispatchHooksTransformer;
+        if (typeof transformers == "function")
+          transformers = [transformers];
+        if (transformers.constructor == Array)
+          for (i = 0; i < transformers.length; ++i) {
+            transformer = transformers[i];
+            if (typeof transformer == "function")
+              hooks = transformer(hooks) || hooks;
+          }
+      }
+      getTag = hooks.getTag;
+      getUnknownTag = hooks.getUnknownTag;
+      prototypeForTag = hooks.prototypeForTag;
+      $.getTagFunction = new H.initHooks_closure(getTag);
+      $.alternateTagFunction = new H.initHooks_closure0(getUnknownTag);
+      $.prototypeForTagFunction = new H.initHooks_closure1(prototypeForTag);
+    },
+    applyHooksTransformer: function(transformer, hooks) {
+      return transformer(hooks) || hooks;
+    },
+    JSSyntaxRegExp_makeNative: function(source, multiLine, caseSensitive, unicode, dotAll, global) {
+      var m = multiLine ? "m" : "",
+        i = caseSensitive ? "" : "i",
+        u = unicode ? "u" : "",
+        s = dotAll ? "s" : "",
+        g = global ? "g" : "",
+        regexp = function(source, modifiers) {
+          try {
+            return new RegExp(source, modifiers);
+          } catch (e) {
+            return e;
+          }
+        }(source, m + i + u + s + g);
+      if (regexp instanceof RegExp)
+        return regexp;
+      throw H.wrapException(P.FormatException$("Illegal RegExp pattern (" + String(regexp) + ")", source, null));
+    },
+    _MatchImplementation$: function(pattern, _match) {
+      H.assertHelper(typeof _match.input == "string");
+      H.assertHelper(H._isInt(_match.index));
+      return new H._MatchImplementation(_match);
+    },
+    stringContainsUnchecked: function(receiver, other, startIndex) {
+      var t1, t2;
+      if (typeof other == "string")
+        return receiver.indexOf(other, startIndex) >= 0;
+      else if (other instanceof H.JSSyntaxRegExp) {
+        t1 = C.JSString_methods.substring$1(receiver, startIndex);
+        t2 = other._nativeRegExp;
+        return t2.test(t1);
+      } else {
+        t1 = J.allMatches$1$s(other, C.JSString_methods.substring$1(receiver, startIndex));
+        return !t1.get$isEmpty(t1);
+      }
+    },
+    escapeReplacement: function(replacement) {
+      if (replacement.indexOf("$", 0) >= 0)
+        return replacement.replace(/\$/g, "$$$$");
+      return replacement;
+    },
+    stringReplaceFirstRE: function(receiver, regexp, replacement, startIndex) {
+      var match = regexp._execGlobal$2(receiver, startIndex);
+      if (match == null)
+        return receiver;
+      return H.stringReplaceRangeUnchecked(receiver, match._match.index, match.get$end(), replacement);
+    },
+    quoteStringForRegExp: function(string) {
+      if (/[[\]{}()*+?.\\^$|]/.test(string))
+        return string.replace(/[[\]{}()*+?.\\^$|]/g, "\\$&");
+      return string;
+    },
+    stringReplaceAllUnchecked: function(receiver, pattern, replacement) {
+      var nativeRegexp;
+      if (typeof pattern == "string")
+        return H.stringReplaceAllUncheckedString(receiver, pattern, replacement);
+      if (pattern instanceof H.JSSyntaxRegExp) {
+        nativeRegexp = pattern.get$_nativeGlobalVersion();
+        nativeRegexp.lastIndex = 0;
+        return receiver.replace(nativeRegexp, H.escapeReplacement(replacement));
+      }
+      if (pattern == null)
+        H.throwExpression(H.argumentErrorValue(pattern));
+      throw H.wrapException("String.replaceAll(Pattern) UNIMPLEMENTED");
+    },
+    stringReplaceAllUncheckedString: function(receiver, pattern, replacement) {
+      var $length, t1, i, index;
+      if (pattern === "") {
+        if (receiver === "")
+          return replacement;
+        $length = receiver.length;
+        for (t1 = replacement, i = 0; i < $length; ++i)
+          t1 = t1 + receiver[i] + replacement;
+        return t1.charCodeAt(0) == 0 ? t1 : t1;
+      }
+      index = receiver.indexOf(pattern, 0);
+      if (index < 0)
+        return receiver;
+      if (receiver.length < 500 || replacement.indexOf("$", 0) >= 0)
+        return receiver.split(pattern).join(replacement);
+      return receiver.replace(new RegExp(H.quoteStringForRegExp(pattern), 'g'), H.escapeReplacement(replacement));
+    },
+    _stringIdentity: function(string) {
+      return string;
+    },
+    stringReplaceAllFuncUnchecked: function(receiver, pattern, onMatch, onNonMatch) {
+      var t1, startIndex, t2, t3, t4, t5;
+      if (!type$.Pattern._is(pattern))
+        throw H.wrapException(P.ArgumentError$value(pattern, "pattern", "is not a Pattern"));
+      for (t1 = pattern.allMatches$1(0, receiver), t1 = new H._AllMatchesIterator(t1._re, t1.__js_helper$_string, t1._start), startIndex = 0, t2 = ""; t1.moveNext$0(); t2 = t3) {
+        t3 = t1.__js_helper$_current;
+        t4 = t3._match;
+        t5 = t4.index;
+        t3 = t2 + H.S(H._stringIdentity(C.JSString_methods.substring$2(receiver, startIndex, t5))) + H.S(onMatch.call$1(t3));
+        startIndex = t5 + t4[0].length;
+      }
+      t1 = t2 + H.S(H._stringIdentity(C.JSString_methods.substring$1(receiver, startIndex)));
+      return t1.charCodeAt(0) == 0 ? t1 : t1;
+    },
+    stringReplaceFirstUnchecked: function(receiver, pattern, replacement, startIndex) {
+      var index, t1, matches, match;
+      if (typeof pattern == "string") {
+        index = receiver.indexOf(pattern, startIndex);
+        if (index < 0)
+          return receiver;
+        return H.stringReplaceRangeUnchecked(receiver, index, index + pattern.length, replacement);
+      }
+      if (pattern instanceof H.JSSyntaxRegExp)
+        return startIndex === 0 ? receiver.replace(pattern._nativeRegExp, H.escapeReplacement(replacement)) : H.stringReplaceFirstRE(receiver, pattern, replacement, startIndex);
+      if (pattern == null)
+        H.throwExpression(H.argumentErrorValue(pattern));
+      t1 = J.allMatches$2$s(pattern, receiver, startIndex);
+      matches = type$.Iterator_Match._check(t1.get$iterator(t1));
+      if (!matches.moveNext$0())
+        return receiver;
+      match = matches.get$current();
+      return C.JSString_methods.replaceRange$3(receiver, match.get$start(), match.get$end(), replacement);
+    },
+    stringReplaceRangeUnchecked: function(receiver, start, end, replacement) {
+      var prefix = receiver.substring(0, start),
+        suffix = receiver.substring(end);
+      return prefix + replacement + suffix;
+    },
+    ConstantMap: function ConstantMap() {
+    },
+    ConstantMap_map_closure: function ConstantMap_map_closure(t0, t1, t2) {
+      this.$this = t0;
+      this.transform = t1;
+      this.result = t2;
+    },
+    ConstantStringMap: function ConstantStringMap(t0, t1, t2, t3) {
+      var _ = this;
+      _.__js_helper$_length = t0;
+      _._jsObject = t1;
+      _.__js_helper$_keys = t2;
+      _.$ti = t3;
+    },
+    _ConstantMapKeyIterable: function _ConstantMapKeyIterable(t0, t1) {
+      this.__js_helper$_map = t0;
+      this.$ti = t1;
+    },
+    Instantiation: function Instantiation() {
+    },
+    Instantiation1: function Instantiation1(t0, t1) {
+      this._genericClosure = t0;
+      this.$ti = t1;
+    },
+    Primitives_initTicker_closure: function Primitives_initTicker_closure(t0) {
+      this.performance = t0;
+    },
+    TypeErrorDecoder: function TypeErrorDecoder(t0, t1, t2, t3, t4, t5) {
+      var _ = this;
+      _._pattern = t0;
+      _._arguments = t1;
+      _._argumentsExpr = t2;
+      _._expr = t3;
+      _._method = t4;
+      _._receiver = t5;
+    },
+    NullError: function NullError(t0, t1) {
+      this.__js_helper$_message = t0;
+      this._method = t1;
+    },
+    JsNoSuchMethodError: function JsNoSuchMethodError(t0, t1, t2) {
+      this.__js_helper$_message = t0;
+      this._method = t1;
+      this._receiver = t2;
+    },
+    UnknownJsTypeError: function UnknownJsTypeError(t0) {
+      this.__js_helper$_message = t0;
+    },
+    ExceptionAndStackTrace: function ExceptionAndStackTrace(t0, t1) {
+      this.dartException = t0;
+      this.stackTrace = t1;
+    },
+    unwrapException_saveStackTrace: function unwrapException_saveStackTrace(t0) {
+      this.ex = t0;
+    },
+    _StackTrace: function _StackTrace(t0) {
+      this._exception = t0;
+      this._trace = null;
+    },
+    Closure: function Closure() {
+    },
+    TearOffClosure: function TearOffClosure() {
+    },
+    StaticClosure: function StaticClosure() {
+    },
+    BoundClosure: function BoundClosure(t0, t1, t2, t3) {
+      var _ = this;
+      _._self = t0;
+      _._target = t1;
+      _._receiver = t2;
+      _._name = t3;
+    },
+    TypeErrorImplementation: function TypeErrorImplementation(t0) {
+      this.message = t0;
+    },
+    RuntimeError: function RuntimeError(t0) {
+      this.message = t0;
+    },
+    _AssertionError: function _AssertionError(t0) {
+      this.message = t0;
+    },
+    JsLinkedHashMap: function JsLinkedHashMap(t0) {
+      var _ = this;
+      _.__js_helper$_length = 0;
+      _._last = _._first = _.__js_helper$_rest = _.__js_helper$_nums = _.__js_helper$_strings = null;
+      _._modifications = 0;
+      _.$ti = t0;
+    },
+    JsLinkedHashMap_values_closure: function JsLinkedHashMap_values_closure(t0) {
+      this.$this = t0;
+    },
+    JsLinkedHashMap_addAll_closure: function JsLinkedHashMap_addAll_closure(t0) {
+      this.$this = t0;
+    },
+    LinkedHashMapCell: function LinkedHashMapCell(t0, t1) {
+      var _ = this;
+      _.hashMapCellKey = t0;
+      _.hashMapCellValue = t1;
+      _._previous = _._next = null;
+    },
+    LinkedHashMapKeyIterable: function LinkedHashMapKeyIterable(t0, t1) {
+      this.__js_helper$_map = t0;
+      this.$ti = t1;
+    },
+    LinkedHashMapKeyIterator: function LinkedHashMapKeyIterator(t0, t1, t2) {
+      var _ = this;
+      _.__js_helper$_map = t0;
+      _._modifications = t1;
+      _.__js_helper$_current = _._cell = null;
+      _.$ti = t2;
+    },
+    initHooks_closure: function initHooks_closure(t0) {
+      this.getTag = t0;
+    },
+    initHooks_closure0: function initHooks_closure0(t0) {
+      this.getUnknownTag = t0;
+    },
+    initHooks_closure1: function initHooks_closure1(t0) {
+      this.prototypeForTag = t0;
+    },
+    JSSyntaxRegExp: function JSSyntaxRegExp(t0, t1) {
+      var _ = this;
+      _.pattern = t0;
+      _._nativeRegExp = t1;
+      _._nativeAnchoredRegExp = _._nativeGlobalRegExp = null;
+    },
+    _MatchImplementation: function _MatchImplementation(t0) {
+      this._match = t0;
+    },
+    _AllMatchesIterable: function _AllMatchesIterable(t0, t1, t2) {
+      this._re = t0;
+      this.__js_helper$_string = t1;
+      this._start = t2;
+    },
+    _AllMatchesIterator: function _AllMatchesIterator(t0, t1, t2) {
+      var _ = this;
+      _._regExp = t0;
+      _.__js_helper$_string = t1;
+      _._nextIndex = t2;
+      _.__js_helper$_current = null;
+    },
+    StringMatch: function StringMatch(t0, t1) {
+      this.start = t0;
+      this.pattern = t1;
+    },
+    _StringAllMatchesIterable: function _StringAllMatchesIterable(t0, t1, t2) {
+      this._input = t0;
+      this._pattern = t1;
+      this.__js_helper$_index = t2;
+    },
+    _StringAllMatchesIterator: function _StringAllMatchesIterator(t0, t1, t2) {
+      var _ = this;
+      _._input = t0;
+      _._pattern = t1;
+      _.__js_helper$_index = t2;
+      _.__js_helper$_current = null;
+    },
+    _ensureNativeList: function(list) {
+      return list;
+    },
+    NativeInt8List__create1: function(arg) {
+      return new Int8Array(arg);
+    },
+    _checkValidIndex: function(index, list, $length) {
+      if (index >>> 0 !== index || index >= $length)
+        throw H.wrapException(H.diagnoseIndexError(list, index));
+    },
+    _checkValidRange: function(start, end, $length) {
+      var t1;
+      if (!(start >>> 0 !== start))
+        if (end == null)
+          t1 = start > $length;
+        else
+          t1 = end >>> 0 !== end || start > end || end > $length;
+      else
+        t1 = true;
+      if (t1)
+        throw H.wrapException(H.diagnoseRangeError(start, end, $length));
+      if (end == null)
+        return $length;
+      return end;
+    },
+    NativeByteBuffer: function NativeByteBuffer() {
+    },
+    NativeTypedData: function NativeTypedData() {
+    },
+    NativeByteData: function NativeByteData() {
+    },
+    NativeTypedArray: function NativeTypedArray() {
+    },
+    NativeTypedArrayOfDouble: function NativeTypedArrayOfDouble() {
+    },
+    NativeTypedArrayOfInt: function NativeTypedArrayOfInt() {
+    },
+    NativeFloat32List: function NativeFloat32List() {
+    },
+    NativeFloat64List: function NativeFloat64List() {
+    },
+    NativeInt16List: function NativeInt16List() {
+    },
+    NativeInt32List: function NativeInt32List() {
+    },
+    NativeInt8List: function NativeInt8List() {
+    },
+    NativeUint16List: function NativeUint16List() {
+    },
+    NativeUint32List: function NativeUint32List() {
+    },
+    NativeUint8ClampedList: function NativeUint8ClampedList() {
+    },
+    NativeUint8List: function NativeUint8List() {
+    },
+    _NativeTypedArrayOfDouble_NativeTypedArray_ListMixin: function _NativeTypedArrayOfDouble_NativeTypedArray_ListMixin() {
+    },
+    _NativeTypedArrayOfDouble_NativeTypedArray_ListMixin_FixedLengthListMixin: function _NativeTypedArrayOfDouble_NativeTypedArray_ListMixin_FixedLengthListMixin() {
+    },
+    _NativeTypedArrayOfInt_NativeTypedArray_ListMixin: function _NativeTypedArrayOfInt_NativeTypedArray_ListMixin() {
+    },
+    _NativeTypedArrayOfInt_NativeTypedArray_ListMixin_FixedLengthListMixin: function _NativeTypedArrayOfInt_NativeTypedArray_ListMixin_FixedLengthListMixin() {
+    },
+    Rti__getFutureFromFutureOr: function(universe, rti) {
+      var future;
+      H.assertHelper(rti._kind === 8);
+      future = rti._precomputed1;
+      if (future == null) {
+        H.assertHelper(rti._kind === 8);
+        future = rti._precomputed1 = H._Universe__lookupInterfaceRti(universe, "Future", [rti._primary]);
+      }
+      return future;
+    },
+    Rti__isUnionOfFunctionType: function(rti) {
+      var kind = rti._kind;
+      if (kind === 6 || kind === 7 || kind === 8)
+        return H.Rti__isUnionOfFunctionType(rti._primary);
+      return kind === 11 || kind === 12;
+    },
+    Rti__getInterfaceTypeArguments: function(rti) {
+      H.assertHelper(rti._kind === 9);
+      return rti._rest;
+    },
+    Rti__getBindingArguments: function(rti) {
+      H.assertHelper(rti._kind === 10);
+      return rti._rest;
+    },
+    Rti__getFunctionParameters: function(rti) {
+      H.assertHelper(rti._kind === 11);
+      return rti._rest;
+    },
+    Rti__getGenericFunctionBounds: function(rti) {
+      H.assertHelper(rti._kind === 12);
+      return rti._rest;
+    },
+    Rti__getCanonicalRecipe: function(rti) {
+      var s = rti._canonicalRecipe;
+      if (H.assertTest(typeof s == "string"))
+        H.assertThrow("Missing canonical recipe");
+      return s;
+    },
+    findType: function(recipe) {
+      return H._Universe_eval(init.typeUniverse, recipe);
+    },
+    instantiatedGenericFunctionType: function(genericFunctionRti, instantiationRti) {
+      var bounds, typeArguments, cache, s, key, probe, rti;
+      if (genericFunctionRti == null)
+        return null;
+      bounds = H.Rti__getGenericFunctionBounds(genericFunctionRti);
+      typeArguments = H.Rti__getInterfaceTypeArguments(instantiationRti);
+      H.assertHelper(bounds.length === typeArguments.length);
+      cache = genericFunctionRti._bindCache;
+      if (cache == null)
+        cache = genericFunctionRti._bindCache = new Map();
+      s = instantiationRti._canonicalRecipe;
+      if (H.assertTest(typeof s == "string"))
+        H.assertThrow("Missing canonical recipe");
+      key = s;
+      probe = cache.get(key);
+      if (probe != null)
+        return probe;
+      H.assertHelper(genericFunctionRti._kind === 12);
+      rti = H._instantiate(init.typeUniverse, genericFunctionRti._primary, typeArguments, 0);
+      cache.set(key, rti);
+      return rti;
+    },
+    _instantiate: function(universe, rti, typeArguments, depth) {
+      var baseType, instantiatedBaseType, s, interfaceTypeArguments, instantiatedInterfaceTypeArguments, base, instantiatedBase, $arguments, instantiatedArguments, returnType, instantiatedReturnType, functionParameters, instantiatedFunctionParameters, bounds, instantiatedBounds, index,
+        _s24_ = "Missing canonical recipe",
+        t1 = rti._kind,
+        kind = t1;
+      switch (kind) {
+        case 5:
+        case 1:
+        case 2:
+        case 3:
+        case 4:
+          return rti;
+        case 6:
+          baseType = rti._primary;
+          instantiatedBaseType = H._instantiate(universe, baseType, typeArguments, depth);
+          if (instantiatedBaseType === baseType)
+            return rti;
+          s = instantiatedBaseType._canonicalRecipe;
+          if (H.assertTest(typeof s == "string"))
+            H.assertThrow(_s24_);
+          return H._Universe__lookupUnaryRti(universe, 6, instantiatedBaseType, s + "*");
+        case 7:
+          baseType = rti._primary;
+          instantiatedBaseType = H._instantiate(universe, baseType, typeArguments, depth);
+          if (instantiatedBaseType === baseType)
+            return rti;
+          s = instantiatedBaseType._canonicalRecipe;
+          if (H.assertTest(typeof s == "string"))
+            H.assertThrow(_s24_);
+          return H._Universe__lookupUnaryRti(universe, 7, instantiatedBaseType, s + "?");
+        case 8:
+          baseType = rti._primary;
+          instantiatedBaseType = H._instantiate(universe, baseType, typeArguments, depth);
+          if (instantiatedBaseType === baseType)
+            return rti;
+          s = instantiatedBaseType._canonicalRecipe;
+          if (H.assertTest(typeof s == "string"))
+            H.assertThrow(_s24_);
+          return H._Universe__lookupUnaryRti(universe, 8, instantiatedBaseType, s + "/");
+        case 9:
+          interfaceTypeArguments = H.Rti__getInterfaceTypeArguments(rti);
+          instantiatedInterfaceTypeArguments = H._instantiateArray(universe, interfaceTypeArguments, typeArguments, depth);
+          if (instantiatedInterfaceTypeArguments === interfaceTypeArguments)
+            return rti;
+          H.assertHelper(rti._kind === 9);
+          return H._Universe__lookupInterfaceRti(universe, rti._primary, instantiatedInterfaceTypeArguments);
+        case 10:
+          H.assertHelper(t1 === 10);
+          base = rti._primary;
+          instantiatedBase = H._instantiate(universe, base, typeArguments, depth);
+          $arguments = H.Rti__getBindingArguments(rti);
+          instantiatedArguments = H._instantiateArray(universe, $arguments, typeArguments, depth);
+          if (instantiatedBase === base && instantiatedArguments === $arguments)
+            return rti;
+          return H._Universe__lookupBindingRti(universe, instantiatedBase, instantiatedArguments);
+        case 11:
+          H.assertHelper(t1 === 11);
+          returnType = rti._primary;
+          instantiatedReturnType = H._instantiate(universe, returnType, typeArguments, depth);
+          functionParameters = H.Rti__getFunctionParameters(rti);
+          instantiatedFunctionParameters = H._instantiateFunctionParameters(universe, functionParameters, typeArguments, depth);
+          if (instantiatedReturnType === returnType && instantiatedFunctionParameters === functionParameters)
+            return rti;
+          return H._Universe__lookupFunctionRti(universe, instantiatedReturnType, instantiatedFunctionParameters);
+        case 12:
+          bounds = H.Rti__getGenericFunctionBounds(rti);
+          depth += bounds.length;
+          instantiatedBounds = H._instantiateArray(universe, bounds, typeArguments, depth);
+          H.assertHelper(rti._kind === 12);
+          base = rti._primary;
+          instantiatedBase = H._instantiate(universe, base, typeArguments, depth);
+          if (instantiatedBounds === bounds && instantiatedBase === base)
+            return rti;
+          return H._Universe__lookupGenericFunctionRti(universe, instantiatedBase, instantiatedBounds);
+        case 13:
+          H.assertHelper(t1 === 13);
+          index = rti._primary;
+          if (index < depth)
+            return null;
+          return typeArguments[index - depth];
+        default:
+          throw H.wrapException(P.AssertionError$("Attempted to instantiate unexpected RTI kind " + kind));
+      }
+    },
+    _instantiateArray: function(universe, rtiArray, typeArguments, depth) {
+      var changed, i, rti, instantiatedRti,
+        $length = rtiArray.length,
+        result = [];
+      for (changed = false, i = 0; i < $length; ++i) {
+        rti = rtiArray[i];
+        instantiatedRti = H._instantiate(universe, rti, typeArguments, depth);
+        if (instantiatedRti !== rti)
+          changed = true;
+        result.push(instantiatedRti);
+      }
+      return changed ? result : rtiArray;
+    },
+    _instantiateNamed: function(universe, namedArray, typeArguments, depth) {
+      var result, changed, i, t1, rti, instantiatedRti,
+        $length = namedArray.length;
+      H.assertHelper(($length & 1) === 0);
+      result = [];
+      for (changed = false, i = 0; i < $length; i += 2) {
+        t1 = namedArray[i];
+        rti = namedArray[i + 1];
+        instantiatedRti = H._instantiate(universe, rti, typeArguments, depth);
+        if (instantiatedRti !== rti)
+          changed = true;
+        result.push(t1);
+        result.push(instantiatedRti);
+      }
+      return changed ? result : namedArray;
+    },
+    _instantiateFunctionParameters: function(universe, functionParameters, typeArguments, depth) {
+      var result,
+        requiredPositional = functionParameters._requiredPositional,
+        instantiatedRequiredPositional = H._instantiateArray(universe, requiredPositional, typeArguments, depth),
+        optionalPositional = functionParameters._optionalPositional,
+        instantiatedOptionalPositional = H._instantiateArray(universe, optionalPositional, typeArguments, depth),
+        optionalNamed = functionParameters._optionalNamed,
+        instantiatedOptionalNamed = H._instantiateNamed(universe, optionalNamed, typeArguments, depth);
+      if (instantiatedRequiredPositional === requiredPositional && instantiatedOptionalPositional === optionalPositional && instantiatedOptionalNamed === optionalNamed)
+        return functionParameters;
+      result = new H._FunctionParameters();
+      result._requiredPositional = instantiatedRequiredPositional;
+      result._optionalPositional = instantiatedOptionalPositional;
+      result._optionalNamed = instantiatedOptionalNamed;
+      return result;
+    },
+    closureFunctionType: function(closure) {
+      var signature = closure.$signature;
+      if (signature != null) {
+        if (typeof signature == "number")
+          return H.getTypeFromTypesTable(signature);
+        return closure.$signature();
+      }
+      return null;
+    },
+    instanceOrFunctionType: function(object, testRti) {
+      var rti;
+      if (H.Rti__isUnionOfFunctionType(testRti))
+        if (object instanceof H.Closure) {
+          rti = H.closureFunctionType(object);
+          if (rti != null)
+            return rti;
+        }
+      return H.instanceType(object);
+    },
+    instanceType: function(object) {
+      var rti;
+      if (object instanceof P.Object) {
+        rti = object.$ti;
+        return rti != null ? rti : H._instanceTypeFromConstructor(object);
+      }
+      if (Array.isArray(object))
+        return H._arrayInstanceType(object);
+      return H._instanceTypeFromConstructor(J.getInterceptor$(object));
+    },
+    _arrayInstanceType: function(object) {
+      var rti = object.$ti,
+        defaultRti = type$.JSArray_dynamic;
+      if (rti == null)
+        return defaultRti;
+      if (rti.constructor !== defaultRti.constructor)
+        return defaultRti;
+      return rti;
+    },
+    _instanceType: function(object) {
+      var rti = object.$ti;
+      return rti != null ? rti : H._instanceTypeFromConstructor(object);
+    },
+    _instanceTypeFromConstructor: function(instance) {
+      var $constructor = instance.constructor,
+        probe = $constructor.$ccache;
+      if (probe != null)
+        return probe;
+      return H._instanceTypeFromConstructorMiss(instance, $constructor);
+    },
+    _instanceTypeFromConstructorMiss: function(instance, $constructor) {
+      var effectiveConstructor = instance instanceof H.Closure ? instance.__proto__.__proto__.constructor : $constructor,
+        rti = H._Universe_findErasedType(init.typeUniverse, effectiveConstructor.name);
+      $constructor.$ccache = rti;
+      return rti;
+    },
+    getTypeFromTypesTable: function(_index) {
+      var rti,
+        index = _index,
+        table = init.types,
+        type = table[index];
+      if (typeof type == "string") {
+        rti = H._Universe_eval(init.typeUniverse, type);
+        table[index] = rti;
+        return rti;
+      }
+      return type;
+    },
+    createRuntimeType: function(rti) {
+      var type = rti._cachedRuntimeType;
+      if (type != null)
+        return type;
+      return rti._cachedRuntimeType = new H._Type(rti);
+    },
+    typeLiteral: function(recipe) {
+      return H.createRuntimeType(H._Universe_eval(init.typeUniverse, recipe));
+    },
+    _installSpecializedIsTest: function(object) {
+      var s, key, testRti = this,
+        t1 = testRti._kind,
+        isFn = H._generalIsTestImplementation;
+      if (H.isTopType(testRti, true)) {
+        isFn = H._isTop;
+        testRti._check = testRti._as = H._asTop;
+      } else if (t1 === 9) {
+        s = testRti._canonicalRecipe;
+        if (H.assertTest(typeof s == "string"))
+          H.assertThrow("Missing canonical recipe");
+        key = s;
+        if ("int" === key)
+          isFn = H._isInt;
+        else if ("double" === key)
+          isFn = H._isNum;
+        else if ("num" === key)
+          isFn = H._isNum;
+        else if ("String" === key)
+          isFn = H._isString;
+        else if ("bool" === key)
+          isFn = H._isBool;
+        else {
+          H.assertHelper(testRti._kind === 9);
+          t1 = testRti._primary;
+          if (H.Rti__getInterfaceTypeArguments(testRti).every(H.isLegacyTopType)) {
+            testRti._specializedTestResource = "$is" + t1;
+            isFn = H._isTestViaProperty;
+          }
+        }
+      }
+      testRti._is = isFn;
+      return testRti._is(object);
+    },
+    _generalIsTestImplementation: function(object) {
+      var testRti = this;
+      return H._isSubtype(init.typeUniverse, H.instanceOrFunctionType(object, testRti), null, testRti, null, true);
+    },
+    _isTestViaProperty: function(object) {
+      var tag = this._specializedTestResource;
+      if (object instanceof P.Object)
+        return !!object[tag];
+      return !!J.getInterceptor$(object)[tag];
+    },
+    _generalAsCheckImplementation: function(object) {
+      var testRti;
+      if (object == null)
+        return object;
+      testRti = this;
+      if (testRti._is(object))
+        return object;
+      throw H.wrapException(H._CastError$fromMessage(H._Error_compose(object, H.instanceOrFunctionType(object, testRti), H._rtiToString(testRti, null))));
+    },
+    _generalTypeCheckImplementation: function(object) {
+      var testRti;
+      if (object == null)
+        return object;
+      testRti = this;
+      if (testRti._is(object))
+        return object;
+      throw H.wrapException(H._TypeError$fromMessage(H._Error_compose(object, H.instanceOrFunctionType(object, testRti), H._rtiToString(testRti, null))));
+    },
+    checkTypeBound: function(type, bound, variable, methodName) {
+      var _null = null;
+      if (H._isSubtype(init.typeUniverse, type, _null, bound, _null, true))
+        return type;
+      throw H.wrapException(H._TypeError$fromMessage("The type argument '" + H.S(H._rtiToString(type, _null)) + "' is not a subtype of the type variable bound '" + H.S(H._rtiToString(bound, _null)) + "' of type variable '" + variable + "' in '" + H.S(methodName) + "'."));
+    },
+    _Error_compose: function(object, objectRti, checkedTypeDescription) {
+      var objectDescription = P.Error_safeToString(object),
+        objectTypeDescription = H._rtiToString(objectRti == null ? H.instanceType(object) : objectRti, null);
+      return objectDescription + ": type '" + H.S(objectTypeDescription) + "' is not a subtype of type '" + H.S(checkedTypeDescription) + "'";
+    },
+    _CastError$fromMessage: function(message) {
+      return new H._CastError("CastError: " + message);
+    },
+    _CastError__CastError$forType: function(object, type) {
+      return new H._CastError("CastError: " + H._Error_compose(object, null, type));
+    },
+    _TypeError$fromMessage: function(message) {
+      return new H._TypeError("TypeError: " + message);
+    },
+    _TypeError__TypeError$forType: function(object, type) {
+      return new H._TypeError("TypeError: " + H._Error_compose(object, null, type));
+    },
+    _isTop: function(object) {
+      return true;
+    },
+    _asTop: function(object) {
+      return object;
+    },
+    _isBool: function(object) {
+      return true === object || false === object;
+    },
+    _asBoolNullable: function(object) {
+      if (true === object || false === object)
+        return object;
+      if (object == null)
+        return object;
+      throw H.wrapException(H._CastError__CastError$forType(object, "bool"));
+    },
+    _checkBoolNullable: function(object) {
+      if (true === object || false === object)
+        return object;
+      if (object == null)
+        return object;
+      throw H.wrapException(H._TypeError__TypeError$forType(object, "bool"));
+    },
+    _asDoubleNullable: function(object) {
+      if (typeof object == "number")
+        return object;
+      if (object == null)
+        return object;
+      throw H.wrapException(H._CastError__CastError$forType(object, "double"));
+    },
+    _checkDoubleNullable: function(object) {
+      if (typeof object == "number")
+        return object;
+      if (object == null)
+        return object;
+      throw H.wrapException(H._TypeError__TypeError$forType(object, "double"));
+    },
+    _isInt: function(object) {
+      return typeof object == "number" && Math.floor(object) === object;
+    },
+    _asIntNullable: function(object) {
+      if (typeof object == "number" && Math.floor(object) === object)
+        return object;
+      if (object == null)
+        return object;
+      throw H.wrapException(H._CastError__CastError$forType(object, "int"));
+    },
+    _checkIntNullable: function(object) {
+      if (typeof object == "number" && Math.floor(object) === object)
+        return object;
+      if (object == null)
+        return object;
+      throw H.wrapException(H._TypeError__TypeError$forType(object, "int"));
+    },
+    _isNum: function(object) {
+      return typeof object == "number";
+    },
+    _asNumNullable: function(object) {
+      if (typeof object == "number")
+        return object;
+      if (object == null)
+        return object;
+      throw H.wrapException(H._CastError__CastError$forType(object, "num"));
+    },
+    _checkNumNullable: function(object) {
+      if (typeof object == "number")
+        return object;
+      if (object == null)
+        return object;
+      throw H.wrapException(H._TypeError__TypeError$forType(object, "num"));
+    },
+    _isString: function(object) {
+      return typeof object == "string";
+    },
+    _asStringNullable: function(object) {
+      if (typeof object == "string")
+        return object;
+      if (object == null)
+        return object;
+      throw H.wrapException(H._CastError__CastError$forType(object, "String"));
+    },
+    _checkStringNullable: function(object) {
+      if (typeof object == "string")
+        return object;
+      if (object == null)
+        return object;
+      throw H.wrapException(H._TypeError__TypeError$forType(object, "String"));
+    },
+    _rtiArrayToString: function(array, genericContext) {
+      var s, sep, i;
+      for (s = "", sep = "", i = 0; i < array.length; ++i, sep = ", ")
+        s += C.JSString_methods.$add(sep, H._rtiToString(array[i], genericContext));
+      return s;
+    },
+    _functionRtiToString: function(functionType, genericContext, bounds) {
+      var boundsLength, outerContextLength, offset, i, typeParametersText, typeSep, t1, t2, boundRti, parameters, requiredPositional, requiredPositionalLength, optionalPositional, optionalPositionalLength, optionalNamed, optionalNamedLength, returnTypeText, argumentsText, sep, _s2_ = ", ";
+      if (bounds != null) {
+        boundsLength = bounds.length;
+        if (genericContext == null) {
+          genericContext = H.setRuntimeTypeInfo([], type$.JSArray_String);
+          outerContextLength = null;
+        } else
+          outerContextLength = genericContext.length;
+        offset = genericContext.length;
+        for (i = boundsLength; i > 0; --i)
+          C.JSArray_methods.add$1(genericContext, "T" + (offset + i));
+        for (typeParametersText = "<", typeSep = "", i = 0; i < boundsLength; ++i, typeSep = _s2_) {
+          typeParametersText += typeSep;
+          t1 = genericContext.length;
+          t2 = t1 - 1 - i;
+          if (t2 < 0)
+            return H.ioore(genericContext, t2);
+          typeParametersText = C.JSString_methods.$add(typeParametersText, genericContext[t2]);
+          boundRti = bounds[i];
+          if (!H.isTopType(boundRti, true))
+            typeParametersText += C.JSString_methods.$add(" extends ", H._rtiToString(boundRti, genericContext));
+        }
+        typeParametersText += ">";
+      } else {
+        typeParametersText = "";
+        outerContextLength = null;
+      }
+      H.assertHelper(functionType._kind === 11);
+      t1 = functionType._primary;
+      parameters = H.Rti__getFunctionParameters(functionType);
+      requiredPositional = parameters._requiredPositional;
+      requiredPositionalLength = requiredPositional.length;
+      optionalPositional = parameters._optionalPositional;
+      optionalPositionalLength = optionalPositional.length;
+      optionalNamed = parameters._optionalNamed;
+      optionalNamedLength = optionalNamed.length;
+      H.assertHelper(optionalPositionalLength === 0 || optionalNamedLength === 0);
+      returnTypeText = H._rtiToString(t1, genericContext);
+      for (argumentsText = "", sep = "", i = 0; i < requiredPositionalLength; ++i, sep = _s2_)
+        argumentsText += C.JSString_methods.$add(sep, H._rtiToString(requiredPositional[i], genericContext));
+      if (optionalPositionalLength > 0) {
+        argumentsText += sep + "[";
+        for (sep = "", i = 0; i < optionalPositionalLength; ++i, sep = _s2_)
+          argumentsText += C.JSString_methods.$add(sep, H._rtiToString(optionalPositional[i], genericContext));
+        argumentsText += "]";
+      }
+      if (optionalNamedLength > 0) {
+        argumentsText += sep + "{";
+        for (sep = "", i = 0; i < optionalNamedLength; i += 2, sep = _s2_)
+          argumentsText += C.JSString_methods.$add(sep, H._rtiToString(optionalNamed[i + 1], genericContext)) + " " + optionalNamed[i];
+        argumentsText += "}";
+      }
+      if (outerContextLength != null)
+        genericContext.length = outerContextLength;
+      return typeParametersText + "(" + argumentsText + ") => " + H.S(returnTypeText);
+    },
+    _rtiToString: function(rti, genericContext) {
+      var $name, $arguments, t2,
+        t1 = rti._kind,
+        kind = t1;
+      if (kind === 5)
+        return "erased";
+      if (kind === 2)
+        return "dynamic";
+      if (kind === 3)
+        return "void";
+      if (kind === 1)
+        return "Never";
+      if (kind === 4)
+        return "any";
+      if (kind === 6) {
+        H.assertHelper(t1 === 6);
+        return H.S(H._rtiToString(rti._primary, genericContext)) + "*";
+      }
+      if (kind === 7) {
+        H.assertHelper(t1 === 7);
+        return H.S(H._rtiToString(rti._primary, genericContext)) + "?";
+      }
+      if (kind === 8) {
+        H.assertHelper(t1 === 8);
+        return "FutureOr<" + H.S(H._rtiToString(rti._primary, genericContext)) + ">";
+      }
+      if (kind === 9) {
+        H.assertHelper(t1 === 9);
+        $name = H._unminifyOrTag(rti._primary);
+        $arguments = H.Rti__getInterfaceTypeArguments(rti);
+        return $arguments.length !== 0 ? $name + ("<" + H._rtiArrayToString($arguments, genericContext) + ">") : $name;
+      }
+      if (kind === 11)
+        return H._functionRtiToString(rti, genericContext, null);
+      if (kind === 12) {
+        H.assertHelper(t1 === 12);
+        return H._functionRtiToString(rti._primary, genericContext, H.Rti__getGenericFunctionBounds(rti));
+      }
+      if (kind === 13) {
+        H.assertHelper(t1 === 13);
+        t1 = rti._primary;
+        t2 = genericContext.length;
+        t1 = t2 - 1 - t1;
+        if (t1 < 0 || t1 >= t2)
+          return H.ioore(genericContext, t1);
+        return genericContext[t1];
+      }
+      return "?";
+    },
+    _unminifyOrTag: function(rawClassName) {
+      var preserved = H.unmangleGlobalNameIfPreservedAnyways(rawClassName);
+      if (preserved != null)
+        return preserved;
+      return rawClassName;
+    },
+    _Universe_findRule: function(universe, targetType) {
+      var rule = universe.tR[targetType];
+      for (; typeof rule == "string";)
+        rule = universe.tR[rule];
+      return rule;
+    },
+    _Universe_findErasedType: function(universe, cls) {
+      var $length, erased, $arguments, i, $interface,
+        metadata = universe.eT,
+        probe = metadata[cls];
+      if (probe == null)
+        return H._Universe_eval(universe, cls);
+      else if (typeof probe == "number") {
+        $length = probe;
+        erased = H._Universe__lookupTerminalRti(universe, 5, "#");
+        $arguments = [];
+        for (i = 0; i < $length; ++i)
+          $arguments.push(erased);
+        $interface = H._Universe__lookupInterfaceRti(universe, cls, $arguments);
+        metadata[cls] = $interface;
+        return $interface;
+      } else
+        return probe;
+    },
+    _Universe_addRules: function(universe, rules) {
+      return H._Utils_objectAssign(universe.tR, rules);
+    },
+    _Universe_addErasedTypes: function(universe, types) {
+      return H._Utils_objectAssign(universe.eT, types);
+    },
+    _Universe_eval: function(universe, recipe) {
+      var rti,
+        cache = universe.eC,
+        probe = cache.get(recipe);
+      if (probe != null)
+        return probe;
+      rti = H._Universe__parseRecipe(universe, null, recipe);
+      cache.set(recipe, rti);
+      return rti;
+    },
+    _Universe_evalInEnvironment: function(universe, environment, recipe) {
+      var probe, rti,
+        cache = environment._evalCache;
+      if (cache == null)
+        cache = environment._evalCache = new Map();
+      probe = cache.get(recipe);
+      if (probe != null)
+        return probe;
+      rti = H._Universe__parseRecipe(universe, environment, recipe);
+      cache.set(recipe, rti);
+      return rti;
+    },
+    _Universe_bind: function(universe, environment, argumentsRti) {
+      var s, argumentsRecipe, probe, rti,
+        cache = environment._bindCache;
+      if (cache == null)
+        cache = environment._bindCache = new Map();
+      s = argumentsRti._canonicalRecipe;
+      if (H.assertTest(typeof s == "string"))
+        H.assertThrow("Missing canonical recipe");
+      argumentsRecipe = s;
+      probe = cache.get(argumentsRecipe);
+      if (probe != null)
+        return probe;
+      rti = H._Universe__lookupBindingRti(universe, environment, argumentsRti._kind === 10 ? H.Rti__getBindingArguments(argumentsRti) : [argumentsRti]);
+      cache.set(argumentsRecipe, rti);
+      return rti;
+    },
+    _Universe__parseRecipe: function(universe, environment, recipe) {
+      var rti = H._Parser_parse(H._Parser_create(universe, environment, recipe));
+      return rti;
+    },
+    _Universe__finishRti: function(universe, rti) {
+      var s = rti._canonicalRecipe;
+      if (H.assertTest(typeof s == "string"))
+        H.assertThrow("Missing canonical recipe");
+      universe.eC.set(s, rti);
+      rti._as = H._generalAsCheckImplementation;
+      rti._check = H._generalTypeCheckImplementation;
+      rti._is = H._installSpecializedIsTest;
+      return rti;
+    },
+    _Universe__lookupTerminalRti: function(universe, kind, canonicalRecipe) {
+      var rti,
+        probe = universe.eC.get(canonicalRecipe);
+      if (probe != null)
+        return probe;
+      rti = new H.Rti(null, null, null);
+      rti._kind = kind;
+      rti._canonicalRecipe = canonicalRecipe;
+      return H._Universe__finishRti(universe, rti);
+    },
+    _Universe__lookupUnaryRti: function(universe, kind, baseType, canonicalRecipe) {
+      var rti,
+        probe = universe.eC.get(canonicalRecipe);
+      if (probe != null)
+        return probe;
+      rti = new H.Rti(null, null, null);
+      rti._kind = kind;
+      rti._primary = baseType;
+      rti._canonicalRecipe = canonicalRecipe;
+      return H._Universe__finishRti(universe, rti);
+    },
+    _Universe__lookupGenericFunctionParameterRti: function(universe, index) {
+      var rti,
+        canonicalRecipe = "" + index + "^",
+        probe = universe.eC.get(canonicalRecipe);
+      if (probe != null)
+        return probe;
+      rti = new H.Rti(null, null, null);
+      rti._kind = 13;
+      rti._primary = index;
+      rti._canonicalRecipe = canonicalRecipe;
+      return H._Universe__finishRti(universe, rti);
+    },
+    _Universe__canonicalRecipeJoin: function($arguments) {
+      var s, sep, i, s0,
+        $length = $arguments.length;
+      for (s = "", sep = "", i = 0; i < $length; ++i, sep = ",") {
+        s0 = $arguments[i]._canonicalRecipe;
+        if (H.assertTest(typeof s0 == "string"))
+          H.assertThrow("Missing canonical recipe");
+        s += sep + s0;
+      }
+      return s;
+    },
+    _Universe__canonicalRecipeJoinNamed: function($arguments) {
+      var s, sep, i, t1, s0,
+        $length = $arguments.length;
+      H.assertHelper(($length & 1) === 0);
+      for (s = "", sep = "", i = 0; i < $length; i += 2, sep = ",") {
+        t1 = $arguments[i];
+        s0 = $arguments[i + 1]._canonicalRecipe;
+        if (H.assertTest(typeof s0 == "string"))
+          H.assertThrow("Missing canonical recipe");
+        s += sep + t1 + ":" + s0;
+      }
+      return s;
+    },
+    _Universe__lookupInterfaceRti: function(universe, $name, $arguments) {
+      var s, probe, rti;
+      H.assertHelper(typeof $name == "string");
+      s = $name;
+      if ($arguments.length !== 0)
+        s += "<" + H._Universe__canonicalRecipeJoin($arguments) + ">";
+      probe = universe.eC.get(s);
+      if (probe != null)
+        return probe;
+      rti = new H.Rti(null, null, null);
+      rti._kind = 9;
+      rti._primary = $name;
+      rti._rest = $arguments;
+      if ($arguments.length > 0)
+        rti._precomputed1 = $arguments[0];
+      rti._canonicalRecipe = s;
+      return H._Universe__finishRti(universe, rti);
+    },
+    _Universe__lookupBindingRti: function(universe, base, $arguments) {
+      var newBase, newArguments, s, probe, rti,
+        t1 = base._kind;
+      if (t1 === 10) {
+        H.assertHelper(t1 === 10);
+        newBase = base._primary;
+        newArguments = H.Rti__getBindingArguments(base).concat($arguments);
+      } else {
+        newArguments = $arguments;
+        newBase = base;
+      }
+      s = newBase._canonicalRecipe;
+      if (H.assertTest(typeof s == "string"))
+        H.assertThrow("Missing canonical recipe");
+      s = s + ";" + ("<" + H._Universe__canonicalRecipeJoin(newArguments) + ">");
+      probe = universe.eC.get(s);
+      if (probe != null)
+        return probe;
+      rti = new H.Rti(null, null, null);
+      rti._kind = 10;
+      rti._primary = newBase;
+      rti._rest = newArguments;
+      rti._canonicalRecipe = s;
+      return H._Universe__finishRti(universe, rti);
+    },
+    _Universe__lookupFunctionRti: function(universe, returnType, parameters) {
+      var requiredPositional, requiredPositionalLength, optionalPositional, optionalPositionalLength, optionalNamed, optionalNamedLength, recipe, key, probe, rti,
+        s = returnType._canonicalRecipe;
+      if (H.assertTest(typeof s == "string"))
+        H.assertThrow("Missing canonical recipe");
+      requiredPositional = parameters._requiredPositional;
+      requiredPositionalLength = requiredPositional.length;
+      optionalPositional = parameters._optionalPositional;
+      optionalPositionalLength = optionalPositional.length;
+      optionalNamed = parameters._optionalNamed;
+      optionalNamedLength = optionalNamed.length;
+      H.assertHelper(optionalPositionalLength === 0 || optionalNamedLength === 0);
+      recipe = "(" + H._Universe__canonicalRecipeJoin(requiredPositional);
+      if (optionalPositionalLength > 0)
+        recipe += (requiredPositionalLength > 0 ? "," : "") + "[" + H._Universe__canonicalRecipeJoin(optionalPositional) + "]";
+      if (optionalNamedLength > 0)
+        recipe += (requiredPositionalLength > 0 ? "," : "") + "{" + H._Universe__canonicalRecipeJoinNamed(optionalNamed) + "}";
+      key = s + (recipe + ")");
+      probe = universe.eC.get(key);
+      if (probe != null)
+        return probe;
+      rti = new H.Rti(null, null, null);
+      rti._kind = 11;
+      rti._primary = returnType;
+      rti._rest = parameters;
+      rti._canonicalRecipe = key;
+      return H._Universe__finishRti(universe, rti);
+    },
+    _Universe__lookupGenericFunctionRti: function(universe, baseFunctionType, bounds) {
+      var key, probe, rti,
+        s = baseFunctionType._canonicalRecipe;
+      if (H.assertTest(typeof s == "string"))
+        H.assertThrow("Missing canonical recipe");
+      key = s + "<" + H._Universe__canonicalRecipeJoin(bounds) + ">";
+      probe = universe.eC.get(key);
+      if (probe != null)
+        return probe;
+      rti = new H.Rti(null, null, null);
+      rti._kind = 12;
+      rti._primary = baseFunctionType;
+      rti._rest = bounds;
+      rti._canonicalRecipe = key;
+      return H._Universe__finishRti(universe, rti);
+    },
+    _Parser_create: function(universe, environment, recipe) {
+      return {u: universe, e: environment, r: recipe, s: [], p: 0};
+    },
+    _Parser_parse: function(parser) {
+      var t1, i, ch, t2, t3, universe, array, head, base, u, s, parameters, optionalPositional, optionalNamed, item,
+        _s24_ = "Missing canonical recipe",
+        source = parser.r,
+        stack = parser.s;
+      for (t1 = source.length, i = 0; i < t1;) {
+        ch = source.charCodeAt(i);
+        if (ch >= 48 && ch <= 57)
+          i = H._Parser_handleDigit(i + 1, ch, source, stack);
+        else if ((((ch | 32) >>> 0) - 97 & 65535) < 26 || ch === 95 || ch === 36)
+          i = H._Parser_handleIdentifier(parser, i, source, stack, false);
+        else if (ch === 46)
+          i = H._Parser_handleIdentifier(parser, i, source, stack, true);
+        else {
+          ++i;
+          switch (ch) {
+            case 44:
+              break;
+            case 58:
+              break;
+            case 59:
+              stack.push(H._Parser_toType(parser.u, parser.e, stack.pop()));
+              break;
+            case 94:
+              t2 = parser.u;
+              t3 = stack.pop();
+              H.assertHelper(typeof t3 == "number");
+              stack.push(H._Universe__lookupGenericFunctionParameterRti(t2, t3));
+              break;
+            case 35:
+              stack.push(H._Universe__lookupTerminalRti(parser.u, 5, "#"));
+              break;
+            case 64:
+              stack.push(H._Universe__lookupTerminalRti(parser.u, 2, "@"));
+              break;
+            case 126:
+              stack.push(H._Universe__lookupTerminalRti(parser.u, 3, "~"));
+              break;
+            case 60:
+              stack.push(parser.p);
+              parser.p = stack.length;
+              break;
+            case 62:
+              universe = parser.u;
+              array = stack.splice(parser.p);
+              H._Parser_toTypes(parser.u, parser.e, array);
+              parser.p = stack.pop();
+              head = stack.pop();
+              if (typeof head == "string")
+                stack.push(H._Universe__lookupInterfaceRti(universe, head, array));
+              else {
+                base = H._Parser_toType(universe, parser.e, head);
+                switch (base._kind) {
+                  case 11:
+                    stack.push(H._Universe__lookupGenericFunctionRti(universe, base, array));
+                    break;
+                  default:
+                    stack.push(H._Universe__lookupBindingRti(universe, base, array));
+                    break;
+                }
+              }
+              break;
+            case 38:
+              H._Parser_handleExtendedOperations(parser, stack);
+              break;
+            case 42:
+              u = parser.u;
+              t2 = H._Parser_toType(u, parser.e, stack.pop());
+              s = t2._canonicalRecipe;
+              if (H.assertTest(typeof s == "string"))
+                H.assertThrow(_s24_);
+              stack.push(H._Universe__lookupUnaryRti(u, 6, t2, s + "*"));
+              break;
+            case 63:
+              u = parser.u;
+              t2 = H._Parser_toType(u, parser.e, stack.pop());
+              s = t2._canonicalRecipe;
+              if (H.assertTest(typeof s == "string"))
+                H.assertThrow(_s24_);
+              stack.push(H._Universe__lookupUnaryRti(u, 7, t2, s + "?"));
+              break;
+            case 47:
+              u = parser.u;
+              t2 = H._Parser_toType(u, parser.e, stack.pop());
+              s = t2._canonicalRecipe;
+              if (H.assertTest(typeof s == "string"))
+                H.assertThrow(_s24_);
+              stack.push(H._Universe__lookupUnaryRti(u, 8, t2, s + "/"));
+              break;
+            case 40:
+              stack.push(parser.p);
+              parser.p = stack.length;
+              break;
+            case 41:
+              universe = parser.u;
+              parameters = new H._FunctionParameters();
+              optionalPositional = universe.sEA;
+              optionalNamed = universe.sEA;
+              head = stack.pop();
+              if (typeof head == "number")
+                switch (head) {
+                  case -1:
+                    optionalPositional = stack.pop();
+                    break;
+                  case -2:
+                    optionalNamed = stack.pop();
+                    break;
+                  default:
+                    stack.push(head);
+                    break;
+                }
+              else
+                stack.push(head);
+              array = stack.splice(parser.p);
+              H._Parser_toTypes(parser.u, parser.e, array);
+              parser.p = stack.pop();
+              parameters._requiredPositional = array;
+              parameters._optionalPositional = optionalPositional;
+              parameters._optionalNamed = optionalNamed;
+              stack.push(H._Universe__lookupFunctionRti(universe, H._Parser_toType(universe, parser.e, stack.pop()), parameters));
+              break;
+            case 91:
+              stack.push(parser.p);
+              parser.p = stack.length;
+              break;
+            case 93:
+              array = stack.splice(parser.p);
+              H._Parser_toTypes(parser.u, parser.e, array);
+              parser.p = stack.pop();
+              stack.push(array);
+              stack.push(-1);
+              break;
+            case 123:
+              stack.push(parser.p);
+              parser.p = stack.length;
+              break;
+            case 125:
+              array = stack.splice(parser.p);
+              H._Parser_toTypesNamed(parser.u, parser.e, array);
+              parser.p = stack.pop();
+              stack.push(array);
+              stack.push(-2);
+              break;
+            default:
+              throw "Bad character " + ch;
+          }
+        }
+      }
+      item = stack.pop();
+      return H._Parser_toType(parser.u, parser.e, item);
+    },
+    _Parser_handleDigit: function(i, digit, source, stack) {
+      var t1, ch,
+        value = digit - 48;
+      for (t1 = source.length; i < t1; ++i) {
+        ch = source.charCodeAt(i);
+        if (!(ch >= 48 && ch <= 57))
+          break;
+        value = value * 10 + (ch - 48);
+      }
+      stack.push(value);
+      return i;
+    },
+    _Parser_handleIdentifier: function(parser, start, source, stack, hasPeriod) {
+      var t1, ch, t2, string, environment, rule, recipe,
+        i = start + 1;
+      for (t1 = source.length; i < t1; ++i) {
+        ch = source.charCodeAt(i);
+        if (ch === 46) {
+          if (hasPeriod)
+            break;
+          hasPeriod = true;
+        } else {
+          if (!((((ch | 32) >>> 0) - 97 & 65535) < 26 || ch === 95 || ch === 36))
+            t2 = ch >= 48 && ch <= 57;
+          else
+            t2 = true;
+          if (!t2)
+            break;
+        }
+      }
+      string = source.substring(start, i);
+      if (hasPeriod) {
+        t1 = parser.u;
+        environment = parser.e;
+        t2 = environment._kind;
+        if (t2 === 10) {
+          H.assertHelper(t2 === 10);
+          environment = environment._primary;
+        }
+        H.assertHelper(environment._kind === 9);
+        rule = H._Universe_findRule(t1, environment._primary);
+        H.assertHelper(rule != null);
+        recipe = rule[string];
+        if (recipe == null)
+          H.throwExpression('No "' + string + '" in "' + H.Rti__getCanonicalRecipe(environment) + '"');
+        stack.push(H._Universe_evalInEnvironment(t1, environment, recipe));
+      } else
+        stack.push(string);
+      return i;
+    },
+    _Parser_handleExtendedOperations: function(parser, stack) {
+      var $top = stack.pop();
+      if (0 === $top) {
+        stack.push(H._Universe__lookupTerminalRti(parser.u, 1, "0&"));
+        return;
+      }
+      if (1 === $top) {
+        stack.push(H._Universe__lookupTerminalRti(parser.u, 4, "1&"));
+        return;
+      }
+      throw H.wrapException(P.AssertionError$("Unexpected extended operation " + H.S($top)));
+    },
+    _Parser_toType: function(universe, environment, item) {
+      if (typeof item == "string")
+        return H._Universe__lookupInterfaceRti(universe, item, universe.sEA);
+      else if (typeof item == "number")
+        return H._Parser_indexToType(universe, environment, item);
+      else
+        return item;
+    },
+    _Parser_toTypes: function(universe, environment, items) {
+      var i,
+        $length = items.length;
+      for (i = 0; i < $length; ++i)
+        items[i] = H._Parser_toType(universe, environment, items[i]);
+    },
+    _Parser_toTypesNamed: function(universe, environment, items) {
+      var i,
+        $length = items.length;
+      H.assertHelper(($length & 1) === 0);
+      for (i = 1; i < $length; i += 2)
+        items[i] = H._Parser_toType(universe, environment, items[i]);
+    },
+    _Parser_indexToType: function(universe, environment, index) {
+      var typeArguments, len,
+        t1 = environment._kind,
+        kind = t1;
+      if (kind === 10) {
+        if (index === 0) {
+          H.assertHelper(t1 === 10);
+          return environment._primary;
+        }
+        typeArguments = H.Rti__getBindingArguments(environment);
+        len = typeArguments.length;
+        if (index <= len)
+          return typeArguments[index - 1];
+        index -= len;
+        H.assertHelper(t1 === 10);
+        environment = environment._primary;
+        kind = environment._kind;
+      } else if (index === 0)
+        return environment;
+      if (kind !== 9)
+        throw H.wrapException(P.AssertionError$("Indexed base must be an interface type"));
+      typeArguments = H.Rti__getInterfaceTypeArguments(environment);
+      if (index <= typeArguments.length)
+        return typeArguments[index - 1];
+      throw H.wrapException(P.AssertionError$("Bad index " + index + " for " + environment.toString$0(0)));
+    },
+    _isSubtype: function(universe, s, sEnv, t, tEnv, isLegacy) {
+      var sKind, leftTypeVariable, t1, tKind, sBounds, tBounds;
+      if (s === t)
+        return true;
+      if (H.isTopType(t, true))
+        return true;
+      sKind = s._kind;
+      if (sKind === 4)
+        return true;
+      if (H.isTopType(s, true))
+        return false;
+      if (s === type$.Null)
+        return true;
+      leftTypeVariable = sKind === 13;
+      if (leftTypeVariable) {
+        H.assertHelper(s._kind === 13);
+        if (H._isSubtype(universe, sEnv[s._primary], sEnv, t, tEnv, true))
+          return true;
+      }
+      t1 = t._kind;
+      tKind = t1;
+      if (sKind === 6) {
+        H.assertHelper(s._kind === 6);
+        return H._isSubtype(universe, s._primary, sEnv, t, tEnv, true);
+      }
+      if (tKind === 6) {
+        H.assertHelper(t1 === 6);
+        t1 = t._primary;
+        return H._isSubtype(universe, s, sEnv, t1, tEnv, true);
+      }
+      if (sKind === 8) {
+        H.assertHelper(s._kind === 8);
+        if (!H._isSubtype(universe, s._primary, sEnv, t, tEnv, true))
+          return false;
+        return H._isSubtype(universe, H.Rti__getFutureFromFutureOr(universe, s), sEnv, t, tEnv, true);
+      }
+      if (sKind === 7) {
+        H.assertHelper(s._kind === 7);
+        t1 = H._isSubtype(universe, s._primary, sEnv, t, tEnv, true);
+        return t1;
+      }
+      if (tKind === 8) {
+        H.assertHelper(t1 === 8);
+        if (H._isSubtype(universe, s, sEnv, t._primary, tEnv, true))
+          return true;
+        return H._isSubtype(universe, s, sEnv, H.Rti__getFutureFromFutureOr(universe, t), tEnv, true);
+      }
+      if (tKind === 7) {
+        H.assertHelper(t1 === 7);
+        t1 = H._isSubtype(universe, s, sEnv, t._primary, tEnv, true);
+        return t1;
+      }
+      if (leftTypeVariable)
+        return false;
+      t1 = sKind !== 11;
+      if ((!t1 || sKind === 12) && t === type$.Function)
+        return true;
+      if (tKind === 12) {
+        if (s === type$.JavaScriptFunction)
+          return true;
+        if (sKind !== 12)
+          return false;
+        sBounds = H.Rti__getGenericFunctionBounds(s);
+        tBounds = H.Rti__getGenericFunctionBounds(t);
+        if (!H.typesEqual(sBounds, tBounds, true))
+          return false;
+        sEnv = sEnv == null ? sBounds : sBounds.concat(sEnv);
+        tEnv = tEnv == null ? tBounds : tBounds.concat(tEnv);
+        H.assertHelper(s._kind === 12);
+        t1 = s._primary;
+        H.assertHelper(t._kind === 12);
+        return H._isFunctionSubtype(universe, t1, sEnv, t._primary, tEnv, true);
+      }
+      if (tKind === 11) {
+        if (s === type$.JavaScriptFunction)
+          return true;
+        if (t1)
+          return false;
+        return H._isFunctionSubtype(universe, s, sEnv, t, tEnv, true);
+      }
+      if (sKind === 9) {
+        if (tKind !== 9)
+          return false;
+        return H._isInterfaceSubtype(universe, s, sEnv, t, tEnv, true);
+      }
+      return false;
+    },
+    _isFunctionSubtype: function(universe, s, sEnv, t, tEnv, isLegacy) {
+      var t1, sParameters, tParameters, sRequiredPositional, tRequiredPositional, sRequiredPositionalLength, tRequiredPositionalLength, requiredPositionalDelta, sOptionalPositional, tOptionalPositional, sOptionalPositionalLength, tOptionalPositionalLength, i, sOptionalNamed, tOptionalNamed, sOptionalNamedLength, tOptionalNamedLength, j, tName, sName;
+      H.assertHelper(s._kind === 11);
+      H.assertHelper(t._kind === 11);
+      H.assertHelper(s._kind === 11);
+      t1 = s._primary;
+      H.assertHelper(t._kind === 11);
+      if (!H._isSubtype(universe, t1, sEnv, t._primary, tEnv, true))
+        return false;
+      sParameters = H.Rti__getFunctionParameters(s);
+      tParameters = H.Rti__getFunctionParameters(t);
+      sRequiredPositional = sParameters._requiredPositional;
+      tRequiredPositional = tParameters._requiredPositional;
+      sRequiredPositionalLength = sRequiredPositional.length;
+      tRequiredPositionalLength = tRequiredPositional.length;
+      if (sRequiredPositionalLength > tRequiredPositionalLength)
+        return false;
+      requiredPositionalDelta = tRequiredPositionalLength - sRequiredPositionalLength;
+      sOptionalPositional = sParameters._optionalPositional;
+      tOptionalPositional = tParameters._optionalPositional;
+      sOptionalPositionalLength = sOptionalPositional.length;
+      tOptionalPositionalLength = tOptionalPositional.length;
+      if (sRequiredPositionalLength + sOptionalPositionalLength < tRequiredPositionalLength + tOptionalPositionalLength)
+        return false;
+      for (i = 0; i < sRequiredPositionalLength; ++i) {
+        t1 = sRequiredPositional[i];
+        if (!H._isSubtype(universe, tRequiredPositional[i], tEnv, t1, sEnv, true))
+          return false;
+      }
+      for (i = 0; i < requiredPositionalDelta; ++i) {
+        t1 = sOptionalPositional[i];
+        if (!H._isSubtype(universe, tRequiredPositional[sRequiredPositionalLength + i], tEnv, t1, sEnv, true))
+          return false;
+      }
+      for (i = 0; i < tOptionalPositionalLength; ++i) {
+        t1 = sOptionalPositional[requiredPositionalDelta + i];
+        if (!H._isSubtype(universe, tOptionalPositional[i], tEnv, t1, sEnv, true))
+          return false;
+      }
+      sOptionalNamed = sParameters._optionalNamed;
+      tOptionalNamed = tParameters._optionalNamed;
+      sOptionalNamedLength = sOptionalNamed.length;
+      tOptionalNamedLength = tOptionalNamed.length;
+      for (i = 0, j = 0; j < tOptionalNamedLength; j += 2) {
+        tName = tOptionalNamed[j];
+        do {
+          if (i >= sOptionalNamedLength)
+            return false;
+          sName = sOptionalNamed[i];
+          i += 2;
+        } while (sName < tName);
+        if (tName < sName)
+          return false;
+        t1 = sOptionalNamed[i - 1];
+        if (!H._isSubtype(universe, tOptionalNamed[j + 1], tEnv, t1, sEnv, true))
+          return false;
+      }
+      return true;
+    },
+    _isInterfaceSubtype: function(universe, s, sEnv, t, tEnv, isLegacy) {
+      var sName, tName, sArgs, tArgs, $length, i, t1, t2, rule, supertypeArgs;
+      H.assertHelper(s._kind === 9);
+      sName = s._primary;
+      H.assertHelper(t._kind === 9);
+      tName = t._primary;
+      if (sName === tName) {
+        sArgs = H.Rti__getInterfaceTypeArguments(s);
+        tArgs = H.Rti__getInterfaceTypeArguments(t);
+        $length = sArgs.length;
+        H.assertHelper($length === tArgs.length);
+        for (i = 0; i < $length; ++i) {
+          t1 = sArgs[i];
+          t2 = tArgs[i];
+          if (!H._isSubtype(universe, t1, sEnv, t2, tEnv, true))
+            return false;
+        }
+        return true;
+      }
+      rule = H._Universe_findRule(universe, sName);
+      if (rule == null)
+        return false;
+      supertypeArgs = rule[tName];
+      if (supertypeArgs == null)
+        return false;
+      $length = supertypeArgs.length;
+      tArgs = H.Rti__getInterfaceTypeArguments(t);
+      H.assertHelper($length === tArgs.length);
+      for (i = 0; i < $length; ++i)
+        if (!H._isSubtype(universe, H._Universe_evalInEnvironment(universe, s, supertypeArgs[i]), sEnv, tArgs[i], tEnv, true))
+          return false;
+      return true;
+    },
+    typeEqual: function(s, t, isLegacy) {
+      var t1, sKind, t2;
+      if (s === t)
+        return true;
+      if (H.isTopType(s, true))
+        return H.isTopType(t, true);
+      t1 = s._kind;
+      sKind = t1;
+      if (sKind !== t._kind)
+        return false;
+      switch (sKind) {
+        case 6:
+        case 7:
+        case 8:
+          return H.typeEqual(s._primary, t._primary, true);
+        case 9:
+          H.assertHelper(t1 === 9);
+          t1 = s._primary;
+          H.assertHelper(t._kind === 9);
+          if (t1 !== t._primary)
+            return false;
+          return H.typesEqual(H.Rti__getInterfaceTypeArguments(s), H.Rti__getInterfaceTypeArguments(t), true);
+        case 10:
+          H.assertHelper(t1 === 10);
+          t1 = s._primary;
+          H.assertHelper(t._kind === 10);
+          return H.typeEqual(t1, t._primary, true) && H.typesEqual(H.Rti__getBindingArguments(s), H.Rti__getBindingArguments(t), true);
+        case 11:
+          H.assertHelper(t1 === 11);
+          t1 = s._primary;
+          H.assertHelper(t._kind === 11);
+          if (H.typeEqual(t1, t._primary, true)) {
+            t1 = H.Rti__getFunctionParameters(s);
+            t2 = H.Rti__getFunctionParameters(t);
+            t1 = H.typesEqual(t1._requiredPositional, t2._requiredPositional, true) && H.typesEqual(t1._optionalPositional, t2._optionalPositional, true) && H.namedTypesEqual(t1._optionalNamed, t2._optionalNamed, true);
+          } else
+            t1 = false;
+          return t1;
+        case 12:
+          H.assertHelper(t1 === 12);
+          t1 = s._primary;
+          H.assertHelper(t._kind === 12);
+          return H.typeEqual(t1, t._primary, true) && H.typesEqual(H.Rti__getGenericFunctionBounds(s), H.Rti__getGenericFunctionBounds(t), true);
+        default:
+          return false;
+      }
+    },
+    typesEqual: function(sArray, tArray, isLegacy) {
+      var i,
+        sLength = sArray.length;
+      if (sLength !== tArray.length)
+        return false;
+      for (i = 0; i < sLength; ++i)
+        if (!H.typeEqual(sArray[i], tArray[i], true))
+          return false;
+      return true;
+    },
+    namedTypesEqual: function(sArray, tArray, isLegacy) {
+      var i, t1,
+        sLength = sArray.length,
+        tLength = tArray.length;
+      H.assertHelper((sLength & 1) === 0);
+      H.assertHelper((tLength & 1) === 0);
+      if (sLength !== tLength)
+        return false;
+      for (i = 0; i < sLength; i += 2) {
+        if (sArray[i] !== tArray[i])
+          return false;
+        t1 = i + 1;
+        if (!H.typeEqual(sArray[t1], tArray[t1], true))
+          return false;
+      }
+      return true;
+    },
+    isLegacyTopType: function(t) {
+      return H.isTopType(t, true);
+    },
+    isTopType: function(t, isLegacy) {
+      var t1, kind;
+      if (t === type$.Object)
+        return true;
+      t1 = t._kind;
+      kind = t1;
+      if (kind !== 2)
+        if (kind !== 3)
+          if (kind !== 4)
+            if (kind !== 5)
+              if (kind === 8) {
+                H.assertHelper(t1 === 8);
+                t1 = H.isTopType(t._primary, true);
+              } else
+                t1 = false;
+            else
+              t1 = true;
+          else
+            t1 = true;
+        else
+          t1 = true;
+      else
+        t1 = true;
+      return t1;
+    },
+    _Utils_objectAssign: function(o, other) {
+      var i, key,
+        keys = Object.keys(other),
+        $length = keys.length;
+      for (i = 0; i < $length; ++i) {
+        key = keys[i];
+        o[key] = other[key];
+      }
+    },
+    Rti: function Rti(t0, t1, t2) {
+      var _ = this;
+      _._as = t0;
+      _._check = t1;
+      _._is = t2;
+      _._cachedRuntimeType = _._specializedTestResource = _._precomputed1 = null;
+      _._kind = 0;
+      _._canonicalRecipe = _._bindCache = _._evalCache = _._rest = _._primary = null;
+    },
+    _FunctionParameters: function _FunctionParameters() {
+      this._optionalNamed = this._optionalPositional = this._requiredPositional = null;
+    },
+    _Type: function _Type(t0) {
+      this._rti = t0;
+      this._hashCode = null;
+    },
+    _Error: function _Error() {
+    },
+    _CastError: function _CastError(t0) {
+      this._message = t0;
+    },
+    _TypeError: function _TypeError(t0) {
+      this._message = t0;
+    },
+    extractKeys: function(victim) {
+      return J.JSArray_JSArray$markFixed(victim ? Object.keys(victim) : [], type$.dynamic);
+    },
+    unmangleGlobalNameIfPreservedAnyways: function($name) {
+      return init.mangledGlobalNames[$name];
+    },
+    printString: function(string) {
+      if (typeof dartPrint == "function") {
+        dartPrint(string);
+        return;
+      }
+      if (typeof console == "object" && typeof console.log != "undefined") {
+        console.log(string);
+        return;
+      }
+      if (typeof window == "object")
+        return;
+      if (typeof print == "function") {
+        print(string);
+        return;
+      }
+      throw "Unable to print message: " + String(string);
+    }
+  },
+  J = {
+    makeDispatchRecord: function(interceptor, proto, extension, indexability) {
+      return {i: interceptor, p: proto, e: extension, x: indexability};
+    },
+    getNativeInterceptor: function(object) {
+      var proto, objectProto, $constructor, interceptor,
+        record = object[init.dispatchPropertyName];
+      if (record == null)
+        if ($.initNativeDispatchFlag == null) {
+          H.initNativeDispatch();
+          record = object[init.dispatchPropertyName];
+        }
+      if (record != null) {
+        proto = record.p;
+        if (false === proto)
+          return record.i;
+        if (true === proto)
+          return object;
+        objectProto = Object.getPrototypeOf(object);
+        if (proto === objectProto)
+          return record.i;
+        if (record.e === objectProto)
+          throw H.wrapException(P.UnimplementedError$("Return interceptor for " + H.S(proto(object, record))));
+      }
+      $constructor = object.constructor;
+      interceptor = $constructor == null ? null : $constructor[$.$get$JS_INTEROP_INTERCEPTOR_TAG()];
+      if (interceptor != null)
+        return interceptor;
+      interceptor = H.lookupAndCacheInterceptor(object);
+      if (interceptor != null)
+        return interceptor;
+      if (typeof object == "function")
+        return C.JavaScriptFunction_methods;
+      proto = Object.getPrototypeOf(object);
+      if (proto == null)
+        return C.PlainJavaScriptObject_methods;
+      if (proto === Object.prototype)
+        return C.PlainJavaScriptObject_methods;
+      if (typeof $constructor == "function") {
+        Object.defineProperty($constructor, $.$get$JS_INTEROP_INTERCEPTOR_TAG(), {value: C.UnknownJavaScriptObject_methods, enumerable: false, writable: true, configurable: true});
+        return C.UnknownJavaScriptObject_methods;
+      }
+      return C.UnknownJavaScriptObject_methods;
+    },
+    JSArray_JSArray$fixed: function($length, $E) {
+      if (!H._isInt($length))
+        throw H.wrapException(P.ArgumentError$value($length, "length", "is not an integer"));
+      if ($length < 0 || $length > 4294967295)
+        throw H.wrapException(P.RangeError$range($length, 0, 4294967295, "length", null));
+      return J.JSArray_JSArray$markFixed(new Array($length), $E);
+    },
+    JSArray_JSArray$markFixed: function(allocation, $E) {
+      return J.JSArray_markFixedList(H.setRuntimeTypeInfo(allocation, $E._eval$1("JSArray<0>")));
+    },
+    JSArray_markFixedList: function(list) {
+      list.fixed$length = Array;
+      return list;
+    },
+    JSString__isWhitespace: function(codeUnit) {
+      if (codeUnit < 256)
+        switch (codeUnit) {
+          case 9:
+          case 10:
+          case 11:
+          case 12:
+          case 13:
+          case 32:
+          case 133:
+          case 160:
+            return true;
+          default:
+            return false;
+        }
+      switch (codeUnit) {
+        case 5760:
+        case 8192:
+        case 8193:
+        case 8194:
+        case 8195:
+        case 8196:
+        case 8197:
+        case 8198:
+        case 8199:
+        case 8200:
+        case 8201:
+        case 8202:
+        case 8232:
+        case 8233:
+        case 8239:
+        case 8287:
+        case 12288:
+        case 65279:
+          return true;
+        default:
+          return false;
+      }
+    },
+    JSString__skipLeadingWhitespace: function(string, index) {
+      var t1, codeUnit;
+      for (t1 = string.length; index < t1;) {
+        codeUnit = C.JSString_methods._codeUnitAt$1(string, index);
+        if (codeUnit !== 32 && codeUnit !== 13 && !J.JSString__isWhitespace(codeUnit))
+          break;
+        ++index;
+      }
+      return index;
+    },
+    JSString__skipTrailingWhitespace: function(string, index) {
+      var index0, codeUnit;
+      for (; index > 0; index = index0) {
+        index0 = index - 1;
+        codeUnit = C.JSString_methods.codeUnitAt$1(string, index0);
+        if (codeUnit !== 32 && codeUnit !== 13 && !J.JSString__isWhitespace(codeUnit))
+          break;
+      }
+      return index;
+    },
+    getInterceptor$: function(receiver) {
+      if (typeof receiver == "number") {
+        if (Math.floor(receiver) == receiver)
+          return J.JSInt.prototype;
+        return J.JSDouble.prototype;
+      }
+      if (typeof receiver == "string")
+        return J.JSString.prototype;
+      if (receiver == null)
+        return J.JSNull.prototype;
+      if (typeof receiver == "boolean")
+        return J.JSBool.prototype;
+      if (receiver.constructor == Array)
+        return J.JSArray.prototype;
+      if (typeof receiver != "object") {
+        if (typeof receiver == "function")
+          return J.JavaScriptFunction.prototype;
+        return receiver;
+      }
+      if (receiver instanceof P.Object)
+        return receiver;
+      return J.getNativeInterceptor(receiver);
+    },
+    getInterceptor$ansx: function(receiver) {
+      if (typeof receiver == "number")
+        return J.JSNumber.prototype;
+      if (typeof receiver == "string")
+        return J.JSString.prototype;
+      if (receiver == null)
+        return receiver;
+      if (receiver.constructor == Array)
+        return J.JSArray.prototype;
+      if (typeof receiver != "object") {
+        if (typeof receiver == "function")
+          return J.JavaScriptFunction.prototype;
+        return receiver;
+      }
+      if (receiver instanceof P.Object)
+        return receiver;
+      return J.getNativeInterceptor(receiver);
+    },
+    getInterceptor$asx: function(receiver) {
+      if (typeof receiver == "string")
+        return J.JSString.prototype;
+      if (receiver == null)
+        return receiver;
+      if (receiver.constructor == Array)
+        return J.JSArray.prototype;
+      if (typeof receiver != "object") {
+        if (typeof receiver == "function")
+          return J.JavaScriptFunction.prototype;
+        return receiver;
+      }
+      if (receiver instanceof P.Object)
+        return receiver;
+      return J.getNativeInterceptor(receiver);
+    },
+    getInterceptor$ax: function(receiver) {
+      if (receiver == null)
+        return receiver;
+      if (receiver.constructor == Array)
+        return J.JSArray.prototype;
+      if (typeof receiver != "object") {
+        if (typeof receiver == "function")
+          return J.JavaScriptFunction.prototype;
+        return receiver;
+      }
+      if (receiver instanceof P.Object)
+        return receiver;
+      return J.getNativeInterceptor(receiver);
+    },
+    getInterceptor$n: function(receiver) {
+      if (typeof receiver == "number")
+        return J.JSNumber.prototype;
+      if (receiver == null)
+        return receiver;
+      if (!(receiver instanceof P.Object))
+        return J.UnknownJavaScriptObject.prototype;
+      return receiver;
+    },
+    getInterceptor$s: function(receiver) {
+      if (typeof receiver == "string")
+        return J.JSString.prototype;
+      if (receiver == null)
+        return receiver;
+      if (!(receiver instanceof P.Object))
+        return J.UnknownJavaScriptObject.prototype;
+      return receiver;
+    },
+    getInterceptor$x: function(receiver) {
+      if (receiver == null)
+        return receiver;
+      if (typeof receiver != "object") {
+        if (typeof receiver == "function")
+          return J.JavaScriptFunction.prototype;
+        return receiver;
+      }
+      if (receiver instanceof P.Object)
+        return receiver;
+      return J.getNativeInterceptor(receiver);
+    },
+    get$first$ax: function(receiver) {
+      return J.getInterceptor$ax(receiver).get$first(receiver);
+    },
+    get$hashCode$: function(receiver) {
+      return J.getInterceptor$(receiver).get$hashCode(receiver);
+    },
+    get$isEmpty$asx: function(receiver) {
+      return J.getInterceptor$asx(receiver).get$isEmpty(receiver);
+    },
+    get$iterator$ax: function(receiver) {
+      return J.getInterceptor$ax(receiver).get$iterator(receiver);
+    },
+    get$last$ax: function(receiver) {
+      return J.getInterceptor$ax(receiver).get$last(receiver);
+    },
+    get$length$asx: function(receiver) {
+      return J.getInterceptor$asx(receiver).get$length(receiver);
+    },
+    get$message$x: function(receiver) {
+      return J.getInterceptor$x(receiver).get$message(receiver);
+    },
+    get$runtimeType$: function(receiver) {
+      return J.getInterceptor$(receiver).get$runtimeType(receiver);
+    },
+    get$startsWith$s: function(receiver) {
+      return J.getInterceptor$s(receiver).get$startsWith(receiver);
+    },
+    $add$ansx: function(receiver, a0) {
+      if (typeof receiver == "number" && typeof a0 == "number")
+        return receiver + a0;
+      return J.getInterceptor$ansx(receiver).$add(receiver, a0);
+    },
+    $eq$: function(receiver, a0) {
+      if (receiver == null)
+        return a0 == null;
+      if (typeof receiver != "object")
+        return a0 != null && receiver === a0;
+      return J.getInterceptor$(receiver).$eq(receiver, a0);
+    },
+    $index$asx: function(receiver, a0) {
+      if (typeof a0 === "number")
+        if (receiver.constructor == Array || typeof receiver == "string" || H.isJsIndexable(receiver, receiver[init.dispatchPropertyName]))
+          if (a0 >>> 0 === a0 && a0 < receiver.length)
+            return receiver[a0];
+      return J.getInterceptor$asx(receiver).$index(receiver, a0);
+    },
+    $indexSet$ax: function(receiver, a0, a1) {
+      return J.getInterceptor$ax(receiver).$indexSet(receiver, a0, a1);
+    },
+    _codeUnitAt$1$s: function(receiver, a0) {
+      return J.getInterceptor$s(receiver)._codeUnitAt$1(receiver, a0);
+    },
+    _removeEventListener$3$x: function(receiver, a0, a1, a2) {
+      return J.getInterceptor$x(receiver)._removeEventListener$3(receiver, a0, a1, a2);
+    },
+    addEventListener$3$x: function(receiver, a0, a1, a2) {
+      return J.getInterceptor$x(receiver).addEventListener$3(receiver, a0, a1, a2);
+    },
+    allMatches$1$s: function(receiver, a0) {
+      return J.getInterceptor$s(receiver).allMatches$1(receiver, a0);
+    },
+    allMatches$2$s: function(receiver, a0, a1) {
+      return J.getInterceptor$s(receiver).allMatches$2(receiver, a0, a1);
+    },
+    codeUnitAt$1$s: function(receiver, a0) {
+      return J.getInterceptor$s(receiver).codeUnitAt$1(receiver, a0);
+    },
+    contains$1$asx: function(receiver, a0) {
+      return J.getInterceptor$asx(receiver).contains$1(receiver, a0);
+    },
+    elementAt$1$ax: function(receiver, a0) {
+      return J.getInterceptor$ax(receiver).elementAt$1(receiver, a0);
+    },
+    endsWith$1$s: function(receiver, a0) {
+      return J.getInterceptor$s(receiver).endsWith$1(receiver, a0);
+    },
+    fillRange$3$ax: function(receiver, a0, a1, a2) {
+      return J.getInterceptor$ax(receiver).fillRange$3(receiver, a0, a1, a2);
+    },
+    map$1$1$ax: function(receiver, a0, $T1) {
+      return J.getInterceptor$ax(receiver).map$1$1(receiver, a0, $T1);
+    },
+    matchAsPrefix$2$s: function(receiver, a0, a1) {
+      return J.getInterceptor$s(receiver).matchAsPrefix$2(receiver, a0, a1);
+    },
+    padRight$1$s: function(receiver, a0) {
+      return J.getInterceptor$s(receiver).padRight$1(receiver, a0);
+    },
+    replaceRange$3$asx: function(receiver, a0, a1, a2) {
+      return J.getInterceptor$asx(receiver).replaceRange$3(receiver, a0, a1, a2);
+    },
+    startsWith$1$s: function(receiver, a0) {
+      return J.getInterceptor$s(receiver).startsWith$1(receiver, a0);
+    },
+    startsWith$2$s: function(receiver, a0, a1) {
+      return J.getInterceptor$s(receiver).startsWith$2(receiver, a0, a1);
+    },
+    substring$1$s: function(receiver, a0) {
+      return J.getInterceptor$s(receiver).substring$1(receiver, a0);
+    },
+    substring$2$s: function(receiver, a0, a1) {
+      return J.getInterceptor$s(receiver).substring$2(receiver, a0, a1);
+    },
+    toRadixString$1$n: function(receiver, a0) {
+      return J.getInterceptor$n(receiver).toRadixString$1(receiver, a0);
+    },
+    toSet$0$ax: function(receiver) {
+      return J.getInterceptor$ax(receiver).toSet$0(receiver);
+    },
+    toString$0$: function(receiver) {
+      return J.getInterceptor$(receiver).toString$0(receiver);
+    },
+    trim$0$s: function(receiver) {
+      return J.getInterceptor$s(receiver).trim$0(receiver);
+    },
+    Interceptor: function Interceptor() {
+    },
+    JSBool: function JSBool() {
+    },
+    JSNull: function JSNull() {
+    },
+    JSObject: function JSObject() {
+    },
+    JavaScriptObject: function JavaScriptObject() {
+    },
+    PlainJavaScriptObject: function PlainJavaScriptObject() {
+    },
+    UnknownJavaScriptObject: function UnknownJavaScriptObject() {
+    },
+    JavaScriptFunction: function JavaScriptFunction() {
+    },
+    JSArray: function JSArray(t0) {
+      this.$ti = t0;
+    },
+    JSUnmodifiableArray: function JSUnmodifiableArray(t0) {
+      this.$ti = t0;
+    },
+    ArrayIterator: function ArrayIterator(t0, t1, t2) {
+      var _ = this;
+      _._iterable = t0;
+      _._length = t1;
+      _._index = 0;
+      _._current = null;
+      _.$ti = t2;
+    },
+    JSNumber: function JSNumber() {
+    },
+    JSInt: function JSInt() {
+    },
+    JSDouble: function JSDouble() {
+    },
+    JSString: function JSString() {
+    }
+  },
+  P = {
+    _AsyncRun__initializeScheduleImmediate: function() {
+      var div, span, t1 = {};
+      if (self.scheduleImmediate != null)
+        return P.async__AsyncRun__scheduleImmediateJsOverride$closure();
+      if (self.MutationObserver != null && self.document != null) {
+        div = self.document.createElement("div");
+        span = self.document.createElement("span");
+        t1.storedCallback = null;
+        new self.MutationObserver(H.convertDartClosureToJS(new P._AsyncRun__initializeScheduleImmediate_internalCallback(t1), 1)).observe(div, {childList: true});
+        return new P._AsyncRun__initializeScheduleImmediate_closure(t1, div, span);
+      } else if (self.setImmediate != null)
+        return P.async__AsyncRun__scheduleImmediateWithSetImmediate$closure();
+      return P.async__AsyncRun__scheduleImmediateWithTimer$closure();
+    },
+    _AsyncRun__scheduleImmediateJsOverride: function(callback) {
+      self.scheduleImmediate(H.convertDartClosureToJS(new P._AsyncRun__scheduleImmediateJsOverride_internalCallback(type$.void_Function._check(callback)), 0));
+    },
+    _AsyncRun__scheduleImmediateWithSetImmediate: function(callback) {
+      self.setImmediate(H.convertDartClosureToJS(new P._AsyncRun__scheduleImmediateWithSetImmediate_internalCallback(type$.void_Function._check(callback)), 0));
+    },
+    _AsyncRun__scheduleImmediateWithTimer: function(callback) {
+      P.Timer__createTimer(C.Duration_0, type$.void_Function._check(callback));
+    },
+    Timer__createTimer: function(duration, callback) {
+      var milliseconds = C.JSInt_methods._tdivFast$1(duration._duration, 1000);
+      return P._TimerImpl$(milliseconds < 0 ? 0 : milliseconds, callback);
+    },
+    _TimerImpl$: function(milliseconds, callback) {
+      var t1 = new P._TimerImpl(true);
+      t1._TimerImpl$2(milliseconds, callback);
+      return t1;
+    },
+    _TimerImpl$periodic: function(milliseconds, callback) {
+      var t1 = new P._TimerImpl(false);
+      t1._TimerImpl$periodic$2(milliseconds, callback);
+      return t1;
+    },
+    _makeAsyncAwaitCompleter: function($T) {
+      return new P._AsyncAwaitCompleter(new P._Future($.Zone__current, $T._eval$1("_Future<0>")), $T._eval$1("_AsyncAwaitCompleter<0>"));
+    },
+    _asyncStartSync: function(bodyFunction, completer) {
+      bodyFunction.call$2(0, null);
+      completer.isSync = true;
+      return completer._future;
+    },
+    _asyncAwait: function(object, bodyFunction) {
+      P._awaitOnObject(object, bodyFunction);
+    },
+    _asyncReturn: function(object, completer) {
+      completer.complete$1(object);
+    },
+    _asyncRethrow: function(object, completer) {
+      completer.completeError$2(H.unwrapException(object), H.getTraceFromException(object));
+    },
+    _awaitOnObject: function(object, bodyFunction) {
+      var t1, future,
+        thenCallback = new P._awaitOnObject_closure(bodyFunction),
+        errorCallback = new P._awaitOnObject_closure0(bodyFunction);
+      if (object instanceof P._Future)
+        object._thenAwait$1$2(thenCallback, errorCallback, type$.dynamic);
+      else {
+        t1 = type$.dynamic;
+        if (type$.Future_dynamic._is(object))
+          object.then$1$2$onError(thenCallback, errorCallback, t1);
+        else {
+          future = new P._Future($.Zone__current, type$._Future_dynamic);
+          future._state = 4;
+          future._resultOrListeners = object;
+          future._thenAwait$1$2(thenCallback, null, t1);
+        }
+      }
+    },
+    _wrapJsFunctionForAsync: function($function) {
+      var $protected = function(fn, ERROR) {
+        return function(errorCode, result) {
+          while (true)
+            try {
+              fn(errorCode, result);
+              break;
+            } catch (error) {
+              result = error;
+              errorCode = ERROR;
+            }
+        };
+      }($function, 1);
+      return $.Zone__current.registerBinaryCallback$3$1(new P._wrapJsFunctionForAsync_closure($protected), type$.Null, type$.int, type$.dynamic);
+    },
+    Future_Future: function(computation, $T) {
+      var result = new P._Future($.Zone__current, $T._eval$1("_Future<0>"));
+      P.Timer_Timer(C.Duration_0, new P.Future_Future_closure(result, computation));
+      return result;
+    },
+    Future_Future$microtask: function(computation, $T) {
+      var result = new P._Future($.Zone__current, $T._eval$1("_Future<0>"));
+      P.scheduleMicrotask(new P.Future_Future$microtask_closure(result, computation));
+      return result;
+    },
+    Future_Future$sync: function(computation, $T) {
+      var result, error, stackTrace, future, replacement, t1, t2, exception;
+      try {
+        result = computation.call$0();
+        if ($T._eval$1("Future<0>")._is(result))
+          return result;
+        else {
+          t1 = $T._check(result);
+          t2 = new P._Future($.Zone__current, $T._eval$1("_Future<0>"));
+          t2._state = 4;
+          t2._resultOrListeners = t1;
+          return t2;
+        }
+      } catch (exception) {
+        error = H.unwrapException(exception);
+        stackTrace = H.getTraceFromException(exception);
+        t1 = $.Zone__current;
+        future = new P._Future(t1, $T._eval$1("_Future<0>"));
+        replacement = t1.errorCallback$2(error, stackTrace);
+        if (replacement != null) {
+          t1 = replacement.error;
+          if (t1 == null)
+            t1 = new P.NullThrownError();
+          future._asyncCompleteError$2(t1, replacement.stackTrace);
+        } else
+          future._asyncCompleteError$2(error, stackTrace);
+        return future;
+      }
+    },
+    Future_Future$error: function(error, stackTrace, $T) {
+      var replacement,
+        t1 = $.Zone__current;
+      if (t1 !== C.C__RootZone) {
+        replacement = t1.errorCallback$2(error, stackTrace);
+        if (replacement != null) {
+          error = replacement.error;
+          if (error == null)
+            error = new P.NullThrownError();
+          stackTrace = replacement.stackTrace;
+        }
+      }
+      t1 = new P._Future($.Zone__current, $T._eval$1("_Future<0>"));
+      t1._asyncCompleteError$2(error, stackTrace);
+      return t1;
+    },
+    Future_wait: function(futures, eagerError, $T) {
+      var handleError, future, pos, e, st, t2, t3, _i, t4, exception, _box_0 = {}, cleanUp = null,
+        t1 = $T._eval$1("_Future<List<0>>"),
+        result = new P._Future($.Zone__current, t1);
+      _box_0.values = null;
+      _box_0.remaining = 0;
+      _box_0.stackTrace = _box_0.error = null;
+      handleError = new P.Future_wait_handleError(_box_0, cleanUp, true, result);
+      try {
+        for (t2 = futures.length, t3 = type$.Null, _i = 0, t4 = 0; _i < futures.length; futures.length === t2 || (0, H.throwConcurrentModificationError)(futures), ++_i) {
+          future = futures[_i];
+          pos = t4;
+          future.then$1$2$onError(new P.Future_wait_closure(_box_0, pos, result, cleanUp, true, $T), handleError, t3);
+          t4 = ++_box_0.remaining;
+        }
+        if (t4 === 0) {
+          t1 = new P._Future($.Zone__current, t1);
+          t1._asyncComplete$1(C.List_empty1);
+          return t1;
+        }
+        t1 = new Array(t4);
+        t1.fixed$length = Array;
+        _box_0.values = H.setRuntimeTypeInfo(t1, $T._eval$1("JSArray<0>"));
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        st = H.getTraceFromException(exception);
+        t1 = P.Future_Future$error(e, st, $T._eval$1("List<0>"));
+        return t1;
+      }
+      return result;
+    },
+    Future_forEach: function(elements, action, $T) {
+      return P.Future_doWhile(new P.Future_forEach_closure(new J.ArrayIterator(elements, 0, H._arrayInstanceType(elements)._eval$1("ArrayIterator<1>")), action));
+    },
+    Future__kTrue: function(_) {
+      return true;
+    },
+    Future_doWhile: function(action) {
+      var nextIteration, t1 = {},
+        t2 = $.Zone__current,
+        doneSignal = new P._Future(t2, type$._Future_dynamic);
+      t1.nextIteration = null;
+      nextIteration = t2.bindUnaryCallbackGuarded$1$1(new P.Future_doWhile_closure(t1, action, doneSignal), type$.bool);
+      t1.nextIteration = nextIteration;
+      nextIteration.call$1(true);
+      return doneSignal;
+    },
+    _completeWithErrorCallback: function(result, error, stackTrace) {
+      var replacement = $.Zone__current.errorCallback$2(error, stackTrace);
+      if (replacement != null) {
+        error = replacement.error;
+        if (error == null)
+          error = new P.NullThrownError();
+        stackTrace = replacement.stackTrace;
+      }
+      result._completeError$2(error, stackTrace);
+    },
+    _Future$zoneValue: function(value, _zone, $T) {
+      var t1 = new P._Future(_zone, $T._eval$1("_Future<0>"));
+      $T._check(value);
+      t1._state = 4;
+      t1._resultOrListeners = value;
+      return t1;
+    },
+    _Future__chainForeignFuture: function(source, target) {
+      var e, s, exception;
+      H.assertHelper(target._state < 4);
+      H.assertHelper(!(source instanceof P._Future));
+      H.assertHelper(target._state === 0);
+      target._state = 1;
+      try {
+        source.then$1$2$onError(new P._Future__chainForeignFuture_closure(target), new P._Future__chainForeignFuture_closure0(target), type$.Null);
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        s = H.getTraceFromException(exception);
+        P.scheduleMicrotask(new P._Future__chainForeignFuture_closure1(target, e, s));
+      }
+    },
+    _Future__chainCoreFuture: function(source, target) {
+      var t1, t2, t3, listeners;
+      H.assertHelper(target._state <= 1);
+      for (t1 = type$._Future_dynamic; t2 = source._state, t3 = t2 === 2, t3;) {
+        H.assertHelper(t3);
+        source = t1._check(source._resultOrListeners);
+      }
+      if (t2 >= 4) {
+        listeners = target._removeListeners$0();
+        target._cloneResult$1(source);
+        P._Future__propagateToListeners(target, listeners);
+      } else {
+        listeners = type$._FutureListener_dynamic_dynamic._check(target._resultOrListeners);
+        H.assertHelper(target._state <= 1);
+        target._state = 2;
+        target._resultOrListeners = source;
+        source._prependListeners$1(listeners);
+      }
+    },
+    _Future__propagateToListeners: function(source, listeners) {
+      var t2, t3, t4, _box_0, hasError, asyncError, listeners0, sourceResult, t5, t6, zone, previous, oldZone, current, result, _box_1 = {},
+        t1 = _box_1.source = source;
+      for (t2 = type$.AsyncError, t3 = type$._FutureListener_dynamic_dynamic, t4 = type$.Future_dynamic; true;) {
+        _box_0 = {};
+        H.assertHelper(t1._state >= 4);
+        t1 = _box_1.source;
+        hasError = t1._state === 8;
+        if (listeners == null) {
+          if (hasError) {
+            asyncError = t2._check(t1._resultOrListeners);
+            t1._zone.handleUncaughtError$2(asyncError.error, asyncError.stackTrace);
+          }
+          return;
+        }
+        for (; listeners0 = listeners._nextListener, listeners0 != null; listeners = listeners0) {
+          listeners._nextListener = null;
+          P._Future__propagateToListeners(_box_1.source, listeners);
+        }
+        t1 = _box_1.source;
+        sourceResult = t1._resultOrListeners;
+        _box_0.listenerHasError = hasError;
+        _box_0.listenerValueOrError = sourceResult;
+        t5 = !hasError;
+        if (t5) {
+          t6 = listeners.state;
+          t6 = (t6 & 1) !== 0 || (t6 & 15) === 8;
+        } else
+          t6 = true;
+        if (t6) {
+          t6 = listeners.result;
+          zone = t6._zone;
+          if (hasError) {
+            t1 = t1._zone;
+            t1 = !(t1 === zone || t1.get$errorZone() === zone.get$errorZone());
+          } else
+            t1 = false;
+          if (t1) {
+            t1 = _box_1.source;
+            H.assertHelper(t1._state === 8);
+            asyncError = t2._check(t1._resultOrListeners);
+            _box_1.source._zone.handleUncaughtError$2(asyncError.error, asyncError.stackTrace);
+            return;
+          }
+          t1 = $.Zone__current;
+          if (t1 !== zone) {
+            H.assertHelper(zone !== t1);
+            previous = $.Zone__current;
+            $.Zone__current = zone;
+            oldZone = previous;
+          } else
+            oldZone = null;
+          t1 = listeners.state;
+          if ((t1 & 15) === 8)
+            new P._Future__propagateToListeners_handleWhenCompleteCallback(_box_1, _box_0, listeners, hasError).call$0();
+          else if (t5) {
+            if ((t1 & 1) !== 0)
+              new P._Future__propagateToListeners_handleValueCallback(_box_0, listeners, sourceResult).call$0();
+          } else if ((t1 & 2) !== 0)
+            new P._Future__propagateToListeners_handleError(_box_1, _box_0, listeners).call$0();
+          if (oldZone != null)
+            $.Zone__current = oldZone;
+          t1 = _box_0.listenerValueOrError;
+          if (t4._is(t1)) {
+            if (t1._state >= 4) {
+              H.assertHelper(t6._state < 4);
+              current = t3._check(t6._resultOrListeners);
+              t6._resultOrListeners = null;
+              listeners = t6._reverseListeners$1(current);
+              H.assertHelper(t6._state < 4);
+              H.assertHelper(t1._state >= 4);
+              t6._state = t1._state;
+              t6._resultOrListeners = t1._resultOrListeners;
+              _box_1.source = t1;
+              continue;
+            } else
+              P._Future__chainCoreFuture(t1, t6);
+            return;
+          }
+        }
+        result = listeners.result;
+        H.assertHelper(result._state < 4);
+        current = t3._check(result._resultOrListeners);
+        result._resultOrListeners = null;
+        listeners = result._reverseListeners$1(current);
+        t1 = _box_0.listenerHasError;
+        t5 = _box_0.listenerValueOrError;
+        t6 = result._state >= 4;
+        if (!t1) {
+          result.$ti._precomputed1._check(t5);
+          H.assertHelper(!t6);
+          result._state = 4;
+          result._resultOrListeners = t5;
+        } else {
+          t2._check(t5);
+          H.assertHelper(!t6);
+          result._state = 8;
+          result._resultOrListeners = t5;
+        }
+        _box_1.source = result;
+        t1 = result;
+      }
+    },
+    _registerErrorHandler: function(errorHandler, zone) {
+      if (type$.dynamic_Function_Object_StackTrace._is(errorHandler))
+        return zone.registerBinaryCallback$3$1(errorHandler, type$.dynamic, type$.Object, type$.StackTrace);
+      if (type$.dynamic_Function_Object._is(errorHandler))
+        return zone.registerUnaryCallback$2$1(errorHandler, type$.dynamic, type$.Object);
+      throw H.wrapException(P.ArgumentError$value(errorHandler, "onError", "Error handler must accept one Object or one Object and a StackTrace as arguments, and return a a valid result"));
+    },
+    _microtaskLoop: function() {
+      var t1, t2;
+      for (; t1 = $._nextCallback, t1 != null;) {
+        $._lastPriorityCallback = null;
+        t2 = t1.next;
+        $._nextCallback = t2;
+        if (t2 == null)
+          $._lastCallback = null;
+        t1.callback.call$0();
+      }
+    },
+    _startMicrotaskLoop: function() {
+      $._isInCallbackLoop = true;
+      try {
+        P._microtaskLoop();
+      } finally {
+        $._lastPriorityCallback = null;
+        $._isInCallbackLoop = false;
+        if ($._nextCallback != null)
+          $.$get$_AsyncRun__scheduleImmediateClosure().call$1(P.async___startMicrotaskLoop$closure());
+      }
+    },
+    _scheduleAsyncCallback: function(callback) {
+      var newEntry = new P._AsyncCallbackEntry(callback);
+      if ($._nextCallback == null) {
+        $._nextCallback = $._lastCallback = newEntry;
+        if (!$._isInCallbackLoop)
+          $.$get$_AsyncRun__scheduleImmediateClosure().call$1(P.async___startMicrotaskLoop$closure());
+      } else
+        $._lastCallback = $._lastCallback.next = newEntry;
+    },
+    _schedulePriorityAsyncCallback: function(callback) {
+      var entry, t2,
+        t1 = $._nextCallback;
+      if (t1 == null) {
+        P._scheduleAsyncCallback(callback);
+        $._lastPriorityCallback = $._lastCallback;
+        return;
+      }
+      entry = new P._AsyncCallbackEntry(callback);
+      t2 = $._lastPriorityCallback;
+      if (t2 == null) {
+        entry.next = t1;
+        $._nextCallback = $._lastPriorityCallback = entry;
+      } else {
+        entry.next = t2.next;
+        $._lastPriorityCallback = t2.next = entry;
+        if (entry.next == null)
+          $._lastCallback = entry;
+      }
+    },
+    scheduleMicrotask: function(callback) {
+      var t1, _null = null,
+        currentZone = $.Zone__current;
+      if (C.C__RootZone === currentZone) {
+        P._rootScheduleMicrotask(_null, _null, C.C__RootZone, callback);
+        return;
+      }
+      if (C.C__RootZone === currentZone.get$_scheduleMicrotask().zone)
+        t1 = C.C__RootZone.get$errorZone() === currentZone.get$errorZone();
+      else
+        t1 = false;
+      if (t1) {
+        P._rootScheduleMicrotask(_null, _null, currentZone, currentZone.registerCallback$1$1(callback, type$.void));
+        return;
+      }
+      t1 = $.Zone__current;
+      t1.scheduleMicrotask$1(t1.bindCallbackGuarded$1(callback));
+    },
+    Stream_Stream$fromFuture: function(future, $T) {
+      var _null = null,
+        t1 = $T._eval$1("_SyncStreamController<0>"),
+        controller = new P._SyncStreamController(_null, _null, _null, _null, t1);
+      future.then$1$2$onError(new P.Stream_Stream$fromFuture_closure(controller, $T), new P.Stream_Stream$fromFuture_closure0(controller), type$.Null);
+      return new P._ControllerStream(controller, t1._eval$1("_ControllerStream<1>"));
+    },
+    Stream_Stream$fromIterable: function(elements, $T) {
+      return new P._GeneratedStreamImpl(new P.Stream_Stream$fromIterable_closure(elements, $T), $T._eval$1("_GeneratedStreamImpl<0>"));
+    },
+    StreamIterator_StreamIterator: function(stream, $T) {
+      if (stream == null)
+        H.throwExpression(P.ArgumentError$notNull("stream"));
+      return new P._StreamIterator($T._eval$1("_StreamIterator<0>"));
+    },
+    StreamController_StreamController: function(onCancel, onListen, sync, $T) {
+      var _null = null;
+      return sync ? new P._SyncStreamController(onListen, _null, _null, onCancel, $T._eval$1("_SyncStreamController<0>")) : new P._AsyncStreamController(onListen, _null, _null, onCancel, $T._eval$1("_AsyncStreamController<0>"));
+    },
+    _runGuarded: function(notificationHandler) {
+      var e, s, exception;
+      if (notificationHandler == null)
+        return;
+      try {
+        notificationHandler.call$0();
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        s = H.getTraceFromException(exception);
+        $.Zone__current.handleUncaughtError$2(e, s);
+      }
+    },
+    _AddStreamState_makeErrorHandler: function(controller) {
+      return new P._AddStreamState_makeErrorHandler_closure(controller);
+    },
+    _BufferingStreamSubscription$: function(onData, onError, onDone, cancelOnError, $T) {
+      var t1 = $.Zone__current,
+        t2 = cancelOnError ? 1 : 0;
+      t2 = new P._BufferingStreamSubscription(t1, t2, $T._eval$1("_BufferingStreamSubscription<0>"));
+      t2._BufferingStreamSubscription$4(onData, onError, onDone, cancelOnError, $T);
+      return t2;
+    },
+    _nullDataHandler: function(value) {
+    },
+    _nullErrorHandler: function(error, stackTrace) {
+      type$.StackTrace._check(stackTrace);
+      $.Zone__current.handleUncaughtError$2(error, stackTrace);
+    },
+    _nullDoneHandler: function() {
+    },
+    _runUserCode: function(userCode, onSuccess, onError, $T) {
+      var e, s, replacement, error, stackTrace, exception, error0;
+      try {
+        onSuccess.call$1(userCode.call$0());
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        s = H.getTraceFromException(exception);
+        replacement = $.Zone__current.errorCallback$2(e, s);
+        if (replacement == null)
+          onError.call$2(e, s);
+        else {
+          error0 = replacement.error;
+          error = error0 == null ? new P.NullThrownError() : error0;
+          stackTrace = replacement.stackTrace;
+          onError.call$2(error, stackTrace);
+        }
+      }
+    },
+    _cancelAndError: function(subscription, future, error, stackTrace) {
+      var cancelFuture = subscription.cancel$0();
+      if (cancelFuture != null && cancelFuture !== $.$get$Future__nullFuture())
+        cancelFuture.whenComplete$1(new P._cancelAndError_closure(future, error, stackTrace));
+      else
+        future._completeError$2(error, stackTrace);
+    },
+    _cancelAndErrorClosure: function(subscription, future) {
+      return new P._cancelAndErrorClosure_closure(subscription, future);
+    },
+    _cancelAndValue: function(subscription, future, value) {
+      var cancelFuture = subscription.cancel$0();
+      if (cancelFuture != null && cancelFuture !== $.$get$Future__nullFuture())
+        cancelFuture.whenComplete$1(new P._cancelAndValue_closure(future, value));
+      else
+        future._complete$1(value);
+    },
+    Timer_Timer: function(duration, callback) {
+      var t1 = $.Zone__current;
+      if (t1 === C.C__RootZone)
+        return t1.createTimer$2(duration, callback);
+      return t1.createTimer$2(duration, t1.bindCallbackGuarded$1(callback));
+    },
+    _ZoneSpecification$: function(createPeriodicTimer, createTimer, errorCallback, fork, handleUncaughtError, $print, registerBinaryCallback, registerCallback, registerUnaryCallback, run, runBinary, runUnary, scheduleMicrotask) {
+      return new P._ZoneSpecification(handleUncaughtError, run, runUnary, runBinary, registerCallback, registerUnaryCallback, registerBinaryCallback, errorCallback, scheduleMicrotask, createTimer, createPeriodicTimer, $print, fork);
+    },
+    Zone__enter: function(zone) {
+      var previous;
+      H.assertHelper(zone != null);
+      H.assertHelper(zone !== $.Zone__current);
+      previous = $.Zone__current;
+      $.Zone__current = zone;
+      return previous;
+    },
+    _parentDelegate: function(zone) {
+      if (zone.get$parent(zone) == null)
+        return null;
+      return zone.get$parent(zone).get$_delegate();
+    },
+    _rootHandleUncaughtError: function($self, $parent, zone, error, stackTrace) {
+      var t1 = {};
+      t1.error = error;
+      P._schedulePriorityAsyncCallback(new P._rootHandleUncaughtError_closure(t1, type$.StackTrace._check(stackTrace)));
+    },
+    _rootRun: function($self, $parent, zone, f, $R) {
+      var old,
+        t1 = type$.Zone;
+      t1._check($self);
+      type$.ZoneDelegate._check($parent);
+      t1._check(zone);
+      $R._eval$1("0()")._check(f);
+      if ($.Zone__current === zone)
+        return f.call$0();
+      old = P.Zone__enter(zone);
+      try {
+        t1 = f.call$0();
+        return t1;
+      } finally {
+        t1 = old;
+        H.assertHelper(t1 != null);
+        $.Zone__current = t1;
+      }
+    },
+    _rootRunUnary: function($self, $parent, zone, f, arg, $R, $T) {
+      var old,
+        t1 = type$.Zone;
+      t1._check($self);
+      type$.ZoneDelegate._check($parent);
+      t1._check(zone);
+      $R._eval$1("@<0>")._bind$1($T)._eval$1("1(2)")._check(f);
+      $T._check(arg);
+      if ($.Zone__current === zone)
+        return f.call$1(arg);
+      old = P.Zone__enter(zone);
+      try {
+        t1 = f.call$1(arg);
+        return t1;
+      } finally {
+        t1 = old;
+        H.assertHelper(t1 != null);
+        $.Zone__current = t1;
+      }
+    },
+    _rootRunBinary: function($self, $parent, zone, f, arg1, arg2, $R, T1, T2) {
+      var old,
+        t1 = type$.Zone;
+      t1._check($self);
+      type$.ZoneDelegate._check($parent);
+      t1._check(zone);
+      $R._eval$1("@<0>")._bind$1(T1)._bind$1(T2)._eval$1("1(2,3)")._check(f);
+      T1._check(arg1);
+      T2._check(arg2);
+      if ($.Zone__current === zone)
+        return f.call$2(arg1, arg2);
+      old = P.Zone__enter(zone);
+      try {
+        t1 = f.call$2(arg1, arg2);
+        return t1;
+      } finally {
+        t1 = old;
+        H.assertHelper(t1 != null);
+        $.Zone__current = t1;
+      }
+    },
+    _rootRegisterCallback: function($self, $parent, zone, f, $R) {
+      return $R._eval$1("0()")._check(f);
+    },
+    _rootRegisterUnaryCallback: function($self, $parent, zone, f, $R, $T) {
+      return $R._eval$1("@<0>")._bind$1($T)._eval$1("1(2)")._check(f);
+    },
+    _rootRegisterBinaryCallback: function($self, $parent, zone, f, $R, T1, T2) {
+      return $R._eval$1("@<0>")._bind$1(T1)._bind$1(T2)._eval$1("1(2,3)")._check(f);
+    },
+    _rootErrorCallback: function($self, $parent, zone, error, stackTrace) {
+      type$.StackTrace._check(stackTrace);
+      return null;
+    },
+    _rootScheduleMicrotask: function($self, $parent, zone, f) {
+      var t1;
+      type$.void_Function._check(f);
+      t1 = C.C__RootZone !== zone;
+      if (t1)
+        f = !(!t1 || C.C__RootZone.get$errorZone() === zone.get$errorZone()) ? zone.bindCallbackGuarded$1(f) : zone.bindCallback$1$1(f, type$.void);
+      P._scheduleAsyncCallback(f);
+    },
+    _rootCreateTimer: function($self, $parent, zone, duration, callback) {
+      type$.Duration._check(duration);
+      callback = zone.bindCallback$1$1(type$.void_Function._check(callback), type$.void);
+      return P.Timer__createTimer(duration, callback);
+    },
+    _rootCreatePeriodicTimer: function($self, $parent, zone, duration, callback) {
+      var milliseconds;
+      type$.Duration._check(duration);
+      callback = zone.bindUnaryCallback$2$1(type$.void_Function_Timer._check(callback), type$.dynamic, type$.Timer);
+      milliseconds = C.JSInt_methods._tdivFast$1(duration._duration, 1000);
+      return P._TimerImpl$periodic(milliseconds < 0 ? 0 : milliseconds, callback);
+    },
+    _rootPrint: function($self, $parent, zone, line) {
+      H.printString(H._checkStringNullable(line));
+    },
+    _printToZone: function(line) {
+      $.Zone__current.print$1(0, line);
+    },
+    _rootFork: function($self, $parent, zone, specification, zoneValues) {
+      var valueMap, t1, t2;
+      type$.ZoneSpecification._check(specification);
+      type$.Map_dynamic_dynamic._check(zoneValues);
+      $.printToZone = P.async___printToZone$closure();
+      if (specification == null)
+        specification = C._ZoneSpecification_ALf;
+      if (zoneValues == null)
+        valueMap = zone.get$_async$_map();
+      else {
+        t1 = type$.dynamic;
+        valueMap = P.HashMap_HashMap$from(zoneValues, t1, t1);
+      }
+      t1 = new P._CustomZone(zone, valueMap);
+      t2 = zone.get$_run();
+      t1.set$_run(t2);
+      t2 = zone.get$_runUnary();
+      t1.set$_runUnary(t2);
+      t2 = zone.get$_runBinary();
+      t1.set$_runBinary(t2);
+      t2 = specification.registerCallback;
+      t1.set$_registerCallback(t2 != null ? new P._ZoneFunction(t1, t2, type$._ZoneFunction_Function) : zone.get$_registerCallback());
+      t2 = specification.registerUnaryCallback;
+      t1.set$_registerUnaryCallback(t2 != null ? new P._ZoneFunction(t1, t2, type$._ZoneFunction_Function) : zone.get$_registerUnaryCallback());
+      t2 = specification.registerBinaryCallback;
+      t1.set$_registerBinaryCallback(t2 != null ? new P._ZoneFunction(t1, t2, type$._ZoneFunction_Function) : zone.get$_registerBinaryCallback());
+      t2 = specification.errorCallback;
+      t1.set$_errorCallback(t2 != null ? new P._ZoneFunction(t1, t2, type$._ZoneFunction_of_AsyncError_Function_Zone_ZoneDelegate_Zone_Object_StackTrace) : zone.get$_errorCallback());
+      t2 = zone.get$_scheduleMicrotask();
+      t1.set$_scheduleMicrotask(t2);
+      t2 = zone.get$_createTimer();
+      t1.set$_createTimer(t2);
+      t2 = zone.get$_createPeriodicTimer();
+      t1.set$_createPeriodicTimer(t2);
+      t2 = specification.print;
+      t1.set$_print(t2 != null ? new P._ZoneFunction(t1, t2, type$._ZoneFunction_of_void_Function_Zone_ZoneDelegate_Zone_String) : zone.get$_print());
+      t2 = zone.get$_fork();
+      t1.set$_fork(t2);
+      t2 = specification.handleUncaughtError;
+      t1.set$_handleUncaughtError(t2 != null ? new P._ZoneFunction(t1, t2, type$._ZoneFunction_of_void_Function_Zone_ZoneDelegate_Zone_Object_StackTrace) : zone.get$_handleUncaughtError());
+      return t1;
+    },
+    runZoned: function(body, onError, zoneSpecification, zoneValues, $R) {
+      var e, stackTrace, errorHandler, t2, t3, t4, t5, t6, t7, t8, t9, t10, t11, t12, t13, exception, _null = null, t1 = {};
+      if (onError == null)
+        return P._runZoned(body, zoneValues, zoneSpecification, $R);
+      t1.binaryOnError = t1.unaryOnError = null;
+      if (type$.void_Function_Object_StackTrace._is(onError))
+        t1.binaryOnError = onError;
+      else if (type$.void_Function_Object._is(onError))
+        t1.unaryOnError = onError;
+      else
+        throw H.wrapException(P.ArgumentError$("onError callback must take either an Object (the error), or both an Object (the error) and a StackTrace."));
+      errorHandler = new P.runZoned_closure(t1);
+      if (zoneSpecification == null)
+        zoneSpecification = P._ZoneSpecification$(_null, _null, _null, _null, errorHandler, _null, _null, _null, _null, _null, _null, _null, _null);
+      else {
+        t2 = zoneSpecification;
+        t3 = t2.run;
+        t4 = t2.runUnary;
+        t5 = t2.runBinary;
+        t6 = t2.registerCallback;
+        t7 = t2.registerUnaryCallback;
+        t8 = t2.registerBinaryCallback;
+        t9 = t2.errorCallback;
+        t10 = t2.scheduleMicrotask;
+        t11 = t2.createTimer;
+        t12 = t2.createPeriodicTimer;
+        t13 = t2.print;
+        zoneSpecification = P._ZoneSpecification$(t12, t11, t9, t2.fork, errorHandler, t13, t8, t6, t7, t3, t5, t4, t10);
+      }
+      try {
+        t2 = P._runZoned(body, zoneValues, zoneSpecification, $R);
+        return t2;
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        stackTrace = H.getTraceFromException(exception);
+        t2 = t1.binaryOnError;
+        if (t2 != null)
+          t2.call$2(e, stackTrace);
+        else {
+          H.assertHelper(t1.unaryOnError != null);
+          t1.unaryOnError.call$1(e);
+        }
+      }
+      return _null;
+    },
+    _runZoned: function(body, zoneValues, specification, $R) {
+      return $.Zone__current.fork$2$specification$zoneValues(specification, zoneValues).run$1$1(body, $R);
+    },
+    _AsyncRun__initializeScheduleImmediate_internalCallback: function _AsyncRun__initializeScheduleImmediate_internalCallback(t0) {
+      this._box_0 = t0;
+    },
+    _AsyncRun__initializeScheduleImmediate_closure: function _AsyncRun__initializeScheduleImmediate_closure(t0, t1, t2) {
+      this._box_0 = t0;
+      this.div = t1;
+      this.span = t2;
+    },
+    _AsyncRun__scheduleImmediateJsOverride_internalCallback: function _AsyncRun__scheduleImmediateJsOverride_internalCallback(t0) {
+      this.callback = t0;
+    },
+    _AsyncRun__scheduleImmediateWithSetImmediate_internalCallback: function _AsyncRun__scheduleImmediateWithSetImmediate_internalCallback(t0) {
+      this.callback = t0;
+    },
+    _TimerImpl: function _TimerImpl(t0) {
+      this._once = t0;
+      this._handle = null;
+      this._tick = 0;
+    },
+    _TimerImpl_internalCallback: function _TimerImpl_internalCallback(t0, t1) {
+      this.$this = t0;
+      this.callback = t1;
+    },
+    _TimerImpl$periodic_closure: function _TimerImpl$periodic_closure(t0, t1, t2, t3) {
+      var _ = this;
+      _.$this = t0;
+      _.milliseconds = t1;
+      _.start = t2;
+      _.callback = t3;
+    },
+    _AsyncAwaitCompleter: function _AsyncAwaitCompleter(t0, t1) {
+      this._future = t0;
+      this.isSync = false;
+      this.$ti = t1;
+    },
+    _awaitOnObject_closure: function _awaitOnObject_closure(t0) {
+      this.bodyFunction = t0;
+    },
+    _awaitOnObject_closure0: function _awaitOnObject_closure0(t0) {
+      this.bodyFunction = t0;
+    },
+    _wrapJsFunctionForAsync_closure: function _wrapJsFunctionForAsync_closure(t0) {
+      this.$protected = t0;
+    },
+    _BroadcastStream: function _BroadcastStream(t0, t1) {
+      this._controller = t0;
+      this.$ti = t1;
+    },
+    _BroadcastSubscription: function _BroadcastSubscription(t0, t1, t2, t3) {
+      var _ = this;
+      _._eventState = 0;
+      _._async$_previous = _._async$_next = null;
+      _._controller = t0;
+      _._onDone = _._onError = _._onData = null;
+      _._zone = t1;
+      _._state = t2;
+      _._pending = _._cancelFuture = null;
+      _.$ti = t3;
+    },
+    _BroadcastStreamController: function _BroadcastStreamController() {
+    },
+    _SyncBroadcastStreamController: function _SyncBroadcastStreamController(t0, t1, t2) {
+      var _ = this;
+      _.onListen = t0;
+      _.onCancel = t1;
+      _._state = 0;
+      _._doneFuture = _._addStreamState = _._lastSubscription = _._firstSubscription = null;
+      _.$ti = t2;
+    },
+    _SyncBroadcastStreamController__sendData_closure: function _SyncBroadcastStreamController__sendData_closure(t0, t1) {
+      this.$this = t0;
+      this.data = t1;
+    },
+    _SyncBroadcastStreamController__sendError_closure: function _SyncBroadcastStreamController__sendError_closure(t0, t1, t2) {
+      this.$this = t0;
+      this.error = t1;
+      this.stackTrace = t2;
+    },
+    _SyncBroadcastStreamController__sendDone_closure: function _SyncBroadcastStreamController__sendDone_closure(t0) {
+      this.$this = t0;
+    },
+    _AsyncBroadcastStreamController: function _AsyncBroadcastStreamController(t0, t1, t2) {
+      var _ = this;
+      _.onListen = t0;
+      _.onCancel = t1;
+      _._state = 0;
+      _._doneFuture = _._addStreamState = _._lastSubscription = _._firstSubscription = null;
+      _.$ti = t2;
+    },
+    Future: function Future() {
+    },
+    Future_Future_closure: function Future_Future_closure(t0, t1) {
+      this.result = t0;
+      this.computation = t1;
+    },
+    Future_Future$microtask_closure: function Future_Future$microtask_closure(t0, t1) {
+      this.result = t0;
+      this.computation = t1;
+    },
+    Future_wait_handleError: function Future_wait_handleError(t0, t1, t2, t3) {
+      var _ = this;
+      _._box_0 = t0;
+      _.cleanUp = t1;
+      _.eagerError = t2;
+      _.result = t3;
+    },
+    Future_wait_closure: function Future_wait_closure(t0, t1, t2, t3, t4, t5) {
+      var _ = this;
+      _._box_0 = t0;
+      _.pos = t1;
+      _.result = t2;
+      _.cleanUp = t3;
+      _.eagerError = t4;
+      _.T = t5;
+    },
+    Future_forEach_closure: function Future_forEach_closure(t0, t1) {
+      this.iterator = t0;
+      this.action = t1;
+    },
+    Future_doWhile_closure: function Future_doWhile_closure(t0, t1, t2) {
+      this._box_0 = t0;
+      this.action = t1;
+      this.doneSignal = t2;
+    },
+    TimeoutException: function TimeoutException(t0, t1) {
+      this.message = t0;
+      this.duration = t1;
+    },
+    Completer: function Completer() {
+    },
+    _Completer: function _Completer() {
+    },
+    _AsyncCompleter: function _AsyncCompleter(t0, t1) {
+      this.future = t0;
+      this.$ti = t1;
+    },
+    _SyncCompleter: function _SyncCompleter(t0, t1) {
+      this.future = t0;
+      this.$ti = t1;
+    },
+    _FutureListener: function _FutureListener(t0, t1, t2, t3, t4) {
+      var _ = this;
+      _._nextListener = null;
+      _.result = t0;
+      _.state = t1;
+      _.callback = t2;
+      _.errorCallback = t3;
+      _.$ti = t4;
+    },
+    _Future: function _Future(t0, t1) {
+      var _ = this;
+      _._state = 0;
+      _._zone = t0;
+      _._resultOrListeners = null;
+      _.$ti = t1;
+    },
+    _Future__addListener_closure: function _Future__addListener_closure(t0, t1) {
+      this.$this = t0;
+      this.listener = t1;
+    },
+    _Future__prependListeners_closure: function _Future__prependListeners_closure(t0, t1) {
+      this._box_0 = t0;
+      this.$this = t1;
+    },
+    _Future__chainForeignFuture_closure: function _Future__chainForeignFuture_closure(t0) {
+      this.target = t0;
+    },
+    _Future__chainForeignFuture_closure0: function _Future__chainForeignFuture_closure0(t0) {
+      this.target = t0;
+    },
+    _Future__chainForeignFuture_closure1: function _Future__chainForeignFuture_closure1(t0, t1, t2) {
+      this.target = t0;
+      this.e = t1;
+      this.s = t2;
+    },
+    _Future__asyncComplete_closure: function _Future__asyncComplete_closure(t0, t1) {
+      this.$this = t0;
+      this.value = t1;
+    },
+    _Future__chainFuture_closure: function _Future__chainFuture_closure(t0, t1) {
+      this.$this = t0;
+      this.value = t1;
+    },
+    _Future__asyncCompleteError_closure: function _Future__asyncCompleteError_closure(t0, t1, t2) {
+      this.$this = t0;
+      this.error = t1;
+      this.stackTrace = t2;
+    },
+    _Future__propagateToListeners_handleWhenCompleteCallback: function _Future__propagateToListeners_handleWhenCompleteCallback(t0, t1, t2, t3) {
+      var _ = this;
+      _._box_1 = t0;
+      _._box_0 = t1;
+      _.listener = t2;
+      _.hasError = t3;
+    },
+    _Future__propagateToListeners_handleWhenCompleteCallback_closure: function _Future__propagateToListeners_handleWhenCompleteCallback_closure(t0) {
+      this.originalSource = t0;
+    },
+    _Future__propagateToListeners_handleValueCallback: function _Future__propagateToListeners_handleValueCallback(t0, t1, t2) {
+      this._box_0 = t0;
+      this.listener = t1;
+      this.sourceResult = t2;
+    },
+    _Future__propagateToListeners_handleError: function _Future__propagateToListeners_handleError(t0, t1, t2) {
+      this._box_1 = t0;
+      this._box_0 = t1;
+      this.listener = t2;
+    },
+    _AsyncCallbackEntry: function _AsyncCallbackEntry(t0) {
+      this.callback = t0;
+      this.next = null;
+    },
+    Stream: function Stream() {
+    },
+    Stream_Stream$fromFuture_closure: function Stream_Stream$fromFuture_closure(t0, t1) {
+      this.controller = t0;
+      this.T = t1;
+    },
+    Stream_Stream$fromFuture_closure0: function Stream_Stream$fromFuture_closure0(t0) {
+      this.controller = t0;
+    },
+    Stream_Stream$fromIterable_closure: function Stream_Stream$fromIterable_closure(t0, t1) {
+      this.elements = t0;
+      this.T = t1;
+    },
+    Stream_pipe_closure: function Stream_pipe_closure(t0) {
+      this.streamConsumer = t0;
+    },
+    Stream_length_closure: function Stream_length_closure(t0, t1) {
+      this._box_0 = t0;
+      this.$this = t1;
+    },
+    Stream_length_closure0: function Stream_length_closure0(t0, t1) {
+      this._box_0 = t0;
+      this.future = t1;
+    },
+    Stream_first_closure: function Stream_first_closure(t0, t1, t2) {
+      this._box_0 = t0;
+      this.$this = t1;
+      this.future = t2;
+    },
+    Stream_first_closure0: function Stream_first_closure0(t0) {
+      this.future = t0;
+    },
+    Stream_last_closure: function Stream_last_closure(t0, t1) {
+      this._box_0 = t0;
+      this.$this = t1;
+    },
+    Stream_last_closure0: function Stream_last_closure0(t0, t1) {
+      this._box_0 = t0;
+      this.future = t1;
+    },
+    Stream_firstWhere_closure: function Stream_firstWhere_closure(t0, t1, t2, t3) {
+      var _ = this;
+      _._box_0 = t0;
+      _.$this = t1;
+      _.test = t2;
+      _.future = t3;
+    },
+    Stream_firstWhere__closure: function Stream_firstWhere__closure(t0, t1) {
+      this.test = t0;
+      this.value = t1;
+    },
+    Stream_firstWhere__closure0: function Stream_firstWhere__closure0(t0, t1, t2) {
+      this._box_0 = t0;
+      this.future = t1;
+      this.value = t2;
+    },
+    Stream_firstWhere_closure0: function Stream_firstWhere_closure0(t0, t1, t2) {
+      this.$this = t0;
+      this.orElse = t1;
+      this.future = t2;
+    },
+    StreamSubscription: function StreamSubscription() {
+    },
+    StreamTransformerBase: function StreamTransformerBase() {
+    },
+    _StreamController: function _StreamController() {
+    },
+    _StreamController__subscribe_closure: function _StreamController__subscribe_closure(t0) {
+      this.$this = t0;
+    },
+    _StreamController__recordCancel_complete: function _StreamController__recordCancel_complete(t0) {
+      this.$this = t0;
+    },
+    _SyncStreamControllerDispatch: function _SyncStreamControllerDispatch() {
+    },
+    _AsyncStreamControllerDispatch: function _AsyncStreamControllerDispatch() {
+    },
+    _AsyncStreamController: function _AsyncStreamController(t0, t1, t2, t3, t4) {
+      var _ = this;
+      _._varData = null;
+      _._state = 0;
+      _._doneFuture = null;
+      _.onListen = t0;
+      _.onPause = t1;
+      _.onResume = t2;
+      _.onCancel = t3;
+      _.$ti = t4;
+    },
+    _SyncStreamController: function _SyncStreamController(t0, t1, t2, t3, t4) {
+      var _ = this;
+      _._varData = null;
+      _._state = 0;
+      _._doneFuture = null;
+      _.onListen = t0;
+      _.onPause = t1;
+      _.onResume = t2;
+      _.onCancel = t3;
+      _.$ti = t4;
+    },
+    _ControllerStream: function _ControllerStream(t0, t1) {
+      this._controller = t0;
+      this.$ti = t1;
+    },
+    _ControllerSubscription: function _ControllerSubscription(t0, t1, t2, t3) {
+      var _ = this;
+      _._controller = t0;
+      _._onDone = _._onError = _._onData = null;
+      _._zone = t1;
+      _._state = t2;
+      _._pending = _._cancelFuture = null;
+      _.$ti = t3;
+    },
+    _StreamSinkWrapper: function _StreamSinkWrapper(t0, t1) {
+      this._async$_target = t0;
+      this.$ti = t1;
+    },
+    _AddStreamState: function _AddStreamState() {
+    },
+    _AddStreamState_makeErrorHandler_closure: function _AddStreamState_makeErrorHandler_closure(t0) {
+      this.controller = t0;
+    },
+    _AddStreamState_cancel_closure: function _AddStreamState_cancel_closure(t0) {
+      this.$this = t0;
+    },
+    _StreamControllerAddStreamState: function _StreamControllerAddStreamState(t0, t1, t2, t3) {
+      var _ = this;
+      _.varData = t0;
+      _.addStreamFuture = t1;
+      _.addSubscription = t2;
+      _.$ti = t3;
+    },
+    _BufferingStreamSubscription: function _BufferingStreamSubscription(t0, t1, t2) {
+      var _ = this;
+      _._onDone = _._onError = _._onData = null;
+      _._zone = t0;
+      _._state = t1;
+      _._pending = _._cancelFuture = null;
+      _.$ti = t2;
+    },
+    _BufferingStreamSubscription__sendError_sendError: function _BufferingStreamSubscription__sendError_sendError(t0, t1, t2) {
+      this.$this = t0;
+      this.error = t1;
+      this.stackTrace = t2;
+    },
+    _BufferingStreamSubscription__sendDone_sendDone: function _BufferingStreamSubscription__sendDone_sendDone(t0) {
+      this.$this = t0;
+    },
+    _StreamImpl: function _StreamImpl() {
+    },
+    _GeneratedStreamImpl: function _GeneratedStreamImpl(t0, t1) {
+      this._pending = t0;
+      this._isUsed = false;
+      this.$ti = t1;
+    },
+    _IterablePendingEvents: function _IterablePendingEvents(t0, t1) {
+      this._async$_iterator = t0;
+      this._state = 0;
+      this.$ti = t1;
+    },
+    _DelayedEvent: function _DelayedEvent() {
+    },
+    _DelayedData: function _DelayedData(t0, t1) {
+      this.value = t0;
+      this.next = null;
+      this.$ti = t1;
+    },
+    _DelayedError: function _DelayedError(t0, t1) {
+      this.error = t0;
+      this.stackTrace = t1;
+      this.next = null;
+    },
+    _DelayedDone: function _DelayedDone() {
+    },
+    _PendingEvents: function _PendingEvents() {
+    },
+    _PendingEvents_schedule_closure: function _PendingEvents_schedule_closure(t0, t1) {
+      this.$this = t0;
+      this.dispatch = t1;
+    },
+    _StreamImplEvents: function _StreamImplEvents(t0) {
+      var _ = this;
+      _.lastPendingEvent = _.firstPendingEvent = null;
+      _._state = 0;
+      _.$ti = t0;
+    },
+    _DoneStreamSubscription: function _DoneStreamSubscription(t0, t1, t2) {
+      var _ = this;
+      _._zone = t0;
+      _._state = 0;
+      _._onDone = t1;
+      _.$ti = t2;
+    },
+    _StreamIterator: function _StreamIterator(t0) {
+      this.$ti = t0;
+    },
+    _EmptyStream: function _EmptyStream(t0) {
+      this.$ti = t0;
+    },
+    _cancelAndError_closure: function _cancelAndError_closure(t0, t1, t2) {
+      this.future = t0;
+      this.error = t1;
+      this.stackTrace = t2;
+    },
+    _cancelAndErrorClosure_closure: function _cancelAndErrorClosure_closure(t0, t1) {
+      this.subscription = t0;
+      this.future = t1;
+    },
+    _cancelAndValue_closure: function _cancelAndValue_closure(t0, t1) {
+      this.future = t0;
+      this.value = t1;
+    },
+    Timer: function Timer() {
+    },
+    AsyncError: function AsyncError(t0, t1) {
+      this.error = t0;
+      this.stackTrace = t1;
+    },
+    _ZoneFunction: function _ZoneFunction(t0, t1, t2) {
+      this.zone = t0;
+      this.$function = t1;
+      this.$ti = t2;
+    },
+    ZoneSpecification: function ZoneSpecification() {
+    },
+    _ZoneSpecification: function _ZoneSpecification(t0, t1, t2, t3, t4, t5, t6, t7, t8, t9, t10, t11, t12) {
+      var _ = this;
+      _.handleUncaughtError = t0;
+      _.run = t1;
+      _.runUnary = t2;
+      _.runBinary = t3;
+      _.registerCallback = t4;
+      _.registerUnaryCallback = t5;
+      _.registerBinaryCallback = t6;
+      _.errorCallback = t7;
+      _.scheduleMicrotask = t8;
+      _.createTimer = t9;
+      _.createPeriodicTimer = t10;
+      _.print = t11;
+      _.fork = t12;
+    },
+    ZoneDelegate: function ZoneDelegate() {
+    },
+    Zone: function Zone() {
+    },
+    _ZoneDelegate: function _ZoneDelegate(t0) {
+      this._delegationTarget = t0;
+    },
+    _Zone: function _Zone() {
+    },
+    _CustomZone: function _CustomZone(t0, t1) {
+      var _ = this;
+      _._delegateCache = _._handleUncaughtError = _._fork = _._print = _._createPeriodicTimer = _._createTimer = _._scheduleMicrotask = _._errorCallback = _._registerBinaryCallback = _._registerUnaryCallback = _._registerCallback = _._runBinary = _._runUnary = _._run = null;
+      _.parent = t0;
+      _._async$_map = t1;
+    },
+    _CustomZone_bindCallback_closure: function _CustomZone_bindCallback_closure(t0, t1, t2) {
+      this.$this = t0;
+      this.registered = t1;
+      this.R = t2;
+    },
+    _CustomZone_bindUnaryCallback_closure: function _CustomZone_bindUnaryCallback_closure(t0, t1, t2, t3) {
+      var _ = this;
+      _.$this = t0;
+      _.registered = t1;
+      _.T = t2;
+      _.R = t3;
+    },
+    _CustomZone_bindCallbackGuarded_closure: function _CustomZone_bindCallbackGuarded_closure(t0, t1) {
+      this.$this = t0;
+      this.registered = t1;
+    },
+    _CustomZone_bindUnaryCallbackGuarded_closure: function _CustomZone_bindUnaryCallbackGuarded_closure(t0, t1, t2) {
+      this.$this = t0;
+      this.registered = t1;
+      this.T = t2;
+    },
+    _rootHandleUncaughtError_closure: function _rootHandleUncaughtError_closure(t0, t1) {
+      this._box_0 = t0;
+      this.stackTrace = t1;
+    },
+    _RootZone: function _RootZone() {
+    },
+    _RootZone_bindCallback_closure: function _RootZone_bindCallback_closure(t0, t1, t2) {
+      this.$this = t0;
+      this.f = t1;
+      this.R = t2;
+    },
+    _RootZone_bindCallbackGuarded_closure: function _RootZone_bindCallbackGuarded_closure(t0, t1) {
+      this.$this = t0;
+      this.f = t1;
+    },
+    _RootZone_bindUnaryCallbackGuarded_closure: function _RootZone_bindUnaryCallbackGuarded_closure(t0, t1, t2) {
+      this.$this = t0;
+      this.f = t1;
+      this.T = t2;
+    },
+    runZoned_closure: function runZoned_closure(t0) {
+      this._box_0 = t0;
+    },
+    HashMap_HashMap: function($K, $V) {
+      return new P._HashMap($K._eval$1("@<0>")._bind$1($V)._eval$1("_HashMap<1,2>"));
+    },
+    _HashMap__getTableEntry: function(table, key) {
+      var entry = table[key];
+      return entry === table ? null : entry;
+    },
+    _HashMap__setTableEntry: function(table, key, value) {
+      if (value == null)
+        table[key] = table;
+      else
+        table[key] = value;
+    },
+    _HashMap__newHashTable: function() {
+      var table = Object.create(null);
+      P._HashMap__setTableEntry(table, "<non-identifier-key>", table);
+      delete table["<non-identifier-key>"];
+      return table;
+    },
+    LinkedHashMap_LinkedHashMap: function($K, $V) {
+      return new H.JsLinkedHashMap($K._eval$1("@<0>")._bind$1($V)._eval$1("JsLinkedHashMap<1,2>"));
+    },
+    LinkedHashMap_LinkedHashMap$_literal: function(keyValuePairs, $K, $V) {
+      return $K._eval$1("@<0>")._bind$1($V)._eval$1("LinkedHashMap<1,2>")._check(H.fillLiteralMap(keyValuePairs, new H.JsLinkedHashMap($K._eval$1("@<0>")._bind$1($V)._eval$1("JsLinkedHashMap<1,2>"))));
+    },
+    LinkedHashMap_LinkedHashMap$_empty: function($K, $V) {
+      return new H.JsLinkedHashMap($K._eval$1("@<0>")._bind$1($V)._eval$1("JsLinkedHashMap<1,2>"));
+    },
+    LinkedHashSet_LinkedHashSet: function($E) {
+      return new P._LinkedHashSet($E._eval$1("_LinkedHashSet<0>"));
+    },
+    LinkedHashSet_LinkedHashSet$_empty: function($E) {
+      return new P._LinkedHashSet($E._eval$1("_LinkedHashSet<0>"));
+    },
+    LinkedHashSet_LinkedHashSet$_literal: function(values, $E) {
+      return $E._eval$1("LinkedHashSet<0>")._check(H.fillLiteralSet(values, new P._LinkedHashSet($E._eval$1("_LinkedHashSet<0>"))));
+    },
+    _LinkedHashSet__newHashTable: function() {
+      var table = Object.create(null);
+      H.assertHelper(table != null);
+      table["<non-identifier-key>"] = table;
+      delete table["<non-identifier-key>"];
+      return table;
+    },
+    _LinkedHashSetIterator$: function(_set, _modifications, $E) {
+      var t1 = new P._LinkedHashSetIterator(_set, _modifications, $E._eval$1("_LinkedHashSetIterator<0>"));
+      t1._collection$_cell = _set._collection$_first;
+      return t1;
+    },
+    HashMap_HashMap$from: function(other, $K, $V) {
+      var result = P.HashMap_HashMap($K, $V);
+      other.forEach$1(0, new P.HashMap_HashMap$from_closure(result, $K, $V));
+      return result;
+    },
+    IterableBase_iterableToShortString: function(iterable, leftDelimiter, rightDelimiter) {
+      var parts, t1;
+      if (P._isToStringVisiting(iterable)) {
+        if (leftDelimiter === "(" && rightDelimiter === ")")
+          return "(...)";
+        return leftDelimiter + "..." + rightDelimiter;
+      }
+      parts = H.setRuntimeTypeInfo([], type$.JSArray_String);
+      C.JSArray_methods.add$1($._toStringVisiting, iterable);
+      try {
+        P._iterablePartsToStrings(iterable, parts);
+      } finally {
+        H.assertHelper(C.JSArray_methods.get$last($._toStringVisiting) === iterable);
+        if (0 >= $._toStringVisiting.length)
+          return H.ioore($._toStringVisiting, -1);
+        $._toStringVisiting.pop();
+      }
+      t1 = P.StringBuffer__writeAll(leftDelimiter, type$.Iterable_dynamic._check(parts), ", ") + rightDelimiter;
+      return t1.charCodeAt(0) == 0 ? t1 : t1;
+    },
+    IterableBase_iterableToFullString: function(iterable, leftDelimiter, rightDelimiter) {
+      var buffer, t1;
+      if (P._isToStringVisiting(iterable))
+        return leftDelimiter + "..." + rightDelimiter;
+      buffer = new P.StringBuffer(leftDelimiter);
+      C.JSArray_methods.add$1($._toStringVisiting, iterable);
+      try {
+        t1 = buffer;
+        t1._contents = P.StringBuffer__writeAll(t1._contents, iterable, ", ");
+      } finally {
+        H.assertHelper(C.JSArray_methods.get$last($._toStringVisiting) === iterable);
+        if (0 >= $._toStringVisiting.length)
+          return H.ioore($._toStringVisiting, -1);
+        $._toStringVisiting.pop();
+      }
+      buffer._contents += rightDelimiter;
+      t1 = buffer._contents;
+      return t1.charCodeAt(0) == 0 ? t1 : t1;
+    },
+    _isToStringVisiting: function(o) {
+      var t1, i;
+      for (t1 = $._toStringVisiting.length, i = 0; i < t1; ++i)
+        if (o === $._toStringVisiting[i])
+          return true;
+      return false;
+    },
+    _iterablePartsToStrings: function(iterable, parts) {
+      var next, ultimateString, penultimateString, penultimate, ultimate, ultimate0, elision,
+        it = iterable.get$iterator(iterable),
+        $length = 0, count = 0;
+      while (true) {
+        if (!($length < 80 || count < 3))
+          break;
+        if (!it.moveNext$0())
+          return;
+        next = H.S(it.get$current());
+        C.JSArray_methods.add$1(parts, next);
+        $length += next.length + 2;
+        ++count;
+      }
+      if (!it.moveNext$0()) {
+        if (count <= 5)
+          return;
+        if (0 >= parts.length)
+          return H.ioore(parts, -1);
+        ultimateString = parts.pop();
+        if (0 >= parts.length)
+          return H.ioore(parts, -1);
+        penultimateString = parts.pop();
+      } else {
+        penultimate = it.get$current();
+        ++count;
+        if (!it.moveNext$0()) {
+          if (count <= 4) {
+            C.JSArray_methods.add$1(parts, H.S(penultimate));
+            return;
+          }
+          ultimateString = H.S(penultimate);
+          if (0 >= parts.length)
+            return H.ioore(parts, -1);
+          penultimateString = parts.pop();
+          $length += ultimateString.length + 2;
+        } else {
+          ultimate = it.get$current();
+          ++count;
+          H.assertHelper(count < 100);
+          for (; it.moveNext$0(); penultimate = ultimate, ultimate = ultimate0) {
+            ultimate0 = it.get$current();
+            ++count;
+            if (count > 100) {
+              while (true) {
+                if (!($length > 75 && count > 3))
+                  break;
+                if (0 >= parts.length)
+                  return H.ioore(parts, -1);
+                $length -= parts.pop().length + 2;
+                --count;
+              }
+              C.JSArray_methods.add$1(parts, "...");
+              return;
+            }
+          }
+          penultimateString = H.S(penultimate);
+          ultimateString = H.S(ultimate);
+          $length += ultimateString.length + penultimateString.length + 4;
+        }
+      }
+      if (count > parts.length + 2) {
+        $length += 5;
+        elision = "...";
+      } else
+        elision = null;
+      while (true) {
+        if (!($length > 80 && parts.length > 3))
+          break;
+        if (0 >= parts.length)
+          return H.ioore(parts, -1);
+        $length -= parts.pop().length + 2;
+        if (elision == null) {
+          $length += 5;
+          elision = "...";
+        }
+      }
+      if (elision != null)
+        C.JSArray_methods.add$1(parts, elision);
+      C.JSArray_methods.add$1(parts, penultimateString);
+      C.JSArray_methods.add$1(parts, ultimateString);
+    },
+    LinkedHashMap_LinkedHashMap$from: function(other, $K, $V) {
+      var result = P.LinkedHashMap_LinkedHashMap($K, $V);
+      other.forEach$1(0, new P.LinkedHashMap_LinkedHashMap$from_closure(result, $K, $V));
+      return result;
+    },
+    LinkedHashSet_LinkedHashSet$from: function(elements, $E) {
+      var t1,
+        result = P.LinkedHashSet_LinkedHashSet($E);
+      for (t1 = J.get$iterator$ax(elements); t1.moveNext$0();)
+        result.add$1(0, $E._check(t1.get$current()));
+      return result;
+    },
+    MapBase_mapToString: function(m) {
+      var result, t1 = {};
+      if (P._isToStringVisiting(m))
+        return "{...}";
+      result = new P.StringBuffer("");
+      try {
+        C.JSArray_methods.add$1($._toStringVisiting, m);
+        result._contents += "{";
+        t1.first = true;
+        m.forEach$1(0, new P.MapBase_mapToString_closure(t1, result));
+        result._contents += "}";
+      } finally {
+        H.assertHelper(C.JSArray_methods.get$last($._toStringVisiting) === m);
+        if (0 >= $._toStringVisiting.length)
+          return H.ioore($._toStringVisiting, -1);
+        $._toStringVisiting.pop();
+      }
+      t1 = result._contents;
+      return t1.charCodeAt(0) == 0 ? t1 : t1;
+    },
+    ListQueue$: function($E) {
+      var t1 = new P.ListQueue($E._eval$1("ListQueue<0>")),
+        t2 = new Array(8);
+      t2.fixed$length = Array;
+      t1.set$_table(H.setRuntimeTypeInfo(t2, $E._eval$1("JSArray<0>")));
+      return t1;
+    },
+    _ListQueueIterator$: function(queue, $E) {
+      return new P._ListQueueIterator(queue, queue._tail, queue._modificationCount, queue._head, $E._eval$1("_ListQueueIterator<0>"));
+    },
+    _HashMap: function _HashMap(t0) {
+      var _ = this;
+      _._collection$_length = 0;
+      _._keys = _._collection$_rest = _._nums = _._strings = null;
+      _.$ti = t0;
+    },
+    _IdentityHashMap: function _IdentityHashMap(t0) {
+      var _ = this;
+      _._collection$_length = 0;
+      _._keys = _._collection$_rest = _._nums = _._strings = null;
+      _.$ti = t0;
+    },
+    _HashMapKeyIterable: function _HashMapKeyIterable(t0, t1) {
+      this._map = t0;
+      this.$ti = t1;
+    },
+    _HashMapKeyIterator: function _HashMapKeyIterator(t0, t1, t2) {
+      var _ = this;
+      _._map = t0;
+      _._keys = t1;
+      _._offset = 0;
+      _._collection$_current = null;
+      _.$ti = t2;
+    },
+    _LinkedHashSet: function _LinkedHashSet(t0) {
+      var _ = this;
+      _._collection$_length = 0;
+      _._collection$_last = _._collection$_first = _._collection$_rest = _._nums = _._strings = null;
+      _._collection$_modifications = 0;
+      _.$ti = t0;
+    },
+    _LinkedHashSetCell: function _LinkedHashSetCell(t0) {
+      this._element = t0;
+      this._collection$_previous = this._collection$_next = null;
+    },
+    _LinkedHashSetIterator: function _LinkedHashSetIterator(t0, t1, t2) {
+      var _ = this;
+      _._set = t0;
+      _._collection$_modifications = t1;
+      _._collection$_current = _._collection$_cell = null;
+      _.$ti = t2;
+    },
+    UnmodifiableListView: function UnmodifiableListView(t0, t1) {
+      this._collection$_source = t0;
+      this.$ti = t1;
+    },
+    HashMap_HashMap$from_closure: function HashMap_HashMap$from_closure(t0, t1, t2) {
+      this.result = t0;
+      this.K = t1;
+      this.V = t2;
+    },
+    IterableBase: function IterableBase() {
+    },
+    LinkedHashMap_LinkedHashMap$from_closure: function LinkedHashMap_LinkedHashMap$from_closure(t0, t1, t2) {
+      this.result = t0;
+      this.K = t1;
+      this.V = t2;
+    },
+    ListBase: function ListBase() {
+    },
+    ListMixin: function ListMixin() {
+    },
+    MapBase: function MapBase() {
+    },
+    MapBase_mapToString_closure: function MapBase_mapToString_closure(t0, t1) {
+      this._box_0 = t0;
+      this.result = t1;
+    },
+    MapMixin: function MapMixin() {
+    },
+    _UnmodifiableMapMixin: function _UnmodifiableMapMixin() {
+    },
+    MapView: function MapView() {
+    },
+    UnmodifiableMapView: function UnmodifiableMapView(t0, t1) {
+      this._map = t0;
+      this.$ti = t1;
+    },
+    ListQueue: function ListQueue(t0) {
+      var _ = this;
+      _._table = null;
+      _._modificationCount = _._tail = _._head = 0;
+      _.$ti = t0;
+    },
+    _ListQueueIterator: function _ListQueueIterator(t0, t1, t2, t3, t4) {
+      var _ = this;
+      _._queue = t0;
+      _._end = t1;
+      _._modificationCount = t2;
+      _._position = t3;
+      _._collection$_current = null;
+      _.$ti = t4;
+    },
+    SetMixin: function SetMixin() {
+    },
+    SetBase: function SetBase() {
+    },
+    _SetBase: function _SetBase() {
+    },
+    _ListBase_Object_ListMixin: function _ListBase_Object_ListMixin() {
+    },
+    _SetBase_Object_SetMixin: function _SetBase_Object_SetMixin() {
+    },
+    _UnmodifiableMapView_MapView__UnmodifiableMapMixin: function _UnmodifiableMapView_MapView__UnmodifiableMapMixin() {
+    },
+    _parseJson: function(source, reviver) {
+      var parsed, e, exception, t1;
+      if (typeof source != "string")
+        throw H.wrapException(H.argumentErrorValue(source));
+      parsed = null;
+      try {
+        parsed = JSON.parse(source);
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        t1 = P.FormatException$(String(e), null, null);
+        throw H.wrapException(t1);
+      }
+      t1 = P._convertJsonToDartLazy(parsed);
+      return t1;
+    },
+    _convertJsonToDartLazy: function(object) {
+      var i;
+      if (object == null)
+        return null;
+      if (typeof object != "object")
+        return object;
+      if (Object.getPrototypeOf(object) !== Array.prototype)
+        return new P._JsonMap(object, Object.create(null));
+      for (i = 0; i < object.length; ++i)
+        object[i] = P._convertJsonToDartLazy(object[i]);
+      return object;
+    },
+    Utf8Decoder__convertIntercepted: function(allowMalformed, codeUnits, start, end) {
+      if (codeUnits instanceof Uint8Array)
+        return P.Utf8Decoder__convertInterceptedUint8List(false, codeUnits, start, end);
+      return null;
+    },
+    Utf8Decoder__convertInterceptedUint8List: function(allowMalformed, codeUnits, start, end) {
+      var t1, $length,
+        decoder = $.$get$Utf8Decoder__decoder();
+      if (decoder == null)
+        return null;
+      t1 = 0 === start;
+      if (t1 && true)
+        return P.Utf8Decoder__useTextDecoderChecked(decoder, codeUnits);
+      $length = codeUnits.length;
+      end = P.RangeError_checkValidRange(start, end, $length);
+      if (t1 && end === $length)
+        return P.Utf8Decoder__useTextDecoderChecked(decoder, codeUnits);
+      return P.Utf8Decoder__useTextDecoderChecked(decoder, codeUnits.subarray(start, end));
+    },
+    Utf8Decoder__useTextDecoderChecked: function(decoder, codeUnits) {
+      if (P.Utf8Decoder__unsafe(codeUnits))
+        return null;
+      return P.Utf8Decoder__useTextDecoderUnchecked(decoder, codeUnits);
+    },
+    Utf8Decoder__useTextDecoderUnchecked: function(decoder, codeUnits) {
+      var t1, exception;
+      try {
+        t1 = decoder.decode(codeUnits);
+        return t1;
+      } catch (exception) {
+        H.unwrapException(exception);
+      }
+      return null;
+    },
+    Utf8Decoder__unsafe: function(codeUnits) {
+      var i,
+        limit = codeUnits.length - 2;
+      for (i = 0; i < limit; ++i)
+        if (codeUnits[i] === 237)
+          if ((codeUnits[i + 1] & 224) === 160)
+            return true;
+      return false;
+    },
+    Utf8Decoder__makeDecoder: function() {
+      var t1, exception;
+      try {
+        t1 = new TextDecoder("utf-8", {fatal: true});
+        return t1;
+      } catch (exception) {
+        H.unwrapException(exception);
+      }
+      return null;
+    },
+    _scanOneByteCharacters: function(units, from, endIndex) {
+      var t1, i, unit;
+      for (t1 = J.getInterceptor$asx(units), i = from; i < endIndex; ++i) {
+        unit = t1.$index(units, i);
+        if (typeof unit !== "number")
+          return unit.$and();
+        if ((unit & 127) !== unit)
+          return i - from;
+      }
+      return endIndex - from;
+    },
+    Base64Codec__checkPadding: function(source, sourceIndex, sourceEnd, firstPadding, paddingCount, $length) {
+      if (C.JSInt_methods.$mod($length, 4) !== 0)
+        throw H.wrapException(P.FormatException$("Invalid base64 padding, padded length must be multiple of four, is " + $length, source, sourceEnd));
+      if (firstPadding + paddingCount !== $length)
+        throw H.wrapException(P.FormatException$("Invalid base64 padding, '=' not at the end", source, sourceIndex));
+      if (paddingCount > 2)
+        throw H.wrapException(P.FormatException$("Invalid base64 padding, more than two '=' characters", source, sourceIndex));
+    },
+    _JsonMap: function _JsonMap(t0, t1) {
+      this._original = t0;
+      this._processed = t1;
+      this._data = null;
+    },
+    _JsonMapKeyIterable: function _JsonMapKeyIterable(t0) {
+      this._parent = t0;
+    },
+    AsciiCodec: function AsciiCodec() {
+    },
+    _UnicodeSubsetEncoder: function _UnicodeSubsetEncoder() {
+    },
+    AsciiEncoder: function AsciiEncoder(t0) {
+      this._subsetMask = t0;
+    },
+    Base64Codec: function Base64Codec() {
+    },
+    Base64Encoder: function Base64Encoder() {
+    },
+    Codec: function Codec() {
+    },
+    _FusedCodec: function _FusedCodec(t0, t1, t2) {
+      this._convert$_first = t0;
+      this._second = t1;
+      this.$ti = t2;
+    },
+    Converter: function Converter() {
+    },
+    Encoding: function Encoding() {
+    },
+    JsonCodec: function JsonCodec() {
+    },
+    JsonDecoder: function JsonDecoder(t0) {
+      this._reviver = t0;
+    },
+    Utf8Codec: function Utf8Codec() {
+    },
+    Utf8Encoder: function Utf8Encoder() {
+    },
+    _Utf8Encoder: function _Utf8Encoder(t0) {
+      this._bufferIndex = this._carry = 0;
+      this._buffer = t0;
+    },
+    Utf8Decoder: function Utf8Decoder(t0) {
+      this._allowMalformed = t0;
+    },
+    _Utf8Decoder: function _Utf8Decoder(t0, t1) {
+      var _ = this;
+      _._allowMalformed = t0;
+      _._stringSink = t1;
+      _._isFirstCharacter = true;
+      _._extraUnits = _._expectedUnits = _._convert$_value = 0;
+    },
+    int_parse: function(source, onError, radix) {
+      var value = H.Primitives_parseInt(source, radix);
+      if (value != null)
+        return value;
+      if (onError != null)
+        return onError.call$1(source);
+      throw H.wrapException(P.FormatException$(source, null, null));
+    },
+    Error__objectToString: function(object) {
+      if (object instanceof H.Closure)
+        return object.toString$0(0);
+      return "Instance of '" + H.S(H.Primitives_objectTypeName(object)) + "'";
+    },
+    List_List$filled: function($length, fill, $E) {
+      var i,
+        result = J.JSArray_JSArray$fixed($length, $E);
+      if ($length !== 0 && true)
+        for (i = 0; i < result.length; ++i)
+          C.JSArray_methods.$indexSet(result, i, fill);
+      return result;
+    },
+    List_List$from: function(elements, growable, $E) {
+      var t1,
+        list = H.setRuntimeTypeInfo([], $E._eval$1("JSArray<0>"));
+      for (t1 = J.get$iterator$ax(elements); t1.moveNext$0();)
+        C.JSArray_methods.add$1(list, $E._check(t1.get$current()));
+      if (growable)
+        return list;
+      return $E._eval$1("List<0>")._check(J.JSArray_markFixedList(list));
+    },
+    List_List$unmodifiable: function(elements, $E) {
+      var result = P.List_List$from(elements, false, $E);
+      result.fixed$length = Array;
+      result.immutable$list = Array;
+      return $E._eval$1("List<0>")._check(result);
+    },
+    String_String$fromCharCodes: function(charCodes, start, end) {
+      var len;
+      if (Array.isArray(charCodes)) {
+        type$.JSArray_int._check(charCodes);
+        len = charCodes.length;
+        end = P.RangeError_checkValidRange(start, end, len);
+        return H.Primitives_stringFromCharCodes(start > 0 || end < len ? C.JSArray_methods.sublist$2(charCodes, start, end) : charCodes);
+      }
+      if (type$.NativeUint8List._is(charCodes))
+        return H.Primitives_stringFromNativeUint8List(charCodes, start, P.RangeError_checkValidRange(start, end, charCodes.length));
+      return P.String__stringFromIterable(charCodes, start, end);
+    },
+    String_String$fromCharCode: function(charCode) {
+      return H.Primitives_stringFromCharCode(charCode);
+    },
+    String__stringFromIterable: function(charCodes, start, end) {
+      var t1, it, i, list, _null = null;
+      if (start < 0)
+        throw H.wrapException(P.RangeError$range(start, 0, J.get$length$asx(charCodes), _null, _null));
+      t1 = end == null;
+      if (!t1 && end < start)
+        throw H.wrapException(P.RangeError$range(end, start, J.get$length$asx(charCodes), _null, _null));
+      it = J.get$iterator$ax(charCodes);
+      for (i = 0; i < start; ++i)
+        if (!it.moveNext$0())
+          throw H.wrapException(P.RangeError$range(start, 0, i, _null, _null));
+      list = [];
+      if (t1)
+        for (; it.moveNext$0();)
+          list.push(it.get$current());
+      else
+        for (i = start; i < end; ++i) {
+          if (!it.moveNext$0())
+            throw H.wrapException(P.RangeError$range(end, start, i, _null, _null));
+          list.push(it.get$current());
+        }
+      return H.Primitives_stringFromCharCodes(list);
+    },
+    RegExp_RegExp: function(source, multiLine) {
+      return new H.JSSyntaxRegExp(source, H.JSSyntaxRegExp_makeNative(source, multiLine, true, false, false, false));
+    },
+    StringBuffer__writeAll: function(string, objects, separator) {
+      var iterator = J.get$iterator$ax(objects);
+      if (!iterator.moveNext$0())
+        return string;
+      if (separator.length === 0) {
+        do
+          string += H.S(iterator.get$current());
+        while (iterator.moveNext$0());
+      } else {
+        string += H.S(iterator.get$current());
+        for (; iterator.moveNext$0();)
+          string = string + separator + H.S(iterator.get$current());
+      }
+      return string;
+    },
+    Uri_base: function() {
+      var uri = H.Primitives_currentUri();
+      if (uri != null)
+        return P.Uri_parse(uri);
+      throw H.wrapException(P.UnsupportedError$("'Uri.base' is not supported"));
+    },
+    _Uri__uriEncode: function(canonicalTable, text, encoding, spaceToPlus) {
+      var t1, bytes, i, t2, byte, t3,
+        _s16_ = "0123456789ABCDEF";
+      if (encoding === C.C_Utf8Codec) {
+        t1 = $.$get$_Uri__needsNoEncoding()._nativeRegExp;
+        if (typeof text != "string")
+          H.throwExpression(H.argumentErrorValue(text));
+        t1 = t1.test(text);
+      } else
+        t1 = false;
+      if (t1)
+        return text;
+      H._instanceType(encoding)._eval$1("Codec.S")._check(text);
+      bytes = encoding.get$encoder().convert$1(text);
+      for (t1 = bytes.length, i = 0, t2 = ""; i < t1; ++i) {
+        byte = bytes[i];
+        if (byte < 128) {
+          t3 = byte >>> 4;
+          if (t3 >= 8)
+            return H.ioore(canonicalTable, t3);
+          t3 = (canonicalTable[t3] & 1 << (byte & 15)) !== 0;
+        } else
+          t3 = false;
+        if (t3)
+          t2 += H.Primitives_stringFromCharCode(byte);
+        else
+          t2 = spaceToPlus && byte === 32 ? t2 + "+" : t2 + "%" + _s16_[byte >>> 4 & 15] + _s16_[byte & 15];
+      }
+      return t2.charCodeAt(0) == 0 ? t2 : t2;
+    },
+    StackTrace_current: function() {
+      var stackTrace, exception;
+      if (H.boolConversionCheck($.$get$_hasErrorStackProperty()))
+        return H.getTraceFromException(new Error());
+      try {
+        throw H.wrapException("");
+      } catch (exception) {
+        H.unwrapException(exception);
+        stackTrace = H.getTraceFromException(exception);
+        return stackTrace;
+      }
+    },
+    DateTime__fourDigits: function(n) {
+      var absN = Math.abs(n),
+        sign = n < 0 ? "-" : "";
+      if (absN >= 1000)
+        return "" + n;
+      if (absN >= 100)
+        return sign + "0" + absN;
+      if (absN >= 10)
+        return sign + "00" + absN;
+      return sign + "000" + absN;
+    },
+    DateTime__threeDigits: function(n) {
+      if (n >= 100)
+        return "" + n;
+      if (n >= 10)
+        return "0" + n;
+      return "00" + n;
+    },
+    DateTime__twoDigits: function(n) {
+      if (n >= 10)
+        return "" + n;
+      return "0" + n;
+    },
+    Duration$: function(microseconds, minutes) {
+      if (typeof microseconds !== "number")
+        return H.iae(microseconds);
+      return new P.Duration(60000000 * minutes + microseconds);
+    },
+    Error_safeToString: function(object) {
+      if (typeof object == "number" || H._isBool(object) || null == object)
+        return J.toString$0$(object);
+      if (typeof object == "string")
+        return JSON.stringify(object);
+      return P.Error__objectToString(object);
+    },
+    AssertionError$: function(message) {
+      return new P.AssertionError(message);
+    },
+    ArgumentError$: function(message) {
+      return new P.ArgumentError(false, null, null, message);
+    },
+    ArgumentError$value: function(value, $name, message) {
+      return new P.ArgumentError(true, value, $name, message);
+    },
+    ArgumentError$notNull: function($name) {
+      return new P.ArgumentError(false, null, $name, "Must not be null");
+    },
+    RangeError$: function(message) {
+      var _null = null;
+      return new P.RangeError(_null, _null, false, _null, _null, message);
+    },
+    RangeError$value: function(value, $name) {
+      return new P.RangeError(null, null, true, value, $name, "Value not in range");
+    },
+    RangeError$range: function(invalidValue, minValue, maxValue, $name, message) {
+      return new P.RangeError(minValue, maxValue, true, invalidValue, $name, "Invalid value");
+    },
+    RangeError_checkValueInInterval: function(value, minValue, maxValue, $name) {
+      if (value < minValue || value > maxValue)
+        throw H.wrapException(P.RangeError$range(value, minValue, maxValue, $name, null));
+    },
+    RangeError_checkValidRange: function(start, end, $length) {
+      if (0 > start || start > $length)
+        throw H.wrapException(P.RangeError$range(start, 0, $length, "start", null));
+      if (end != null) {
+        if (start > end || end > $length)
+          throw H.wrapException(P.RangeError$range(end, start, $length, "end", null));
+        return end;
+      }
+      return $length;
+    },
+    RangeError_checkNotNegative: function(value, $name) {
+      if (typeof value !== "number")
+        return value.$lt();
+      if (value < 0)
+        throw H.wrapException(P.RangeError$range(value, 0, null, $name, null));
+    },
+    IndexError$: function(invalidValue, indexable, $name, message, $length) {
+      var t1 = H._checkIntNullable($length == null ? J.get$length$asx(indexable) : $length);
+      return new P.IndexError(t1, true, invalidValue, $name, "Index out of range");
+    },
+    UnsupportedError$: function(message) {
+      return new P.UnsupportedError(message);
+    },
+    UnimplementedError$: function(message) {
+      return new P.UnimplementedError(message);
+    },
+    StateError$: function(message) {
+      return new P.StateError(message);
+    },
+    ConcurrentModificationError$: function(modifiedObject) {
+      return new P.ConcurrentModificationError(modifiedObject);
+    },
+    FormatException$: function(message, source, offset) {
+      return new P.FormatException(message, source, offset);
+    },
+    List_List$generate: function($length, generator, growable, $E) {
+      var i,
+        result = H.setRuntimeTypeInfo([], $E._eval$1("JSArray<0>"));
+      C.JSArray_methods.set$length(result, $length);
+      for (i = 0; i < $length; ++i)
+        C.JSArray_methods.$indexSet(result, i, generator.call$1(i));
+      return result;
+    },
+    Map_castFrom: function(source, $K, $V, K2, V2) {
+      return new H.CastMap(source, $K._eval$1("@<0>")._bind$1($V)._bind$1(K2)._bind$1(V2)._eval$1("CastMap<1,2,3,4>"));
+    },
+    print: function(object) {
+      var line = H.S(object),
+        t1 = $.printToZone;
+      if (t1 == null)
+        H.printString(line);
+      else
+        t1.call$1(line);
+    },
+    _combineSurrogatePair: function(start, end) {
+      return 65536 + ((start & 1023) << 10) + (end & 1023);
+    },
+    Uri_parse: function(uri) {
+      var delta, t1, indices, schemeEnd, hostStart, portStart, pathStart, queryStart, fragmentStart, isSimple, scheme, t2, schemeAuth, queryStart0, pathStart0, _null = null,
+        end = uri.length;
+      if (end >= 5) {
+        delta = ((J._codeUnitAt$1$s(uri, 4) ^ 58) * 3 | C.JSString_methods._codeUnitAt$1(uri, 0) ^ 100 | C.JSString_methods._codeUnitAt$1(uri, 1) ^ 97 | C.JSString_methods._codeUnitAt$1(uri, 2) ^ 116 | C.JSString_methods._codeUnitAt$1(uri, 3) ^ 97) >>> 0;
+        if (delta === 0)
+          return P.UriData__parse(end < end ? C.JSString_methods.substring$2(uri, 0, end) : uri, 5, _null).get$uri();
+        else if (delta === 32)
+          return P.UriData__parse(C.JSString_methods.substring$2(uri, 5, end), 0, _null).get$uri();
+      }
+      t1 = new Array(8);
+      t1.fixed$length = Array;
+      indices = H.setRuntimeTypeInfo(t1, type$.JSArray_int);
+      C.JSArray_methods.$indexSet(indices, 0, 0);
+      C.JSArray_methods.$indexSet(indices, 1, -1);
+      C.JSArray_methods.$indexSet(indices, 2, -1);
+      C.JSArray_methods.$indexSet(indices, 7, -1);
+      C.JSArray_methods.$indexSet(indices, 3, 0);
+      C.JSArray_methods.$indexSet(indices, 4, 0);
+      C.JSArray_methods.$indexSet(indices, 5, end);
+      C.JSArray_methods.$indexSet(indices, 6, end);
+      if (P._scan(uri, 0, end, 0, indices) >= 14)
+        C.JSArray_methods.$indexSet(indices, 7, end);
+      schemeEnd = indices[1];
+      if (typeof schemeEnd !== "number")
+        return schemeEnd.$ge();
+      if (schemeEnd >= 0)
+        if (P._scan(uri, 0, schemeEnd, 20, indices) === 20)
+          indices[7] = schemeEnd;
+      t1 = indices[2];
+      if (typeof t1 !== "number")
+        return t1.$add();
+      hostStart = t1 + 1;
+      portStart = indices[3];
+      pathStart = indices[4];
+      queryStart = indices[5];
+      fragmentStart = indices[6];
+      if (typeof fragmentStart !== "number")
+        return fragmentStart.$lt();
+      if (typeof queryStart !== "number")
+        return H.iae(queryStart);
+      if (fragmentStart < queryStart)
+        queryStart = fragmentStart;
+      if (typeof pathStart !== "number")
+        return pathStart.$lt();
+      if (pathStart < hostStart)
+        pathStart = queryStart;
+      else if (pathStart <= schemeEnd)
+        pathStart = schemeEnd + 1;
+      if (typeof portStart !== "number")
+        return portStart.$lt();
+      if (portStart < hostStart)
+        portStart = pathStart;
+      H.assertHelper(hostStart === 0 || schemeEnd <= hostStart);
+      H.assertHelper(hostStart <= portStart);
+      H.assertHelper(schemeEnd <= pathStart);
+      H.assertHelper(portStart <= pathStart);
+      H.assertHelper(pathStart <= queryStart);
+      H.assertHelper(queryStart <= fragmentStart);
+      t1 = indices[7];
+      if (typeof t1 !== "number")
+        return t1.$lt();
+      isSimple = t1 < 0;
+      if (isSimple)
+        if (hostStart > schemeEnd + 3) {
+          scheme = _null;
+          isSimple = false;
+        } else {
+          t1 = portStart > 0;
+          if (t1 && portStart + 1 === pathStart) {
+            scheme = _null;
+            isSimple = false;
+          } else {
+            if (!(queryStart < end && queryStart === pathStart + 2 && J.startsWith$2$s(uri, "..", pathStart)))
+              t2 = queryStart > pathStart + 2 && J.startsWith$2$s(uri, "/..", queryStart - 3);
+            else
+              t2 = true;
+            if (t2) {
+              scheme = _null;
+              isSimple = false;
+            } else {
+              if (schemeEnd === 4)
+                if (J.startsWith$2$s(uri, "file", 0)) {
+                  if (hostStart <= 0) {
+                    if (!C.JSString_methods.startsWith$2(uri, "/", pathStart)) {
+                      schemeAuth = "file:///";
+                      delta = 3;
+                    } else {
+                      schemeAuth = "file://";
+                      delta = 2;
+                    }
+                    uri = schemeAuth + C.JSString_methods.substring$2(uri, pathStart, end);
+                    schemeEnd -= 0;
+                    t1 = delta - 0;
+                    queryStart += t1;
+                    fragmentStart += t1;
+                    end = uri.length;
+                    hostStart = 7;
+                    portStart = 7;
+                    pathStart = 7;
+                  } else if (pathStart === queryStart) {
+                    queryStart0 = queryStart + 1;
+                    ++fragmentStart;
+                    uri = C.JSString_methods.replaceRange$3(uri, pathStart, queryStart, "/");
+                    ++end;
+                    queryStart = queryStart0;
+                  }
+                  scheme = "file";
+                } else if (C.JSString_methods.startsWith$2(uri, "http", 0)) {
+                  if (t1 && portStart + 3 === pathStart && C.JSString_methods.startsWith$2(uri, "80", portStart + 1)) {
+                    pathStart0 = pathStart - 3;
+                    queryStart -= 3;
+                    fragmentStart -= 3;
+                    uri = C.JSString_methods.replaceRange$3(uri, portStart, pathStart, "");
+                    end -= 3;
+                    pathStart = pathStart0;
+                  }
+                  scheme = "http";
+                } else
+                  scheme = _null;
+              else if (schemeEnd === 5 && J.startsWith$2$s(uri, "https", 0)) {
+                if (t1 && portStart + 4 === pathStart && J.startsWith$2$s(uri, "443", portStart + 1)) {
+                  pathStart0 = pathStart - 4;
+                  queryStart -= 4;
+                  fragmentStart -= 4;
+                  uri = J.replaceRange$3$asx(uri, portStart, pathStart, "");
+                  end -= 3;
+                  pathStart = pathStart0;
+                }
+                scheme = "https";
+              } else
+                scheme = _null;
+              isSimple = true;
+            }
+          }
+        }
+      else
+        scheme = _null;
+      if (isSimple) {
+        t1 = uri.length;
+        if (end < t1) {
+          uri = J.substring$2$s(uri, 0, end);
+          schemeEnd -= 0;
+          hostStart -= 0;
+          portStart -= 0;
+          pathStart -= 0;
+          queryStart -= 0;
+          fragmentStart -= 0;
+        }
+        return new P._SimpleUri(uri, schemeEnd, hostStart, portStart, pathStart, queryStart, fragmentStart, scheme);
+      }
+      return P._Uri__Uri$notSimple(uri, 0, end, schemeEnd, hostStart, portStart, pathStart, queryStart, fragmentStart, scheme);
+    },
+    Uri_decodeComponent: function(encodedComponent) {
+      H._checkStringNullable(encodedComponent);
+      return P._Uri__uriDecode(encodedComponent, 0, encodedComponent.length, C.C_Utf8Codec, false);
+    },
+    Uri__parseIPv4Address: function(host, start, end) {
+      var t1, i, partStart, partIndex, char, part, partIndex0, _null = null,
+        _s43_ = "IPv4 address should contain exactly 4 parts",
+        _s37_ = "each part must be in the range 0..255",
+        error = new P.Uri__parseIPv4Address_error(host),
+        result = new Uint8Array(4);
+      for (t1 = result.length, i = start, partStart = i, partIndex = 0; i < end; ++i) {
+        char = C.JSString_methods.codeUnitAt$1(host, i);
+        if (char !== 46) {
+          if ((char ^ 48) > 9)
+            error.call$2("invalid character", i);
+        } else {
+          if (partIndex === 3)
+            error.call$2(_s43_, i);
+          part = P.int_parse(C.JSString_methods.substring$2(host, partStart, i), _null, _null);
+          if (typeof part !== "number")
+            return part.$gt();
+          if (part > 255)
+            error.call$2(_s37_, partStart);
+          partIndex0 = partIndex + 1;
+          if (partIndex >= t1)
+            return H.ioore(result, partIndex);
+          result[partIndex] = part;
+          partStart = i + 1;
+          partIndex = partIndex0;
+        }
+      }
+      if (partIndex !== 3)
+        error.call$2(_s43_, end);
+      part = P.int_parse(C.JSString_methods.substring$2(host, partStart, end), _null, _null);
+      if (typeof part !== "number")
+        return part.$gt();
+      if (part > 255)
+        error.call$2(_s37_, partStart);
+      if (partIndex >= t1)
+        return H.ioore(result, partIndex);
+      result[partIndex] = part;
+      return result;
+    },
+    Uri_parseIPv6Address: function(host, start, end) {
+      var parts, i, partStart, wildcardSeen, seenDot, char, atEnd, t1, last, bytes, t2, wildCardLength, index, value, j, t3,
+        error = new P.Uri_parseIPv6Address_error(host),
+        parseHex = new P.Uri_parseIPv6Address_parseHex(error, host);
+      if (host.length < 2)
+        error.call$1("address is too short");
+      parts = H.setRuntimeTypeInfo([], type$.JSArray_int);
+      for (i = start, partStart = i, wildcardSeen = false, seenDot = false; i < end; ++i) {
+        char = C.JSString_methods.codeUnitAt$1(host, i);
+        if (char === 58) {
+          if (i === start) {
+            ++i;
+            if (C.JSString_methods.codeUnitAt$1(host, i) !== 58)
+              error.call$2("invalid start colon.", i);
+            partStart = i;
+          }
+          if (i === partStart) {
+            if (wildcardSeen)
+              error.call$2("only one wildcard `::` is allowed", i);
+            C.JSArray_methods.add$1(parts, -1);
+            wildcardSeen = true;
+          } else
+            C.JSArray_methods.add$1(parts, parseHex.call$2(partStart, i));
+          partStart = i + 1;
+        } else if (char === 46)
+          seenDot = true;
+      }
+      if (parts.length === 0)
+        error.call$1("too few parts");
+      atEnd = partStart === end;
+      t1 = C.JSArray_methods.get$last(parts);
+      if (atEnd && t1 !== -1)
+        error.call$2("expected a part after last `:`", end);
+      if (!atEnd)
+        if (!seenDot)
+          C.JSArray_methods.add$1(parts, parseHex.call$2(partStart, end));
+        else {
+          last = P.Uri__parseIPv4Address(host, partStart, end);
+          C.JSArray_methods.add$1(parts, (last[0] << 8 | last[1]) >>> 0);
+          C.JSArray_methods.add$1(parts, (last[2] << 8 | last[3]) >>> 0);
+        }
+      if (wildcardSeen) {
+        if (parts.length > 7)
+          error.call$1("an address with a wildcard must have less than 7 parts");
+      } else if (parts.length !== 8)
+        error.call$1("an address without a wildcard must contain exactly 8 parts");
+      bytes = new Uint8Array(16);
+      for (t1 = parts.length, t2 = bytes.length, wildCardLength = 9 - t1, i = 0, index = 0; i < t1; ++i) {
+        value = parts[i];
+        if (value === -1)
+          for (j = 0; j < wildCardLength; ++j) {
+            if (index < 0 || index >= t2)
+              return H.ioore(bytes, index);
+            bytes[index] = 0;
+            t3 = index + 1;
+            if (t3 >= t2)
+              return H.ioore(bytes, t3);
+            bytes[t3] = 0;
+            index += 2;
+          }
+        else {
+          t3 = C.JSInt_methods._shrOtherPositive$1(value, 8);
+          if (index < 0 || index >= t2)
+            return H.ioore(bytes, index);
+          bytes[index] = t3;
+          t3 = index + 1;
+          if (t3 >= t2)
+            return H.ioore(bytes, t3);
+          bytes[t3] = value & 255;
+          index += 2;
+        }
+      }
+      return bytes;
+    },
+    _Uri__Uri$notSimple: function(uri, start, end, schemeEnd, hostStart, portStart, pathStart, queryStart, fragmentStart, scheme) {
+      var userInfoStart, userInfo, host, t1, port, path, query, _null = null;
+      if (scheme == null)
+        if (schemeEnd > start)
+          scheme = P._Uri__makeScheme(uri, start, schemeEnd);
+        else {
+          if (schemeEnd === start)
+            P._Uri__fail(uri, start, "Invalid empty scheme");
+          scheme = "";
+        }
+      if (hostStart > start) {
+        userInfoStart = schemeEnd + 3;
+        userInfo = userInfoStart < hostStart ? P._Uri__makeUserInfo(uri, userInfoStart, hostStart - 1) : "";
+        host = P._Uri__makeHost(uri, hostStart, portStart, false);
+        t1 = portStart + 1;
+        port = t1 < pathStart ? P._Uri__makePort(P.int_parse(J.substring$2$s(uri, t1, pathStart), new P._Uri__Uri$notSimple_closure(uri, portStart), _null), scheme) : _null;
+      } else {
+        port = _null;
+        host = port;
+        userInfo = "";
+      }
+      path = P._Uri__makePath(uri, pathStart, queryStart, _null, scheme, host != null);
+      query = queryStart < fragmentStart ? P._Uri__makeQuery(uri, queryStart + 1, fragmentStart, _null) : _null;
+      return new P._Uri(scheme, userInfo, host, port, path, query, fragmentStart < end ? P._Uri__makeFragment(uri, fragmentStart + 1, end) : _null);
+    },
+    _Uri__Uri: function(host, path, pathSegments, scheme) {
+      var userInfo, query, fragment, port, isFile, t1, hasAuthority, t2, _null = null;
+      scheme = P._Uri__makeScheme(scheme, 0, scheme == null ? 0 : scheme.length);
+      userInfo = P._Uri__makeUserInfo(_null, 0, 0);
+      host = P._Uri__makeHost(host, 0, host == null ? 0 : host.length, false);
+      query = P._Uri__makeQuery(_null, 0, 0, _null);
+      fragment = P._Uri__makeFragment(_null, 0, 0);
+      port = P._Uri__makePort(_null, scheme);
+      isFile = scheme === "file";
+      if (host == null)
+        t1 = userInfo.length !== 0 || port != null || isFile;
+      else
+        t1 = false;
+      if (t1)
+        host = "";
+      t1 = host == null;
+      hasAuthority = !t1;
+      path = P._Uri__makePath(path, 0, path == null ? 0 : path.length, pathSegments, scheme, hasAuthority);
+      t2 = scheme.length === 0;
+      if (t2 && t1 && !C.JSString_methods.startsWith$1(path, "/"))
+        path = P._Uri__normalizeRelativePath(path, !t2 || hasAuthority);
+      else
+        path = P._Uri__removeDotSegments(path);
+      return new P._Uri(scheme, userInfo, t1 && C.JSString_methods.startsWith$1(path, "//") ? "" : host, port, path, query, fragment);
+    },
+    _Uri__defaultPort: function(scheme) {
+      if (scheme === "http")
+        return 80;
+      if (scheme === "https")
+        return 443;
+      return 0;
+    },
+    _Uri__fail: function(uri, index, message) {
+      throw H.wrapException(P.FormatException$(message, uri, index));
+    },
+    _Uri__Uri$file: function(path, windows) {
+      return windows ? P._Uri__makeWindowsFileUrl(path, false) : P._Uri__makeFileUri(path, false);
+    },
+    _Uri__checkNonWindowsPathReservedCharacters: function(segments, argumentError) {
+      C.JSArray_methods.forEach$1(segments, new P._Uri__checkNonWindowsPathReservedCharacters_closure(false));
+    },
+    _Uri__checkWindowsPathReservedCharacters: function(segments, argumentError, firstSegment) {
+      var t1, t2;
+      for (t1 = H.SubListIterable$(segments, firstSegment, null, H._arrayInstanceType(segments)._precomputed1), t1 = new H.ListIterator(t1, t1.get$length(t1), t1.$ti._eval$1("ListIterator<ListIterable.E>")); t1.moveNext$0();) {
+        t2 = t1.__internal$_current;
+        if (J.contains$1$asx(t2, P.RegExp_RegExp('["*/:<>?\\\\|]', false)))
+          if (argumentError)
+            throw H.wrapException(P.ArgumentError$("Illegal character in path"));
+          else
+            throw H.wrapException(P.UnsupportedError$("Illegal character in path: " + t2));
+      }
+    },
+    _Uri__checkWindowsDriveLetter: function(charCode, argumentError) {
+      var t1,
+        _s21_ = "Illegal drive letter ";
+      if (!(65 <= charCode && charCode <= 90))
+        t1 = 97 <= charCode && charCode <= 122;
+      else
+        t1 = true;
+      if (t1)
+        return;
+      if (argumentError)
+        throw H.wrapException(P.ArgumentError$(_s21_ + P.String_String$fromCharCode(charCode)));
+      else
+        throw H.wrapException(P.UnsupportedError$(_s21_ + P.String_String$fromCharCode(charCode)));
+    },
+    _Uri__makeFileUri: function(path, slashTerminated) {
+      var _null = null,
+        segments = H.setRuntimeTypeInfo(path.split("/"), type$.JSArray_String);
+      if (C.JSString_methods.startsWith$1(path, "/"))
+        return P._Uri__Uri(_null, _null, segments, "file");
+      else
+        return P._Uri__Uri(_null, _null, segments, _null);
+    },
+    _Uri__makeWindowsFileUrl: function(path, slashTerminated) {
+      var t1, pathSegments, pathStart, hostPart, _s1_ = "\\", _null = null, _s4_ = "file";
+      if (C.JSString_methods.startsWith$1(path, "\\\\?\\"))
+        if (C.JSString_methods.startsWith$2(path, "UNC\\", 4))
+          path = C.JSString_methods.replaceRange$3(path, 0, 7, _s1_);
+        else {
+          path = C.JSString_methods.substring$1(path, 4);
+          if (path.length < 3 || C.JSString_methods._codeUnitAt$1(path, 1) !== 58 || C.JSString_methods._codeUnitAt$1(path, 2) !== 92)
+            throw H.wrapException(P.ArgumentError$("Windows paths with \\\\?\\ prefix must be absolute"));
+        }
+      else
+        path = H.stringReplaceAllUnchecked(path, "/", _s1_);
+      t1 = path.length;
+      if (t1 > 1 && C.JSString_methods._codeUnitAt$1(path, 1) === 58) {
+        P._Uri__checkWindowsDriveLetter(C.JSString_methods._codeUnitAt$1(path, 0), true);
+        if (t1 === 2 || C.JSString_methods._codeUnitAt$1(path, 2) !== 92)
+          throw H.wrapException(P.ArgumentError$("Windows paths with drive letter must be absolute"));
+        pathSegments = H.setRuntimeTypeInfo(path.split(_s1_), type$.JSArray_String);
+        P._Uri__checkWindowsPathReservedCharacters(pathSegments, true, 1);
+        return P._Uri__Uri(_null, _null, pathSegments, _s4_);
+      }
+      if (C.JSString_methods.startsWith$1(path, _s1_))
+        if (C.JSString_methods.startsWith$2(path, _s1_, 1)) {
+          pathStart = C.JSString_methods.indexOf$2(path, _s1_, 2);
+          t1 = pathStart < 0;
+          hostPart = t1 ? C.JSString_methods.substring$1(path, 2) : C.JSString_methods.substring$2(path, 2, pathStart);
+          pathSegments = H.setRuntimeTypeInfo((t1 ? "" : C.JSString_methods.substring$1(path, pathStart + 1)).split(_s1_), type$.JSArray_String);
+          P._Uri__checkWindowsPathReservedCharacters(pathSegments, true, 0);
+          return P._Uri__Uri(hostPart, _null, pathSegments, _s4_);
+        } else {
+          pathSegments = H.setRuntimeTypeInfo(path.split(_s1_), type$.JSArray_String);
+          P._Uri__checkWindowsPathReservedCharacters(pathSegments, true, 0);
+          return P._Uri__Uri(_null, _null, pathSegments, _s4_);
+        }
+      else {
+        pathSegments = H.setRuntimeTypeInfo(path.split(_s1_), type$.JSArray_String);
+        P._Uri__checkWindowsPathReservedCharacters(pathSegments, true, 0);
+        return P._Uri__Uri(_null, _null, pathSegments, _null);
+      }
+    },
+    _Uri__makePort: function(port, scheme) {
+      if (port != null && port === P._Uri__defaultPort(scheme))
+        return null;
+      return port;
+    },
+    _Uri__makeHost: function(host, start, end, strictIPv6) {
+      var t1, t2, index, zoneIDstart, zoneID, i;
+      if (host == null)
+        return null;
+      if (start === end)
+        return "";
+      if (C.JSString_methods.codeUnitAt$1(host, start) === 91) {
+        t1 = end - 1;
+        if (C.JSString_methods.codeUnitAt$1(host, t1) !== 93)
+          P._Uri__fail(host, start, "Missing end `]` to match `[` in host");
+        t2 = start + 1;
+        index = P._Uri__checkZoneID(host, t2, t1);
+        if (index < t1) {
+          zoneIDstart = index + 1;
+          zoneID = P._Uri__normalizeZoneID(host, C.JSString_methods.startsWith$2(host, "25", zoneIDstart) ? index + 3 : zoneIDstart, t1, "%25");
+        } else
+          zoneID = "";
+        P.Uri_parseIPv6Address(host, t2, index);
+        return C.JSString_methods.substring$2(host, start, index).toLowerCase() + zoneID + "]";
+      }
+      for (i = start; i < end; ++i)
+        if (C.JSString_methods.codeUnitAt$1(host, i) === 58) {
+          index = C.JSString_methods.indexOf$2(host, "%", start);
+          index = index >= start && index < end ? index : end;
+          if (index < end) {
+            zoneIDstart = index + 1;
+            zoneID = P._Uri__normalizeZoneID(host, C.JSString_methods.startsWith$2(host, "25", zoneIDstart) ? index + 3 : zoneIDstart, end, "%25");
+          } else
+            zoneID = "";
+          P.Uri_parseIPv6Address(host, start, index);
+          return "[" + C.JSString_methods.substring$2(host, start, index) + zoneID + "]";
+        }
+      return P._Uri__normalizeRegName(host, start, end);
+    },
+    _Uri__checkZoneID: function(host, start, end) {
+      var index = C.JSString_methods.indexOf$2(host, "%", start);
+      return index >= start && index < end ? index : end;
+    },
+    _Uri__normalizeZoneID: function(host, start, end, prefix) {
+      var index, sectionStart, isNormalized, char, replacement, t1, t2, tail, sourceLength,
+        buffer = prefix !== "" ? new P.StringBuffer(prefix) : null;
+      for (index = start, sectionStart = index, isNormalized = true; index < end;) {
+        char = C.JSString_methods.codeUnitAt$1(host, index);
+        if (char === 37) {
+          replacement = P._Uri__normalizeEscape(host, index, true);
+          t1 = replacement == null;
+          if (t1 && isNormalized) {
+            index += 3;
+            continue;
+          }
+          if (buffer == null)
+            buffer = new P.StringBuffer("");
+          t2 = buffer._contents += C.JSString_methods.substring$2(host, sectionStart, index);
+          if (t1)
+            replacement = C.JSString_methods.substring$2(host, index, index + 3);
+          else if (replacement === "%")
+            P._Uri__fail(host, index, "ZoneID should not contain % anymore");
+          buffer._contents = t2 + replacement;
+          index += 3;
+          sectionStart = index;
+          isNormalized = true;
+        } else {
+          if (char < 127) {
+            t1 = char >>> 4;
+            if (t1 >= 8)
+              return H.ioore(C.List_nxB, t1);
+            t1 = (C.List_nxB[t1] & 1 << (char & 15)) !== 0;
+          } else
+            t1 = false;
+          if (t1) {
+            if (isNormalized && 65 <= char && 90 >= char) {
+              if (buffer == null)
+                buffer = new P.StringBuffer("");
+              if (sectionStart < index) {
+                buffer._contents += C.JSString_methods.substring$2(host, sectionStart, index);
+                sectionStart = index;
+              }
+              isNormalized = false;
+            }
+            ++index;
+          } else {
+            if ((char & 64512) === 55296 && index + 1 < end) {
+              tail = C.JSString_methods.codeUnitAt$1(host, index + 1);
+              if ((tail & 64512) === 56320) {
+                char = 65536 | (char & 1023) << 10 | tail & 1023;
+                sourceLength = 2;
+              } else
+                sourceLength = 1;
+            } else
+              sourceLength = 1;
+            if (buffer == null)
+              buffer = new P.StringBuffer("");
+            buffer._contents += C.JSString_methods.substring$2(host, sectionStart, index);
+            buffer._contents += P._Uri__escapeChar(char);
+            index += sourceLength;
+            sectionStart = index;
+          }
+        }
+      }
+      if (buffer == null)
+        return C.JSString_methods.substring$2(host, start, end);
+      if (sectionStart < end)
+        buffer._contents += C.JSString_methods.substring$2(host, sectionStart, end);
+      t1 = buffer._contents;
+      return t1.charCodeAt(0) == 0 ? t1 : t1;
+    },
+    _Uri__normalizeRegName: function(host, start, end) {
+      var index, sectionStart, buffer, isNormalized, char, replacement, t1, slice, t2, sourceLength, tail;
+      for (index = start, sectionStart = index, buffer = null, isNormalized = true; index < end;) {
+        char = C.JSString_methods.codeUnitAt$1(host, index);
+        if (char === 37) {
+          replacement = P._Uri__normalizeEscape(host, index, true);
+          t1 = replacement == null;
+          if (t1 && isNormalized) {
+            index += 3;
+            continue;
+          }
+          if (buffer == null)
+            buffer = new P.StringBuffer("");
+          slice = C.JSString_methods.substring$2(host, sectionStart, index);
+          t2 = buffer._contents += !isNormalized ? slice.toLowerCase() : slice;
+          if (t1) {
+            replacement = C.JSString_methods.substring$2(host, index, index + 3);
+            sourceLength = 3;
+          } else if (replacement === "%") {
+            replacement = "%25";
+            sourceLength = 1;
+          } else
+            sourceLength = 3;
+          buffer._contents = t2 + replacement;
+          index += sourceLength;
+          sectionStart = index;
+          isNormalized = true;
+        } else {
+          if (char < 127) {
+            t1 = char >>> 4;
+            if (t1 >= 8)
+              return H.ioore(C.List_qNA, t1);
+            t1 = (C.List_qNA[t1] & 1 << (char & 15)) !== 0;
+          } else
+            t1 = false;
+          if (t1) {
+            if (isNormalized && 65 <= char && 90 >= char) {
+              if (buffer == null)
+                buffer = new P.StringBuffer("");
+              if (sectionStart < index) {
+                buffer._contents += C.JSString_methods.substring$2(host, sectionStart, index);
+                sectionStart = index;
+              }
+              isNormalized = false;
+            }
+            ++index;
+          } else {
+            if (char <= 93) {
+              t1 = char >>> 4;
+              if (t1 >= 8)
+                return H.ioore(C.List_2Vk, t1);
+              t1 = (C.List_2Vk[t1] & 1 << (char & 15)) !== 0;
+            } else
+              t1 = false;
+            if (t1)
+              P._Uri__fail(host, index, "Invalid character");
+            else {
+              if ((char & 64512) === 55296 && index + 1 < end) {
+                tail = C.JSString_methods.codeUnitAt$1(host, index + 1);
+                if ((tail & 64512) === 56320) {
+                  char = 65536 | (char & 1023) << 10 | tail & 1023;
+                  sourceLength = 2;
+                } else
+                  sourceLength = 1;
+              } else
+                sourceLength = 1;
+              if (buffer == null)
+                buffer = new P.StringBuffer("");
+              slice = C.JSString_methods.substring$2(host, sectionStart, index);
+              buffer._contents += !isNormalized ? slice.toLowerCase() : slice;
+              buffer._contents += P._Uri__escapeChar(char);
+              index += sourceLength;
+              sectionStart = index;
+            }
+          }
+        }
+      }
+      if (buffer == null)
+        return C.JSString_methods.substring$2(host, start, end);
+      if (sectionStart < end) {
+        slice = C.JSString_methods.substring$2(host, sectionStart, end);
+        buffer._contents += !isNormalized ? slice.toLowerCase() : slice;
+      }
+      t1 = buffer._contents;
+      return t1.charCodeAt(0) == 0 ? t1 : t1;
+    },
+    _Uri__makeScheme: function(scheme, start, end) {
+      var i, containsUpperCase, codeUnit, t1;
+      if (start === end)
+        return "";
+      if (!P._Uri__isAlphabeticCharacter(J.getInterceptor$s(scheme)._codeUnitAt$1(scheme, start)))
+        P._Uri__fail(scheme, start, "Scheme not starting with alphabetic character");
+      for (i = start, containsUpperCase = false; i < end; ++i) {
+        codeUnit = C.JSString_methods._codeUnitAt$1(scheme, i);
+        if (codeUnit < 128) {
+          t1 = codeUnit >>> 4;
+          if (t1 >= 8)
+            return H.ioore(C.List_JYB, t1);
+          t1 = (C.List_JYB[t1] & 1 << (codeUnit & 15)) !== 0;
+        } else
+          t1 = false;
+        if (!t1)
+          P._Uri__fail(scheme, i, "Illegal scheme character");
+        if (65 <= codeUnit && codeUnit <= 90)
+          containsUpperCase = true;
+      }
+      scheme = C.JSString_methods.substring$2(scheme, start, end);
+      return P._Uri__canonicalizeScheme(containsUpperCase ? scheme.toLowerCase() : scheme);
+    },
+    _Uri__canonicalizeScheme: function(scheme) {
+      if (scheme === "http")
+        return "http";
+      if (scheme === "file")
+        return "file";
+      if (scheme === "https")
+        return "https";
+      if (scheme === "package")
+        return "package";
+      return scheme;
+    },
+    _Uri__makeUserInfo: function(userInfo, start, end) {
+      if (userInfo == null)
+        return "";
+      return P._Uri__normalizeOrSubstring(userInfo, start, end, C.List_gRj, false);
+    },
+    _Uri__makePath: function(path, start, end, pathSegments, scheme, hasAuthority) {
+      var result,
+        isFile = scheme === "file",
+        ensureLeadingSlash = isFile || hasAuthority,
+        t1 = path == null;
+      if (t1 && pathSegments == null)
+        return isFile ? "/" : "";
+      t1 = !t1;
+      if (t1 && pathSegments != null)
+        throw H.wrapException(P.ArgumentError$("Both path and pathSegments specified"));
+      if (t1)
+        result = P._Uri__normalizeOrSubstring(path, start, end, C.List_qg4, true);
+      else {
+        pathSegments.toString;
+        t1 = H._arrayInstanceType(pathSegments);
+        result = new H.MappedListIterable(pathSegments, t1._eval$1("String(1)")._check(new P._Uri__makePath_closure()), t1._eval$1("MappedListIterable<1,String>")).join$1(0, "/");
+      }
+      if (result.length === 0) {
+        if (isFile)
+          return "/";
+      } else if (ensureLeadingSlash && !C.JSString_methods.startsWith$1(result, "/"))
+        result = "/" + result;
+      return P._Uri__normalizePath(result, scheme, hasAuthority);
+    },
+    _Uri__normalizePath: function(path, scheme, hasAuthority) {
+      var t1 = scheme.length === 0;
+      if (t1 && !hasAuthority && !C.JSString_methods.startsWith$1(path, "/"))
+        return P._Uri__normalizeRelativePath(path, !t1 || hasAuthority);
+      return P._Uri__removeDotSegments(path);
+    },
+    _Uri__makeQuery: function(query, start, end, queryParameters) {
+      if (query != null)
+        return P._Uri__normalizeOrSubstring(query, start, end, C.List_CVk, true);
+      return null;
+    },
+    _Uri__makeFragment: function(fragment, start, end) {
+      if (fragment == null)
+        return null;
+      return P._Uri__normalizeOrSubstring(fragment, start, end, C.List_CVk, true);
+    },
+    _Uri__normalizeEscape: function(source, index, lowerCase) {
+      var t1, firstDigit, secondDigit, firstDigitValue, secondDigitValue, value;
+      H.assertHelper(C.JSString_methods.codeUnitAt$1(source, index) === 37);
+      t1 = index + 2;
+      if (t1 >= source.length)
+        return "%";
+      firstDigit = C.JSString_methods.codeUnitAt$1(source, index + 1);
+      secondDigit = C.JSString_methods.codeUnitAt$1(source, t1);
+      firstDigitValue = H.hexDigitValue(firstDigit);
+      secondDigitValue = H.hexDigitValue(secondDigit);
+      if (firstDigitValue < 0 || secondDigitValue < 0)
+        return "%";
+      value = firstDigitValue * 16 + secondDigitValue;
+      if (value < 127) {
+        t1 = C.JSInt_methods._shrOtherPositive$1(value, 4);
+        if (t1 >= 8)
+          return H.ioore(C.List_nxB, t1);
+        t1 = (C.List_nxB[t1] & 1 << (value & 15)) !== 0;
+      } else
+        t1 = false;
+      if (t1)
+        return H.Primitives_stringFromCharCode(lowerCase && 65 <= value && 90 >= value ? (value | 32) >>> 0 : value);
+      if (firstDigit >= 97 || secondDigit >= 97)
+        return C.JSString_methods.substring$2(source, index, index + 3).toUpperCase();
+      return null;
+    },
+    _Uri__escapeChar: function(char) {
+      var t1, codeUnits, flag, encodedBytes, index, byte,
+        _s16_ = "0123456789ABCDEF";
+      H.assertHelper(char <= 1114111);
+      if (char < 128) {
+        t1 = new Array(3);
+        t1.fixed$length = Array;
+        codeUnits = H.setRuntimeTypeInfo(t1, type$.JSArray_int);
+        C.JSArray_methods.$indexSet(codeUnits, 0, 37);
+        C.JSArray_methods.$indexSet(codeUnits, 1, C.JSString_methods._codeUnitAt$1(_s16_, char >>> 4));
+        C.JSArray_methods.$indexSet(codeUnits, 2, C.JSString_methods._codeUnitAt$1(_s16_, char & 15));
+      } else {
+        if (char > 2047)
+          if (char > 65535) {
+            flag = 240;
+            encodedBytes = 4;
+          } else {
+            flag = 224;
+            encodedBytes = 3;
+          }
+        else {
+          flag = 192;
+          encodedBytes = 2;
+        }
+        t1 = new Array(3 * encodedBytes);
+        t1.fixed$length = Array;
+        codeUnits = H.setRuntimeTypeInfo(t1, type$.JSArray_int);
+        for (index = 0; --encodedBytes, encodedBytes >= 0; flag = 128) {
+          byte = C.JSInt_methods._shrReceiverPositive$1(char, 6 * encodedBytes) & 63 | flag;
+          C.JSArray_methods.$indexSet(codeUnits, index, 37);
+          C.JSArray_methods.$indexSet(codeUnits, index + 1, C.JSString_methods._codeUnitAt$1(_s16_, byte >>> 4));
+          C.JSArray_methods.$indexSet(codeUnits, index + 2, C.JSString_methods._codeUnitAt$1(_s16_, byte & 15));
+          index += 3;
+        }
+      }
+      return P.String_String$fromCharCodes(codeUnits, 0, null);
+    },
+    _Uri__normalizeOrSubstring: function(component, start, end, charTable, escapeDelimiters) {
+      var t1 = P._Uri__normalize(component, start, end, charTable, escapeDelimiters);
+      return t1 == null ? C.JSString_methods.substring$2(component, start, end) : t1;
+    },
+    _Uri__normalize: function(component, start, end, charTable, escapeDelimiters) {
+      var t1, index, sectionStart, buffer, char, t2, replacement, sourceLength, tail, _null = null;
+      for (t1 = !escapeDelimiters, index = start, sectionStart = index, buffer = _null; index < end;) {
+        char = C.JSString_methods.codeUnitAt$1(component, index);
+        if (char < 127) {
+          t2 = char >>> 4;
+          if (t2 >= 8)
+            return H.ioore(charTable, t2);
+          t2 = (charTable[t2] & 1 << (char & 15)) !== 0;
+        } else
+          t2 = false;
+        if (t2)
+          ++index;
+        else {
+          if (char === 37) {
+            replacement = P._Uri__normalizeEscape(component, index, false);
+            if (replacement == null) {
+              index += 3;
+              continue;
+            }
+            if ("%" === replacement) {
+              replacement = "%25";
+              sourceLength = 1;
+            } else
+              sourceLength = 3;
+          } else {
+            if (t1)
+              if (char <= 93) {
+                t2 = char >>> 4;
+                if (t2 >= 8)
+                  return H.ioore(C.List_2Vk, t2);
+                t2 = (C.List_2Vk[t2] & 1 << (char & 15)) !== 0;
+              } else
+                t2 = false;
+            else
+              t2 = false;
+            if (t2) {
+              P._Uri__fail(component, index, "Invalid character");
+              sourceLength = _null;
+              replacement = sourceLength;
+            } else {
+              if ((char & 64512) === 55296) {
+                t2 = index + 1;
+                if (t2 < end) {
+                  tail = C.JSString_methods.codeUnitAt$1(component, t2);
+                  if ((tail & 64512) === 56320) {
+                    char = 65536 | (char & 1023) << 10 | tail & 1023;
+                    sourceLength = 2;
+                  } else
+                    sourceLength = 1;
+                } else
+                  sourceLength = 1;
+              } else
+                sourceLength = 1;
+              replacement = P._Uri__escapeChar(char);
+            }
+          }
+          if (buffer == null)
+            buffer = new P.StringBuffer("");
+          buffer._contents += C.JSString_methods.substring$2(component, sectionStart, index);
+          buffer._contents += H.S(replacement);
+          if (typeof sourceLength !== "number")
+            return H.iae(sourceLength);
+          index += sourceLength;
+          sectionStart = index;
+        }
+      }
+      if (buffer == null)
+        return _null;
+      if (sectionStart < end)
+        buffer._contents += C.JSString_methods.substring$2(component, sectionStart, end);
+      t1 = buffer._contents;
+      return t1.charCodeAt(0) == 0 ? t1 : t1;
+    },
+    _Uri__mayContainDotSegments: function(path) {
+      if (C.JSString_methods.startsWith$1(path, "."))
+        return true;
+      return C.JSString_methods.indexOf$1(path, "/.") !== -1;
+    },
+    _Uri__removeDotSegments: function(path) {
+      var output, t1, t2, appendSlash, _i, segment, t3;
+      if (!P._Uri__mayContainDotSegments(path))
+        return path;
+      H.assertHelper(path.length !== 0);
+      output = H.setRuntimeTypeInfo([], type$.JSArray_String);
+      for (t1 = path.split("/"), t2 = t1.length, appendSlash = false, _i = 0; _i < t2; ++_i) {
+        segment = t1[_i];
+        if (J.$eq$(segment, "..")) {
+          t3 = output.length;
+          if (t3 !== 0) {
+            if (0 >= t3)
+              return H.ioore(output, -1);
+            output.pop();
+            if (output.length === 0)
+              C.JSArray_methods.add$1(output, "");
+          }
+          appendSlash = true;
+        } else if ("." === segment)
+          appendSlash = true;
+        else {
+          C.JSArray_methods.add$1(output, segment);
+          appendSlash = false;
+        }
+      }
+      if (appendSlash)
+        C.JSArray_methods.add$1(output, "");
+      return C.JSArray_methods.join$1(output, "/");
+    },
+    _Uri__normalizeRelativePath: function(path, allowScheme) {
+      var output, t1, t2, appendSlash, _i, segment;
+      H.assertHelper(!C.JSString_methods.startsWith$1(path, "/"));
+      if (!P._Uri__mayContainDotSegments(path))
+        return !allowScheme ? P._Uri__escapeScheme(path) : path;
+      H.assertHelper(path.length !== 0);
+      output = H.setRuntimeTypeInfo([], type$.JSArray_String);
+      for (t1 = path.split("/"), t2 = t1.length, appendSlash = false, _i = 0; _i < t2; ++_i) {
+        segment = t1[_i];
+        if (".." === segment)
+          if (output.length !== 0 && C.JSArray_methods.get$last(output) !== "..") {
+            if (0 >= output.length)
+              return H.ioore(output, -1);
+            output.pop();
+            appendSlash = true;
+          } else {
+            C.JSArray_methods.add$1(output, "..");
+            appendSlash = false;
+          }
+        else if ("." === segment)
+          appendSlash = true;
+        else {
+          C.JSArray_methods.add$1(output, segment);
+          appendSlash = false;
+        }
+      }
+      t1 = output.length;
+      if (t1 !== 0)
+        if (t1 === 1) {
+          if (0 >= t1)
+            return H.ioore(output, 0);
+          t1 = output[0].length === 0;
+        } else
+          t1 = false;
+      else
+        t1 = true;
+      if (t1)
+        return "./";
+      if (appendSlash || C.JSArray_methods.get$last(output) === "..")
+        C.JSArray_methods.add$1(output, "");
+      if (!allowScheme) {
+        if (0 >= output.length)
+          return H.ioore(output, 0);
+        C.JSArray_methods.$indexSet(output, 0, P._Uri__escapeScheme(output[0]));
+      }
+      return C.JSArray_methods.join$1(output, "/");
+    },
+    _Uri__escapeScheme: function(path) {
+      var i, char, t2,
+        t1 = path.length;
+      if (t1 >= 2 && P._Uri__isAlphabeticCharacter(J._codeUnitAt$1$s(path, 0)))
+        for (i = 1; i < t1; ++i) {
+          char = C.JSString_methods._codeUnitAt$1(path, i);
+          if (char === 58)
+            return C.JSString_methods.substring$2(path, 0, i) + "%3A" + C.JSString_methods.substring$1(path, i + 1);
+          if (char <= 127) {
+            t2 = char >>> 4;
+            if (t2 >= 8)
+              return H.ioore(C.List_JYB, t2);
+            t2 = (C.List_JYB[t2] & 1 << (char & 15)) === 0;
+          } else
+            t2 = true;
+          if (t2)
+            break;
+        }
+      return path;
+    },
+    _Uri__toWindowsFilePath: function(uri) {
+      var hasDriveLetter, t2, host,
+        segments = uri.get$pathSegments(),
+        t1 = segments.length;
+      if (t1 > 0 && J.get$length$asx(segments[0]) === 2 && J.codeUnitAt$1$s(segments[0], 1) === 58) {
+        if (0 >= t1)
+          return H.ioore(segments, 0);
+        P._Uri__checkWindowsDriveLetter(J.codeUnitAt$1$s(segments[0], 0), false);
+        P._Uri__checkWindowsPathReservedCharacters(segments, false, 1);
+        hasDriveLetter = true;
+      } else {
+        P._Uri__checkWindowsPathReservedCharacters(segments, false, 0);
+        hasDriveLetter = false;
+      }
+      t2 = uri.get$hasAbsolutePath() && !hasDriveLetter ? "\\" : "";
+      if (uri.get$hasAuthority()) {
+        host = uri.get$host(uri);
+        if (host.length !== 0)
+          t2 = t2 + "\\" + host + "\\";
+      }
+      t2 = P.StringBuffer__writeAll(t2, segments, "\\");
+      t1 = hasDriveLetter && t1 === 1 ? t2 + "\\" : t2;
+      return t1.charCodeAt(0) == 0 ? t1 : t1;
+    },
+    _Uri__hexCharPairToByte: function(s, pos) {
+      var byte, i, charCode;
+      for (byte = 0, i = 0; i < 2; ++i) {
+        charCode = C.JSString_methods._codeUnitAt$1(s, pos + i);
+        if (48 <= charCode && charCode <= 57)
+          byte = byte * 16 + charCode - 48;
+        else {
+          charCode |= 32;
+          if (97 <= charCode && charCode <= 102)
+            byte = byte * 16 + charCode - 87;
+          else
+            throw H.wrapException(P.ArgumentError$("Invalid URL encoding"));
+        }
+      }
+      return byte;
+    },
+    _Uri__uriDecode: function(text, start, end, encoding, plusToSpace) {
+      var t1, simple, t2, i, codeUnit, t3, bytes;
+      H.assertHelper(start <= end);
+      t1 = text.length;
+      H.assertHelper(end <= t1);
+      t2 = J.getInterceptor$s(text);
+      i = start;
+      while (true) {
+        if (!(i < end)) {
+          simple = true;
+          break;
+        }
+        codeUnit = t2._codeUnitAt$1(text, i);
+        if (codeUnit <= 127)
+          if (codeUnit !== 37)
+            t3 = false;
+          else
+            t3 = true;
+        else
+          t3 = true;
+        if (t3) {
+          simple = false;
+          break;
+        }
+        ++i;
+      }
+      if (simple) {
+        if (C.C_Utf8Codec !== encoding)
+          t1 = false;
+        else
+          t1 = true;
+        if (t1)
+          return t2.substring$2(text, start, end);
+        else
+          bytes = new H.CodeUnits(t2.substring$2(text, start, end));
+      } else {
+        bytes = H.setRuntimeTypeInfo([], type$.JSArray_int);
+        for (i = start; i < end; ++i) {
+          codeUnit = t2._codeUnitAt$1(text, i);
+          if (codeUnit > 127)
+            throw H.wrapException(P.ArgumentError$("Illegal percent encoding in URI"));
+          if (codeUnit === 37) {
+            if (i + 3 > t1)
+              throw H.wrapException(P.ArgumentError$("Truncated URI"));
+            C.JSArray_methods.add$1(bytes, P._Uri__hexCharPairToByte(text, i + 1));
+            i += 2;
+          } else
+            C.JSArray_methods.add$1(bytes, codeUnit);
+        }
+      }
+      type$.List_int._check(bytes);
+      return new P.Utf8Decoder(false).convert$1(bytes);
+    },
+    _Uri__isAlphabeticCharacter: function(codeUnit) {
+      var lowerCase = codeUnit | 32;
+      return 97 <= lowerCase && lowerCase <= 122;
+    },
+    UriData__writeUri: function(mimeType, charsetName, parameters, buffer, indices) {
+      var slashIndex, t1;
+      if (true)
+        buffer._contents = buffer._contents;
+      else {
+        slashIndex = P.UriData__validateMimeType("");
+        if (slashIndex < 0)
+          throw H.wrapException(P.ArgumentError$value("", "mimeType", "Invalid MIME type"));
+        t1 = buffer._contents += H.S(P._Uri__uriEncode(C.List_qFt, C.JSString_methods.substring$2("", 0, slashIndex), C.C_Utf8Codec, false));
+        buffer._contents = t1 + "/";
+        buffer._contents += H.S(P._Uri__uriEncode(C.List_qFt, C.JSString_methods.substring$1("", slashIndex + 1), C.C_Utf8Codec, false));
+      }
+    },
+    UriData__validateMimeType: function(mimeType) {
+      var t1, slashIndex, i;
+      for (t1 = mimeType.length, slashIndex = -1, i = 0; i < t1; ++i) {
+        if (C.JSString_methods._codeUnitAt$1(mimeType, i) !== 47)
+          continue;
+        if (slashIndex < 0) {
+          slashIndex = i;
+          continue;
+        }
+        return -1;
+      }
+      return slashIndex;
+    },
+    UriData__parse: function(text, start, sourceUri) {
+      var indices, t1, i, slashIndex, char, equalsIndex, lastSeparator, t2, data,
+        _s17_ = "Invalid MIME type";
+      H.assertHelper(start === 0 || start === 5);
+      H.assertHelper(start === 5 === C.JSString_methods.startsWith$1(text, "data:"));
+      indices = H.setRuntimeTypeInfo([start - 1], type$.JSArray_int);
+      for (t1 = text.length, i = start, slashIndex = -1, char = null; i < t1; ++i) {
+        char = C.JSString_methods._codeUnitAt$1(text, i);
+        if (char === 44 || char === 59)
+          break;
+        if (char === 47) {
+          if (slashIndex < 0) {
+            slashIndex = i;
+            continue;
+          }
+          throw H.wrapException(P.FormatException$(_s17_, text, i));
+        }
+      }
+      if (slashIndex < 0 && i > start)
+        throw H.wrapException(P.FormatException$(_s17_, text, i));
+      for (; char !== 44;) {
+        C.JSArray_methods.add$1(indices, i);
+        ++i;
+        for (equalsIndex = -1; i < t1; ++i) {
+          char = C.JSString_methods._codeUnitAt$1(text, i);
+          if (char === 61) {
+            if (equalsIndex < 0)
+              equalsIndex = i;
+          } else if (char === 59 || char === 44)
+            break;
+        }
+        if (equalsIndex >= 0)
+          C.JSArray_methods.add$1(indices, equalsIndex);
+        else {
+          lastSeparator = C.JSArray_methods.get$last(indices);
+          if (char !== 44 || i !== lastSeparator + 7 || !C.JSString_methods.startsWith$2(text, "base64", lastSeparator + 1))
+            throw H.wrapException(P.FormatException$("Expecting '='", text, i));
+          break;
+        }
+      }
+      C.JSArray_methods.add$1(indices, i);
+      t2 = i + 1;
+      if ((indices.length & 1) === 1)
+        text = C.C_Base64Codec.normalize$3(text, t2, t1);
+      else {
+        data = P._Uri__normalize(text, t2, t1, C.List_CVk, true);
+        if (data != null)
+          text = C.JSString_methods.replaceRange$3(text, t2, t1, data);
+      }
+      return new P.UriData(text, indices, sourceUri);
+    },
+    UriData__uriEncodeBytes: function(canonicalTable, bytes, buffer) {
+      var t1, byteOr, i, byte, t2, t3,
+        _s16_ = "0123456789ABCDEF";
+      for (t1 = J.getInterceptor$asx(bytes), byteOr = 0, i = 0; i < t1.get$length(bytes); ++i) {
+        byte = t1.$index(bytes, i);
+        if (typeof byte !== "number")
+          return H.iae(byte);
+        byteOr |= byte;
+        if (byte < 128) {
+          t2 = C.JSInt_methods._shrOtherPositive$1(byte, 4);
+          if (t2 >= 8)
+            return H.ioore(canonicalTable, t2);
+          t2 = (canonicalTable[t2] & 1 << (byte & 15)) !== 0;
+        } else
+          t2 = false;
+        t3 = buffer._contents;
+        if (t2)
+          buffer._contents = t3 + H.Primitives_stringFromCharCode(byte);
+        else {
+          t2 = t3 + H.Primitives_stringFromCharCode(37);
+          buffer._contents = t2;
+          t2 += H.Primitives_stringFromCharCode(C.JSString_methods._codeUnitAt$1(_s16_, C.JSInt_methods._shrOtherPositive$1(byte, 4)));
+          buffer._contents = t2;
+          buffer._contents = t2 + H.Primitives_stringFromCharCode(C.JSString_methods._codeUnitAt$1(_s16_, byte & 15));
+        }
+      }
+      if ((byteOr & 4294967040) >>> 0 !== 0)
+        for (i = 0; i < t1.get$length(bytes); ++i) {
+          byte = t1.$index(bytes, i);
+          if (typeof byte !== "number")
+            return byte.$lt();
+          if (byte < 0 || byte > 255)
+            throw H.wrapException(P.ArgumentError$value(byte, "non-byte value", null));
+        }
+    },
+    _createTables: function() {
+      var _s77_ = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz-._~!$&'()*+,;=",
+        _s1_ = ".", _s1_0 = ":", _s1_1 = "/", _s1_2 = "?", _s1_3 = "#",
+        t1 = type$.Uint8List,
+        tables = P.List_List$generate(22, new P._createTables_closure(), true, t1),
+        t2 = new P._createTables_build(tables),
+        t3 = new P._createTables_setChars(),
+        t4 = new P._createTables_setRange(),
+        t5 = t1._check(t2.call$2(0, 225));
+      t3.call$3(t5, _s77_, 1);
+      t3.call$3(t5, _s1_, 14);
+      t3.call$3(t5, _s1_0, 34);
+      t3.call$3(t5, _s1_1, 3);
+      t3.call$3(t5, _s1_2, 172);
+      t3.call$3(t5, _s1_3, 205);
+      t5 = t1._check(t2.call$2(14, 225));
+      t3.call$3(t5, _s77_, 1);
+      t3.call$3(t5, _s1_, 15);
+      t3.call$3(t5, _s1_0, 34);
+      t3.call$3(t5, _s1_1, 234);
+      t3.call$3(t5, _s1_2, 172);
+      t3.call$3(t5, _s1_3, 205);
+      t5 = t1._check(t2.call$2(15, 225));
+      t3.call$3(t5, _s77_, 1);
+      t3.call$3(t5, "%", 225);
+      t3.call$3(t5, _s1_0, 34);
+      t3.call$3(t5, _s1_1, 9);
+      t3.call$3(t5, _s1_2, 172);
+      t3.call$3(t5, _s1_3, 205);
+      t5 = t1._check(t2.call$2(1, 225));
+      t3.call$3(t5, _s77_, 1);
+      t3.call$3(t5, _s1_0, 34);
+      t3.call$3(t5, _s1_1, 10);
+      t3.call$3(t5, _s1_2, 172);
+      t3.call$3(t5, _s1_3, 205);
+      t5 = t1._check(t2.call$2(2, 235));
+      t3.call$3(t5, _s77_, 139);
+      t3.call$3(t5, _s1_1, 131);
+      t3.call$3(t5, _s1_, 146);
+      t3.call$3(t5, _s1_2, 172);
+      t3.call$3(t5, _s1_3, 205);
+      t5 = t1._check(t2.call$2(3, 235));
+      t3.call$3(t5, _s77_, 11);
+      t3.call$3(t5, _s1_1, 68);
+      t3.call$3(t5, _s1_, 18);
+      t3.call$3(t5, _s1_2, 172);
+      t3.call$3(t5, _s1_3, 205);
+      t5 = t1._check(t2.call$2(4, 229));
+      t3.call$3(t5, _s77_, 5);
+      t4.call$3(t5, "AZ", 229);
+      t3.call$3(t5, _s1_0, 102);
+      t3.call$3(t5, "@", 68);
+      t3.call$3(t5, "[", 232);
+      t3.call$3(t5, _s1_1, 138);
+      t3.call$3(t5, _s1_2, 172);
+      t3.call$3(t5, _s1_3, 205);
+      t5 = t1._check(t2.call$2(5, 229));
+      t3.call$3(t5, _s77_, 5);
+      t4.call$3(t5, "AZ", 229);
+      t3.call$3(t5, _s1_0, 102);
+      t3.call$3(t5, "@", 68);
+      t3.call$3(t5, _s1_1, 138);
+      t3.call$3(t5, _s1_2, 172);
+      t3.call$3(t5, _s1_3, 205);
+      t5 = t1._check(t2.call$2(6, 231));
+      t4.call$3(t5, "19", 7);
+      t3.call$3(t5, "@", 68);
+      t3.call$3(t5, _s1_1, 138);
+      t3.call$3(t5, _s1_2, 172);
+      t3.call$3(t5, _s1_3, 205);
+      t5 = t1._check(t2.call$2(7, 231));
+      t4.call$3(t5, "09", 7);
+      t3.call$3(t5, "@", 68);
+      t3.call$3(t5, _s1_1, 138);
+      t3.call$3(t5, _s1_2, 172);
+      t3.call$3(t5, _s1_3, 205);
+      t3.call$3(t1._check(t2.call$2(8, 8)), "]", 5);
+      t5 = t1._check(t2.call$2(9, 235));
+      t3.call$3(t5, _s77_, 11);
+      t3.call$3(t5, _s1_, 16);
+      t3.call$3(t5, _s1_1, 234);
+      t3.call$3(t5, _s1_2, 172);
+      t3.call$3(t5, _s1_3, 205);
+      t5 = t1._check(t2.call$2(16, 235));
+      t3.call$3(t5, _s77_, 11);
+      t3.call$3(t5, _s1_, 17);
+      t3.call$3(t5, _s1_1, 234);
+      t3.call$3(t5, _s1_2, 172);
+      t3.call$3(t5, _s1_3, 205);
+      t5 = t1._check(t2.call$2(17, 235));
+      t3.call$3(t5, _s77_, 11);
+      t3.call$3(t5, _s1_1, 9);
+      t3.call$3(t5, _s1_2, 172);
+      t3.call$3(t5, _s1_3, 205);
+      t5 = t1._check(t2.call$2(10, 235));
+      t3.call$3(t5, _s77_, 11);
+      t3.call$3(t5, _s1_, 18);
+      t3.call$3(t5, _s1_1, 234);
+      t3.call$3(t5, _s1_2, 172);
+      t3.call$3(t5, _s1_3, 205);
+      t5 = t1._check(t2.call$2(18, 235));
+      t3.call$3(t5, _s77_, 11);
+      t3.call$3(t5, _s1_, 19);
+      t3.call$3(t5, _s1_1, 234);
+      t3.call$3(t5, _s1_2, 172);
+      t3.call$3(t5, _s1_3, 205);
+      t5 = t1._check(t2.call$2(19, 235));
+      t3.call$3(t5, _s77_, 11);
+      t3.call$3(t5, _s1_1, 234);
+      t3.call$3(t5, _s1_2, 172);
+      t3.call$3(t5, _s1_3, 205);
+      t5 = t1._check(t2.call$2(11, 235));
+      t3.call$3(t5, _s77_, 11);
+      t3.call$3(t5, _s1_1, 10);
+      t3.call$3(t5, _s1_2, 172);
+      t3.call$3(t5, _s1_3, 205);
+      t5 = t1._check(t2.call$2(12, 236));
+      t3.call$3(t5, _s77_, 12);
+      t3.call$3(t5, _s1_2, 12);
+      t3.call$3(t5, _s1_3, 205);
+      t5 = t1._check(t2.call$2(13, 237));
+      t3.call$3(t5, _s77_, 13);
+      t3.call$3(t5, _s1_2, 13);
+      t4.call$3(t1._check(t2.call$2(20, 245)), "az", 21);
+      t2 = t1._check(t2.call$2(21, 245));
+      t4.call$3(t2, "az", 21);
+      t4.call$3(t2, "09", 21);
+      t3.call$3(t2, "+-.", 21);
+      return tables;
+    },
+    _scan: function(uri, start, end, state, indices) {
+      var t1, i, table, char, transition,
+        tables = $.$get$_scannerTables();
+      H.assertHelper(end <= uri.length);
+      for (t1 = J.getInterceptor$s(uri), i = start; i < end; ++i) {
+        if (state < 0 || state >= tables.length)
+          return H.ioore(tables, state);
+        table = tables[state];
+        char = t1._codeUnitAt$1(uri, i) ^ 96;
+        if (char > 95)
+          char = 31;
+        if (char >= table.length)
+          return H.ioore(table, char);
+        transition = table[char];
+        state = transition & 31;
+        C.JSArray_methods.$indexSet(indices, transition >>> 5, i);
+      }
+      return state;
+    },
+    bool: function bool() {
+    },
+    DateTime: function DateTime(t0, t1) {
+      this._value = t0;
+      this.isUtc = t1;
+    },
+    double: function double() {
+    },
+    Duration: function Duration(t0) {
+      this._duration = t0;
+    },
+    Duration_toString_sixDigits: function Duration_toString_sixDigits() {
+    },
+    Duration_toString_twoDigits: function Duration_toString_twoDigits() {
+    },
+    Error: function Error() {
+    },
+    AssertionError: function AssertionError(t0) {
+      this.message = t0;
+    },
+    NullThrownError: function NullThrownError() {
+    },
+    ArgumentError: function ArgumentError(t0, t1, t2, t3) {
+      var _ = this;
+      _._hasValue = t0;
+      _.invalidValue = t1;
+      _.name = t2;
+      _.message = t3;
+    },
+    RangeError: function RangeError(t0, t1, t2, t3, t4, t5) {
+      var _ = this;
+      _.start = t0;
+      _.end = t1;
+      _._hasValue = t2;
+      _.invalidValue = t3;
+      _.name = t4;
+      _.message = t5;
+    },
+    IndexError: function IndexError(t0, t1, t2, t3, t4) {
+      var _ = this;
+      _.length = t0;
+      _._hasValue = t1;
+      _.invalidValue = t2;
+      _.name = t3;
+      _.message = t4;
+    },
+    UnsupportedError: function UnsupportedError(t0) {
+      this.message = t0;
+    },
+    UnimplementedError: function UnimplementedError(t0) {
+      this.message = t0;
+    },
+    StateError: function StateError(t0) {
+      this.message = t0;
+    },
+    ConcurrentModificationError: function ConcurrentModificationError(t0) {
+      this.modifiedObject = t0;
+    },
+    OutOfMemoryError: function OutOfMemoryError() {
+    },
+    StackOverflowError: function StackOverflowError() {
+    },
+    CyclicInitializationError: function CyclicInitializationError(t0) {
+      this.variableName = t0;
+    },
+    _Exception: function _Exception(t0) {
+      this.message = t0;
+    },
+    FormatException: function FormatException(t0, t1, t2) {
+      this.message = t0;
+      this.source = t1;
+      this.offset = t2;
+    },
+    Expando: function Expando(t0, t1, t2) {
+      this._jsWeakMapOrKey = t0;
+      this.name = t1;
+      this.$ti = t2;
+    },
+    Function: function Function() {
+    },
+    int: function int() {
+    },
+    Iterable: function Iterable() {
+    },
+    Iterator: function Iterator() {
+    },
+    List: function List() {
+    },
+    Map: function Map() {
+    },
+    MapEntry: function MapEntry(t0, t1, t2) {
+      this.key = t0;
+      this.value = t1;
+      this.$ti = t2;
+    },
+    Null: function Null() {
+    },
+    num: function num() {
+    },
+    Object: function Object() {
+    },
+    Pattern: function Pattern() {
+    },
+    Match: function Match() {
+    },
+    RegExpMatch: function RegExpMatch() {
+    },
+    Set: function Set() {
+    },
+    StackTrace: function StackTrace() {
+    },
+    _StringStackTrace: function _StringStackTrace(t0) {
+      this._stackTrace = t0;
+    },
+    Stopwatch: function Stopwatch() {
+      this._stop = this._core$_start = 0;
+    },
+    String: function String() {
+    },
+    Runes: function Runes(t0) {
+      this.string = t0;
+    },
+    RuneIterator: function RuneIterator(t0) {
+      var _ = this;
+      _.string = t0;
+      _._nextPosition = _._core$_position = 0;
+      _._currentCodePoint = null;
+    },
+    StringBuffer: function StringBuffer(t0) {
+      this._contents = t0;
+    },
+    Uri: function Uri() {
+    },
+    Uri__parseIPv4Address_error: function Uri__parseIPv4Address_error(t0) {
+      this.host = t0;
+    },
+    Uri_parseIPv6Address_error: function Uri_parseIPv6Address_error(t0) {
+      this.host = t0;
+    },
+    Uri_parseIPv6Address_parseHex: function Uri_parseIPv6Address_parseHex(t0, t1) {
+      this.error = t0;
+      this.host = t1;
+    },
+    _Uri: function _Uri(t0, t1, t2, t3, t4, t5, t6) {
+      var _ = this;
+      _.scheme = t0;
+      _._userInfo = t1;
+      _._host = t2;
+      _._port = t3;
+      _.path = t4;
+      _._query = t5;
+      _._fragment = t6;
+      _._hashCodeCache = _._text = _._pathSegments = null;
+    },
+    _Uri__Uri$notSimple_closure: function _Uri__Uri$notSimple_closure(t0, t1) {
+      this.uri = t0;
+      this.portStart = t1;
+    },
+    _Uri__checkNonWindowsPathReservedCharacters_closure: function _Uri__checkNonWindowsPathReservedCharacters_closure(t0) {
+      this.argumentError = t0;
+    },
+    _Uri__makePath_closure: function _Uri__makePath_closure() {
+    },
+    UriData: function UriData(t0, t1, t2) {
+      this._text = t0;
+      this._separatorIndices = t1;
+      this._uriCache = t2;
+    },
+    _createTables_closure: function _createTables_closure() {
+    },
+    _createTables_build: function _createTables_build(t0) {
+      this.tables = t0;
+    },
+    _createTables_setChars: function _createTables_setChars() {
+    },
+    _createTables_setRange: function _createTables_setRange() {
+    },
+    _SimpleUri: function _SimpleUri(t0, t1, t2, t3, t4, t5, t6, t7) {
+      var _ = this;
+      _._uri = t0;
+      _._schemeEnd = t1;
+      _._hostStart = t2;
+      _._portStart = t3;
+      _._pathStart = t4;
+      _._queryStart = t5;
+      _._fragmentStart = t6;
+      _._schemeCache = t7;
+      _._hashCodeCache = null;
+    },
+    _DataUri: function _DataUri(t0, t1, t2, t3, t4, t5, t6) {
+      var _ = this;
+      _.scheme = t0;
+      _._userInfo = t1;
+      _._host = t2;
+      _._port = t3;
+      _.path = t4;
+      _._query = t5;
+      _._fragment = t6;
+      _._hashCodeCache = _._text = _._pathSegments = null;
+    },
+    _StructuredClone: function _StructuredClone() {
+    },
+    _StructuredClone_walk_closure: function _StructuredClone_walk_closure(t0, t1) {
+      this._box_0 = t0;
+      this.$this = t1;
+    },
+    _StructuredClone_walk_closure0: function _StructuredClone_walk_closure0(t0, t1) {
+      this._box_0 = t0;
+      this.$this = t1;
+    },
+    _AcceptStructuredClone: function _AcceptStructuredClone() {
+    },
+    _AcceptStructuredClone_walk_closure: function _AcceptStructuredClone_walk_closure(t0, t1) {
+      this._box_0 = t0;
+      this.$this = t1;
+    },
+    _StructuredCloneDart2Js: function _StructuredCloneDart2Js(t0, t1) {
+      this.values = t0;
+      this.copies = t1;
+    },
+    _AcceptStructuredCloneDart2Js: function _AcceptStructuredCloneDart2Js(t0, t1) {
+      this.values = t0;
+      this.copies = t1;
+      this.mustCopy = false;
+    },
+    _convertDataTree: function(data) {
+      return new P._convertDataTree__convert(new P._IdentityHashMap(type$._IdentityHashMap_dynamic_dynamic)).call$1(data);
+    },
+    promiseToFuture: function(jsPromise, $T) {
+      var t1 = new P._Future($.Zone__current, $T._eval$1("_Future<0>")),
+        completer = new P._AsyncCompleter(t1, $T._eval$1("_AsyncCompleter<0>"));
+      jsPromise.then(H.convertDartClosureToJS(new P.promiseToFuture_closure(completer, $T), 1), H.convertDartClosureToJS(new P.promiseToFuture_closure0(completer), 1));
+      return t1;
+    },
+    _convertDataTree__convert: function _convertDataTree__convert(t0) {
+      this._convertedObjects = t0;
+    },
+    promiseToFuture_closure: function promiseToFuture_closure(t0, t1) {
+      this.completer = t0;
+      this.T = t1;
+    },
+    promiseToFuture_closure0: function promiseToFuture_closure0(t0) {
+      this.completer = t0;
+    },
+    ByteBuffer: function ByteBuffer() {
+    },
+    ByteData: function ByteData() {
+    },
+    Int8List: function Int8List() {
+    },
+    Uint8List: function Uint8List() {
+    },
+    Uint8ClampedList: function Uint8ClampedList() {
+    },
+    Int16List: function Int16List() {
+    },
+    Uint16List: function Uint16List() {
+    },
+    Int32List: function Int32List() {
+    },
+    Uint32List: function Uint32List() {
+    },
+    Float32List: function Float32List() {
+    },
+    Float64List: function Float64List() {
+    },
+    SqlError: function SqlError() {
+    },
+    max: function(a, b, $T) {
+      H.checkTypeBound($T, type$.num, "T", "max");
+      $T._check(a);
+      $T._check(b);
+      return Math.max(H.checkNum(a), H.checkNum(b));
+    },
+    pow: function(x, exponent) {
+      return Math.pow(x, exponent);
+    }
+  },
+  W = {
+    _EventStreamSubscription$: function(_target, _eventType, onData, _useCapture, $T) {
+      var t1 = onData == null ? null : W._wrapZone(new W._EventStreamSubscription_closure(onData), type$.Event);
+      t1 = new W._EventStreamSubscription(_target, _eventType, t1, false, $T._eval$1("_EventStreamSubscription<0>"));
+      t1._tryResume$0();
+      return t1;
+    },
+    _wrapZone: function(callback, $T) {
+      var t1 = $.Zone__current;
+      if (t1 === C.C__RootZone)
+        return callback;
+      return t1.bindUnaryCallbackGuarded$1$1(callback, $T);
+    },
+    ApplicationCacheErrorEvent: function ApplicationCacheErrorEvent() {
+    },
+    Blob: function Blob() {
+    },
+    DomError: function DomError() {
+    },
+    DomException: function DomException() {
+    },
+    ErrorEvent: function ErrorEvent() {
+    },
+    Event: function Event() {
+    },
+    EventTarget: function EventTarget() {
+    },
+    File: function File() {
+    },
+    Location: function Location() {
+    },
+    MediaError: function MediaError() {
+    },
+    MediaKeyMessageEvent: function MediaKeyMessageEvent() {
+    },
+    MessageEvent: function MessageEvent() {
+    },
+    MessagePort: function MessagePort() {
+    },
+    NavigatorUserMediaError: function NavigatorUserMediaError() {
+    },
+    OverconstrainedError: function OverconstrainedError() {
+    },
+    PositionError: function PositionError() {
+    },
+    PresentationConnectionCloseEvent: function PresentationConnectionCloseEvent() {
+    },
+    SpeechRecognitionError: function SpeechRecognitionError() {
+    },
+    EventStreamProvider: function EventStreamProvider(t0) {
+      this.$ti = t0;
+    },
+    _EventStream: function _EventStream(t0, t1, t2, t3) {
+      var _ = this;
+      _._html$_target = t0;
+      _._eventType = t1;
+      _._useCapture = t2;
+      _.$ti = t3;
+    },
+    _EventStreamSubscription: function _EventStreamSubscription(t0, t1, t2, t3, t4) {
+      var _ = this;
+      _._pauseCount = 0;
+      _._html$_target = t0;
+      _._eventType = t1;
+      _._html$_onData = t2;
+      _._useCapture = t3;
+      _.$ti = t4;
+    },
+    _EventStreamSubscription_closure: function _EventStreamSubscription_closure(t0) {
+      this.onData = t0;
+    }
+  },
+  S = {AsyncMemoizer: function AsyncMemoizer(t0, t1) {
+      this._async_memoizer$_completer = t0;
+      this.$ti = t1;
+    }, NullStreamSink: function NullStreamSink(t0, t1) {
+      var _ = this;
+      _.done = t0;
+      _._addingStream = _._null_stream_sink$_closed = false;
+      _.$ti = t1;
+    }, NullStreamSink_addStream_closure: function NullStreamSink_addStream_closure(t0) {
+      this.$this = t0;
+    }, Validator: function Validator(t0) {
+      this._isDefined = t0;
+    },
+    SpanScanner$: function(string) {
+      var t1, t2;
+      string.toString;
+      t1 = new H.CodeUnits(string);
+      t2 = H.setRuntimeTypeInfo([0], type$.JSArray_int);
+      t2 = new Y.SourceFile(null, t2, new Uint32Array(H._ensureNativeList(t1.toList$0(t1))));
+      t2.SourceFile$decoded$2$url(t1, null);
+      return new S.SpanScanner(t2, null, string);
+    },
+    SpanScanner: function SpanScanner(t0, t1, t2) {
+      var _ = this;
+      _._sourceFile = t0;
+      _._lastSpan = null;
+      _.sourceUrl = t1;
+      _.string = t2;
+      _._string_scanner$_position = 0;
+      _._lastMatchPosition = _._lastMatch = null;
+    },
+    _SpanScannerState: function _SpanScannerState(t0, t1) {
+      this._span_scanner$_scanner = t0;
+      this.position = t1;
+    },
+    RemoteListener_start: function(getMain, beforeLoad, hidePrints) {
+      var printZone, spec, t3, _null = null, t1 = {},
+        controller = B.StreamChannelController$(false, true, type$.Object),
+        t2 = type$.dynamic,
+        channel = D._MultiChannel$(controller._local, t2);
+      t1.verboseChain = true;
+      printZone = $.Zone__current;
+      spec = P._ZoneSpecification$(_null, _null, _null, _null, _null, new S.RemoteListener_start_closure(printZone, channel), _null, _null, _null, _null, _null, _null, _null);
+      P.Stream_Stream$fromIterable([], t2).listen$1(new S.RemoteListener_start_closure0()).cancel$0();
+      t3 = type$.String;
+      P.runZoned(type$.Null_Function._check(new S.RemoteListener_start_closure1(t1, getMain, channel, controller, beforeLoad, printZone, spec)), _null, _null, P.LinkedHashMap_LinkedHashMap$_literal([$.$get$_currentKey(), new N.SuiteChannelManager(P.LinkedHashMap_LinkedHashMap$_empty(t3, type$.StreamChannel_dynamic), P.LinkedHashMap_LinkedHashMap$_empty(t3, type$.StreamChannelCompleter_dynamic), P.LinkedHashSet_LinkedHashSet$_empty(t3))], t2, t2), type$.Null);
+      return controller._foreign;
+    },
+    RemoteListener__deserializeSet: function(list) {
+      if (list == null)
+        return null;
+      if (J.get$isEmpty$asx(list))
+        return null;
+      return P.LinkedHashSet_LinkedHashSet$from(list, type$.String);
+    },
+    RemoteListener__sendLoadException: function(channel, message) {
+      var t1 = type$.String;
+      channel._mainController._foreign._sink.add$1(0, P.LinkedHashMap_LinkedHashMap$_literal(["type", "loadException", "message", message], t1, t1));
+    },
+    RemoteListener__sendError: function(channel, error, stackTrace, verboseChain) {
+      channel._mainController._foreign._sink.add$1(0, P.LinkedHashMap_LinkedHashMap$_literal(["type", "error", "error", U.RemoteException_serialize(error, type$.StackTraceFormatter._as($.Zone__current.$index(0, $.$get$_currentKey0())).formatStackTrace$2$verbose(stackTrace, verboseChain))], type$.String, type$.Object));
+    },
+    RemoteListener: function RemoteListener(t0, t1) {
+      this._suite = t0;
+      this._printZone = t1;
+    },
+    RemoteListener_start_closure: function RemoteListener_start_closure(t0, t1) {
+      this.printZone = t0;
+      this.channel = t1;
+    },
+    RemoteListener_start_closure0: function RemoteListener_start_closure0() {
+    },
+    RemoteListener_start_closure1: function RemoteListener_start_closure1(t0, t1, t2, t3, t4, t5, t6) {
+      var _ = this;
+      _._box_0 = t0;
+      _.getMain = t1;
+      _.channel = t2;
+      _.controller = t3;
+      _.beforeLoad = t4;
+      _.printZone = t5;
+      _.spec = t6;
+    },
+    RemoteListener_start__closure: function RemoteListener_start__closure(t0, t1, t2, t3, t4, t5, t6) {
+      var _ = this;
+      _._box_0 = t0;
+      _.getMain = t1;
+      _.channel = t2;
+      _.controller = t3;
+      _.beforeLoad = t4;
+      _.printZone = t5;
+      _.spec = t6;
+    },
+    RemoteListener_start___closure: function RemoteListener_start___closure(t0, t1, t2, t3, t4, t5) {
+      var _ = this;
+      _._box_0 = t0;
+      _.getMain = t1;
+      _.channel = t2;
+      _.controller = t3;
+      _.beforeLoad = t4;
+      _.printZone = t5;
+    },
+    RemoteListener_start____closure: function RemoteListener_start____closure(t0, t1) {
+      this.controller = t0;
+      this.channel = t1;
+    },
+    RemoteListener_start____closure0: function RemoteListener_start____closure0(t0, t1, t2) {
+      this.suite = t0;
+      this.printZone = t1;
+      this.channel = t2;
+    },
+    RemoteListener_start_____closure: function RemoteListener_start_____closure(t0, t1, t2) {
+      this.suite = t0;
+      this.printZone = t1;
+      this.channel = t2;
+    },
+    RemoteListener_start___closure0: function RemoteListener_start___closure0(t0, t1) {
+      this._box_0 = t0;
+      this.channel = t1;
+    },
+    RemoteListener__serializeGroup_closure: function RemoteListener__serializeGroup_closure(t0, t1, t2) {
+      this._box_0 = t0;
+      this.$this = t1;
+      this.channel = t2;
+    },
+    RemoteListener__serializeTest_closure: function RemoteListener__serializeTest_closure(t0, t1, t2, t3) {
+      var _ = this;
+      _.$this = t0;
+      _.test = t1;
+      _.groups = t2;
+      _.channel = t3;
+    },
+    RemoteListener__runLiveTest_closure: function RemoteListener__runLiveTest_closure(t0) {
+      this.liveTest = t0;
+    },
+    RemoteListener__runLiveTest_closure0: function RemoteListener__runLiveTest_closure0(t0) {
+      this.channel = t0;
+    },
+    RemoteListener__runLiveTest_closure1: function RemoteListener__runLiveTest_closure1(t0, t1) {
+      this.channel = t0;
+      this.liveTest = t1;
+    },
+    RemoteListener__runLiveTest_closure2: function RemoteListener__runLiveTest_closure2(t0, t1) {
+      this.$this = t0;
+      this.channel = t1;
+    },
+    RemoteListener__runLiveTest_closure3: function RemoteListener__runLiveTest_closure3(t0, t1) {
+      this.liveTest = t0;
+      this.channel = t1;
+    },
+    RemoteListener__runLiveTest__closure: function RemoteListener__runLiveTest__closure(t0) {
+      this.channel = t0;
+    }
+  },
+  O = {DelegatingSink: function DelegatingSink(t0, t1) {
+      this._sink$_sink = t0;
+      this.$ti = t1;
+    }, None: function None() {
+    }, Scanner: function Scanner(t0) {
+      this._scanner = t0;
+      this._scanner$_next = null;
+      this._endOfFileEmitted = false;
+    }, EmptyUnmodifiableSet: function EmptyUnmodifiableSet(t0) {
+      this.$ti = t0;
+    },
+    Style__getPlatformStyle: function() {
+      if (P.Uri_base().get$scheme() !== "file")
+        return $.$get$Style_url();
+      var t1 = P.Uri_base();
+      if (!C.JSString_methods.endsWith$1(t1.get$path(t1), "/"))
+        return $.$get$Style_url();
+      if (P._Uri__Uri(null, "a/b", null, null).toFilePath$0() === "a\\b")
+        return $.$get$Style_windows();
+      return $.$get$Style_posix();
+    },
+    Style: function Style() {
+    },
+    Pool$: function(_maxAllocatedResources) {
+      var t4,
+        t1 = type$.Completer_PoolResource,
+        t2 = P.ListQueue$(t1),
+        t3 = P.ListQueue$(type$.void_Function);
+      t1 = P.ListQueue$(t1);
+      t4 = $.Zone__current;
+      if (_maxAllocatedResources <= 0)
+        H.throwExpression(P.ArgumentError$value(_maxAllocatedResources, "maxAllocatedResources", "Must be greater than zero."));
+      return new O.Pool(t2, t3, t1, _maxAllocatedResources, new S.AsyncMemoizer(new P._AsyncCompleter(new P._Future(t4, type$._Future_dynamic), type$._AsyncCompleter_dynamic), type$.AsyncMemoizer_dynamic));
+    },
+    Pool: function Pool(t0, t1, t2, t3, t4) {
+      var _ = this;
+      _._requestedResources = t0;
+      _._onReleaseCallbacks = t1;
+      _._onReleaseCompleters = t2;
+      _._maxAllocatedResources = t3;
+      _._allocatedResources = 0;
+      _._closeGroup = _._timer = null;
+      _._pool$_closeMemo = t4;
+    },
+    Pool_close_closure: function Pool_close_closure(t0) {
+      this.$this = t0;
+    },
+    Pool__onResourceReleaseAllowed_closure: function Pool__onResourceReleaseAllowed_closure(t0, t1) {
+      this.zone = t0;
+      this.registered = t1;
+    },
+    Pool__runOnRelease_closure: function Pool__runOnRelease_closure(t0) {
+      this.$this = t0;
+    },
+    Pool__runOnRelease_closure0: function Pool__runOnRelease_closure0(t0) {
+      this.$this = t0;
+    },
+    PoolResource: function PoolResource(t0) {
+      this._pool = t0;
+      this._released = false;
+    },
+    mapStackTrace: function(sourceMap, stackTrace, minified, packageResolver, sdkRoot) {
+      var t2, t3, sdkLib, t4, t1 = {};
+      t1.packageResolver = packageResolver;
+      if (type$.Chain._is(stackTrace)) {
+        t2 = stackTrace.get$traces();
+        t3 = H._arrayInstanceType(t2);
+        return new U.Chain(P.List_List$unmodifiable(new H.MappedListIterable(t2, t3._eval$1("Trace(1)")._check(new O.mapStackTrace_closure(t1, sourceMap, false, sdkRoot)), t3._eval$1("MappedListIterable<1,Trace>")), type$.Trace));
+      }
+      t2 = sdkRoot == null;
+      !t2;
+      sdkLib = t2 ? null : sdkRoot.toString$0(0) + "/lib";
+      t2 = Y.Trace_Trace$from(stackTrace).get$frames();
+      t3 = H._arrayInstanceType(t2);
+      t4 = t3._eval$1("MappedListIterable<1,Frame>");
+      return new Y.Trace(P.List_List$unmodifiable(new H.MappedListIterable(t2, t3._eval$1("Frame(1)")._check(new O.mapStackTrace_closure0(t1, sourceMap, sdkRoot, sdkLib, false)), t4).super$Iterable$where(0, t4._eval$1("bool(ListIterable.E)")._check(new O.mapStackTrace_closure1())), type$.Frame), new P._StringStackTrace(null));
+    },
+    _prettifyMember: function(member) {
+      var t2, t3,
+        t1 = P.RegExp_RegExp("/?<$", false);
+      member.toString;
+      t1 = H.stringReplaceAllUnchecked(member, t1, "");
+      t2 = P.RegExp_RegExp("\\$\\d+(\\$[a-zA-Z_0-9]+)*$", false);
+      t3 = type$.String_Function_Match;
+      t2 = C.JSString_methods.splitMapJoin$2$onMatch(H.stringReplaceAllUnchecked(t1, t2, ""), P.RegExp_RegExp("(_+)closure\\d*\\.call$", false), t3._check(new O._prettifyMember_closure()));
+      t1 = P.RegExp_RegExp("\\.call$", false);
+      t1 = H.stringReplaceAllUnchecked(t2, t1, "");
+      t2 = P.RegExp_RegExp("^dart\\.", false);
+      t1 = H.stringReplaceAllUnchecked(t1, t2, "");
+      t2 = P.RegExp_RegExp("[a-zA-Z_0-9]+\\$", false);
+      t1 = H.stringReplaceAllUnchecked(t1, t2, "");
+      t2 = P.RegExp_RegExp("^[a-zA-Z_0-9]+.(static|dart).", false);
+      return C.JSString_methods.splitMapJoin$2$onMatch(H.stringReplaceAllUnchecked(t1, t2, ""), P.RegExp_RegExp("([a-zA-Z0-9]+)_", false), t3._check(new O._prettifyMember_closure0()));
+    },
+    mapStackTrace_closure: function mapStackTrace_closure(t0, t1, t2, t3) {
+      var _ = this;
+      _._box_0 = t0;
+      _.sourceMap = t1;
+      _.minified = t2;
+      _.sdkRoot = t3;
+    },
+    mapStackTrace_closure0: function mapStackTrace_closure0(t0, t1, t2, t3, t4) {
+      var _ = this;
+      _._box_0 = t0;
+      _.sourceMap = t1;
+      _.sdkRoot = t2;
+      _.sdkLib = t3;
+      _.minified = t4;
+    },
+    mapStackTrace_closure1: function mapStackTrace_closure1() {
+    },
+    _prettifyMember_closure: function _prettifyMember_closure() {
+    },
+    _prettifyMember_closure0: function _prettifyMember_closure0() {
+    },
+    StackZoneSpecification: function StackZoneSpecification(t0, t1, t2) {
+      var _ = this;
+      _._chains = t0;
+      _._stack_zone_specification$_onError = t1;
+      _._currentNode = null;
+      _._errorZone = t2;
+    },
+    StackZoneSpecification_chainFor_closure: function StackZoneSpecification_chainFor_closure(t0) {
+      this._box_0 = t0;
+    },
+    StackZoneSpecification_chainFor_closure0: function StackZoneSpecification_chainFor_closure0(t0, t1) {
+      this.$this = t0;
+      this.original = t1;
+    },
+    StackZoneSpecification__registerCallback_closure: function StackZoneSpecification__registerCallback_closure(t0, t1, t2, t3) {
+      var _ = this;
+      _.$this = t0;
+      _.f = t1;
+      _.node = t2;
+      _.R = t3;
+    },
+    StackZoneSpecification__registerUnaryCallback_closure: function StackZoneSpecification__registerUnaryCallback_closure(t0, t1, t2, t3, t4) {
+      var _ = this;
+      _.$this = t0;
+      _.f = t1;
+      _.node = t2;
+      _.T = t3;
+      _.R = t4;
+    },
+    StackZoneSpecification__registerUnaryCallback__closure: function StackZoneSpecification__registerUnaryCallback__closure(t0, t1, t2) {
+      this.f = t0;
+      this.arg = t1;
+      this.R = t2;
+    },
+    StackZoneSpecification__registerBinaryCallback_closure: function StackZoneSpecification__registerBinaryCallback_closure(t0, t1, t2, t3, t4, t5) {
+      var _ = this;
+      _.$this = t0;
+      _.f = t1;
+      _.node = t2;
+      _.T1 = t3;
+      _.T2 = t4;
+      _.R = t5;
+    },
+    StackZoneSpecification__registerBinaryCallback__closure: function StackZoneSpecification__registerBinaryCallback__closure(t0, t1, t2, t3) {
+      var _ = this;
+      _.f = t0;
+      _.arg1 = t1;
+      _.arg2 = t2;
+      _.R = t3;
+    },
+    StackZoneSpecification__currentTrace_closure: function StackZoneSpecification__currentTrace_closure(t0, t1, t2) {
+      this._box_0 = t0;
+      this.$this = t1;
+      this.stackTrace = t2;
+    },
+    _Node: function _Node(t0, t1) {
+      this.trace = t0;
+      this.previous = t1;
+    },
+    Group$: function($name, entries, metadata, setUpAll, tearDownAll, trace) {
+      var t1 = P.List_List$unmodifiable(entries, type$.GroupEntry);
+      return new O.Group($name, metadata, trace, t1, setUpAll, tearDownAll);
+    },
+    Group: function Group(t0, t1, t2, t3, t4, t5) {
+      var _ = this;
+      _.name = t0;
+      _.metadata = t1;
+      _.trace = t2;
+      _.entries = t3;
+      _.setUpAll = t4;
+      _.tearDownAll = t5;
+    },
+    Group_forPlatform_closure: function Group_forPlatform_closure(t0) {
+      this.platform = t0;
+    },
+    Group__map_closure: function Group__map_closure(t0) {
+      this.callback = t0;
+    },
+    Group__map_closure0: function Group__map_closure0() {
+    },
+    Metadata__parseOnPlatform: function(onPlatform) {
+      return P.LinkedHashMap_LinkedHashMap$_empty(type$.PlatformSelector, type$.Metadata);
+    },
+    Metadata__parseTags: function(tags) {
+      return P.LinkedHashSet_LinkedHashSet$_empty(type$.String);
+    },
+    Metadata_Metadata: function(chainStackTraces, forTag, onPlatform, retry, skip, skipReason, tags, testOn, timeout, verboseTrace) {
+      var t2, t3, empty, t4, merged, _null = null, t1 = {};
+      t1.tags = tags;
+      t1.forTag = forTag;
+      t2 = new O.Metadata_Metadata__unresolved(t1, testOn, timeout, skip, verboseTrace, chainStackTraces, retry, skipReason, onPlatform);
+      if (forTag == null || tags == null)
+        return t2.call$0();
+      t1.tags = P.LinkedHashSet_LinkedHashSet$from(tags, type$.String);
+      t3 = type$.Metadata;
+      t1.forTag = P.LinkedHashMap_LinkedHashMap$from(t1.forTag, type$.BooleanSelector, t3);
+      empty = O.Metadata$_(_null, _null, _null, _null, _null, _null, _null, _null, _null, _null);
+      t4 = t1.forTag.get$keys();
+      merged = C.JSArray_methods.fold$1$2(P.List_List$from(t4, true, H._instanceType(t4)._eval$1("Iterable.E")), empty, new O.Metadata_Metadata_closure(t1), t3);
+      if (merged === empty)
+        return t2.call$0();
+      return merged.merge$1(t2.call$0());
+    },
+    Metadata$_: function(chainStackTraces, forTag, onPlatform, retry, skip, skipReason, tags, testOn, timeout, verboseTrace) {
+      var t1 = testOn == null ? C.PlatformSelector_All : testOn,
+        t2 = timeout == null ? C.Timeout_null_1 : timeout,
+        t3 = tags == null ? P.LinkedHashSet_LinkedHashSet$_empty(type$.String) : tags.toSet$0(0),
+        t4 = onPlatform == null ? C.Map_empty : new P.UnmodifiableMapView(onPlatform, type$.UnmodifiableMapView_PlatformSelector_Metadata),
+        t5 = forTag == null ? C.Map_empty0 : new P.UnmodifiableMapView(forTag, type$.UnmodifiableMapView_BooleanSelector_Metadata);
+      t5 = new O.Metadata(t1, t2, skip, skipReason, verboseTrace, chainStackTraces, new L.UnmodifiableSetView(t3, type$.UnmodifiableSetView_String), retry, t4, t5);
+      if (retry != null)
+        P.RangeError_checkNotNegative(retry, "retry");
+      t5._validateTags$0();
+      return t5;
+    },
+    Metadata$parse: function(onPlatform, retry, skip, tags, testOn, timeout) {
+      var _null = null,
+        t1 = timeout == null ? C.Timeout_null_1 : timeout,
+        t2 = skip == null,
+        t3 = t2 ? _null : skip,
+        t4 = O.Metadata__parseOnPlatform(onPlatform);
+      t4 = new O.Metadata(C.PlatformSelector_All, t1, t3, _null, _null, _null, O.Metadata__parseTags(tags), retry, t4, C.Map_empty0);
+      !t2;
+      if (retry != null)
+        P.RangeError_checkNotNegative(retry, "retry");
+      t4._validateTags$0();
+      return t4;
+    },
+    Metadata$deserialize: function(serialized) {
+      var pair, t13,
+        t1 = J.getInterceptor$asx(serialized),
+        t2 = t1.$index(serialized, "testOn") == null ? C.PlatformSelector_All : E.PlatformSelector$parse(H._asStringNullable(t1.$index(serialized, "testOn"))),
+        t3 = O.Metadata__deserializeTimeout(t1.$index(serialized, "timeout")),
+        t4 = H._asBoolNullable(t1.$index(serialized, "skip")),
+        t5 = H._asStringNullable(t1.$index(serialized, "skipReason")),
+        t6 = H._asBoolNullable(t1.$index(serialized, "verboseTrace")),
+        t7 = H._asBoolNullable(t1.$index(serialized, "chainStackTraces")),
+        t8 = H._asIntNullable(t1.$index(serialized, "retry")),
+        t9 = type$.Iterable_dynamic,
+        t10 = P.LinkedHashSet_LinkedHashSet$from(t9._as(t1.$index(serialized, "tags")), type$.String),
+        t11 = type$.Metadata,
+        t12 = P.LinkedHashMap_LinkedHashMap$_empty(type$.PlatformSelector, t11);
+      for (t9 = J.get$iterator$ax(t9._check(t1.$index(serialized, "onPlatform"))); t9.moveNext$0();) {
+        pair = t9.get$current();
+        t13 = J.getInterceptor$ax(pair);
+        t12.$indexSet(0, E.PlatformSelector$parse(H._asStringNullable(t13.get$first(pair))), O.Metadata$deserialize(t13.get$last(pair)));
+      }
+      return new O.Metadata(t2, t3, t4, t5, t6, t7, t10, t8, t12, type$.Map_dynamic_dynamic._as(t1.$index(serialized, "forTag")).map$2$1(0, new O.Metadata$deserialize_closure(), type$.BooleanSelector, t11));
+    },
+    Metadata__deserializeTimeout: function(serialized) {
+      var scaleFactor,
+        t1 = J.getInterceptor$(serialized);
+      if (t1.$eq(serialized, "none"))
+        return C.Timeout_null_null;
+      scaleFactor = t1.$index(serialized, "scaleFactor");
+      if (scaleFactor != null)
+        return new R.Timeout(null, H._asNumNullable(scaleFactor));
+      return new R.Timeout(P.Duration$(H._asIntNullable(t1.$index(serialized, "duration")), 0), null);
+    },
+    Metadata: function Metadata(t0, t1, t2, t3, t4, t5, t6, t7, t8, t9) {
+      var _ = this;
+      _.testOn = t0;
+      _.timeout = t1;
+      _._skip = t2;
+      _.skipReason = t3;
+      _._verboseTrace = t4;
+      _._chainStackTraces = t5;
+      _.tags = t6;
+      _._retry = t7;
+      _.onPlatform = t8;
+      _.forTag = t9;
+    },
+    Metadata_Metadata__unresolved: function Metadata_Metadata__unresolved(t0, t1, t2, t3, t4, t5, t6, t7, t8) {
+      var _ = this;
+      _._box_0 = t0;
+      _.testOn = t1;
+      _.timeout = t2;
+      _.skip = t3;
+      _.verboseTrace = t4;
+      _.chainStackTraces = t5;
+      _.retry = t6;
+      _.skipReason = t7;
+      _.onPlatform = t8;
+    },
+    Metadata_Metadata_closure: function Metadata_Metadata_closure(t0) {
+      this._box_0 = t0;
+    },
+    Metadata$deserialize_closure: function Metadata$deserialize_closure() {
+    },
+    Metadata__validateTags_closure: function Metadata__validateTags_closure() {
+    },
+    Metadata__validateTags_closure0: function Metadata__validateTags_closure0() {
+    },
+    Metadata_validatePlatformSelectors_closure: function Metadata_validatePlatformSelectors_closure(t0) {
+      this.validVariables = t0;
+    },
+    Metadata_merge_closure: function Metadata_merge_closure() {
+    },
+    Metadata_merge_closure0: function Metadata_merge_closure0() {
+    },
+    Metadata_forPlatform_closure: function Metadata_forPlatform_closure(t0, t1) {
+      this._box_0 = t0;
+      this.platform = t1;
+    },
+    Metadata_serialize_closure: function Metadata_serialize_closure(t0) {
+      this.serializedOnPlatform = t0;
+    },
+    Metadata_serialize_closure0: function Metadata_serialize_closure0() {
+    },
+    IterableSet: function IterableSet(t0, t1) {
+      this._iterable_set$_base = t0;
+      this.$ti = t1;
+    },
+    _IterableSet_SetMixin_UnmodifiableSetMixin: function _IterableSet_SetMixin_UnmodifiableSetMixin() {
+    },
+    Engine$: function() {
+      var t6, t7, t8, t9, t10, t11, _null = null,
+        t1 = $.Zone__current,
+        t2 = H.setRuntimeTypeInfo([], type$.JSArray_dynamic),
+        t3 = type$.RunnerSuite,
+        t4 = P.StreamController_StreamController(_null, _null, false, t3),
+        t5 = new L.StreamGroup(C._StreamGroupState_dormant, new H.JsLinkedHashMap(type$.JsLinkedHashMap_of_Stream_LiveTest_and_StreamSubscription_LiveTest), type$.StreamGroup_LiveTest);
+      t5.set$_stream_group$_controller(new P._SyncBroadcastStreamController(t5.get$_onListen(), t5.get$_onCancelBroadcast(), type$._SyncBroadcastStreamController_LiveTest));
+      t6 = type$.LiveTest;
+      t7 = Y.UnionSetController$(true, t6);
+      t8 = Y.UnionSetController$(true, t6);
+      t9 = Y.UnionSetController$(true, t6);
+      t10 = Q.QueueList$(t6);
+      t11 = O.Pool$(1);
+      t1 = new O.Engine(t11, O.Pool$(2), new F.FutureGroup(new P._AsyncCompleter(new P._Future(t1, type$._Future_List_dynamic), type$._AsyncCompleter_List_dynamic), t2, type$.FutureGroup_dynamic), P.LinkedHashSet_LinkedHashSet$_empty(type$.StreamSubscription_dynamic), t4, P.LinkedHashSet_LinkedHashSet$_empty(t3), new P._AsyncBroadcastStreamController(_null, _null, type$._AsyncBroadcastStreamController_RunnerSuite), P.LinkedHashSet_LinkedHashSet$_empty(type$.LiveSuite), new P._AsyncBroadcastStreamController(_null, _null, type$._AsyncBroadcastStreamController_LiveSuite), t5, t7, t8, t9, t10, P.LinkedHashSet_LinkedHashSet$_empty(t6), P.LinkedHashSet_LinkedHashSet$_empty(t6));
+      t1.Engine$3$concurrency$coverage$maxSuites(_null, _null, _null);
+      return t1;
+    },
+    Engine: function Engine(t0, t1, t2, t3, t4, t5, t6, t7, t8, t9, t10, t11, t12, t13, t14, t15) {
+      var _ = this;
+      _._engine$_closed = _._engine$_runCalled = false;
+      _._closedBeforeDone = null;
+      _._runPool = t0;
+      _._loadPool = t1;
+      _._group = t2;
+      _._engine$_subscriptions = t3;
+      _._suiteController = t4;
+      _._addedSuites = t5;
+      _._onSuiteAddedController = t6;
+      _._liveSuites = t7;
+      _._onSuiteStartedController = t8;
+      _._onTestStartedGroup = t9;
+      _._passedGroup = t10;
+      _._skippedGroup = t11;
+      _._failedGroup = t12;
+      _._active = t13;
+      _._restarted = t14;
+      _._activeLoadTests = t15;
+    },
+    Engine_success_closure: function Engine_success_closure() {
+    },
+    Engine_closure: function Engine_closure(t0) {
+      this.$this = t0;
+    },
+    Engine_closure0: function Engine_closure0() {
+    },
+    Engine_run_closure: function Engine_run_closure(t0) {
+      this.$this = t0;
+    },
+    Engine_run__closure: function Engine_run__closure(t0, t1) {
+      this.$this = t0;
+      this.suite = t1;
+    },
+    Engine_run___closure: function Engine_run___closure(t0, t1, t2) {
+      this._box_0 = t0;
+      this.$this = t1;
+      this.loadResource = t2;
+    },
+    Engine_run____closure: function Engine_run____closure(t0) {
+      this._box_0 = t0;
+    },
+    Engine_run_closure0: function Engine_run_closure0(t0, t1) {
+      this._box_1 = t0;
+      this.$this = t1;
+    },
+    Engine__runLiveTest_closure: function Engine__runLiveTest_closure(t0, t1) {
+      this.$this = t0;
+      this.liveTest = t1;
+    },
+    Engine__runLiveTest_closure0: function Engine__runLiveTest_closure0(t0, t1) {
+      this._box_0 = t0;
+      this.$this = t1;
+    },
+    Engine__runLiveTest_closure1: function Engine__runLiveTest_closure1() {
+    },
+    Engine__runSkippedTest_closure: function Engine__runSkippedTest_closure() {
+    },
+    Engine__runSkippedTest_closure0: function Engine__runSkippedTest_closure0(t0, t1) {
+      this._box_0 = t0;
+      this.skipped = t1;
+    },
+    Engine__runSkippedTest_closure1: function Engine__runSkippedTest_closure1() {
+    },
+    binarySearch: function(list, matches) {
+      var max, min, half;
+      if (list.length === 0)
+        return -1;
+      if (H.boolConversionCheck(matches.call$1(C.JSArray_methods.get$first(list))))
+        return 0;
+      if (!H.boolConversionCheck(matches.call$1(C.JSArray_methods.get$last(list))))
+        return list.length;
+      max = list.length - 1;
+      for (min = 0; min < max;) {
+        half = min + C.JSInt_methods._tdivFast$1(max - min, 2);
+        if (half < 0 || half >= list.length)
+          return H.ioore(list, half);
+        if (H.boolConversionCheck(matches.call$1(list[half])))
+          max = half;
+        else
+          min = half + 1;
+      }
+      return max;
+    }
+  },
+  Y = {DelegatingStreamSubscription: function DelegatingStreamSubscription() {
+    }, StreamCompleter: function StreamCompleter(t0, t1) {
+      this._stream = t0;
+      this.$ti = t1;
+    }, _CompleterStream: function _CompleterStream(t0) {
+      this._sourceStream = this._stream_completer$_controller = null;
+      this.$ti = t0;
+    }, BooleanSelectorImpl: function BooleanSelectorImpl(t0) {
+      this._selector = t0;
+    },
+    mapMap: function(map, value, K1, V1, K2, V2) {
+      var key, result, t1 = {};
+      t1.key = key;
+      t1.value = value;
+      t1.key = null;
+      t1.key = new Y.mapMap_closure(K2, K1, V1);
+      result = P.LinkedHashMap_LinkedHashMap$_empty(K2, V2);
+      map.forEach$1(0, new Y.mapMap_closure0(t1, result, K1, V1));
+      return result;
+    },
+    mergeMaps: function(map1, map2, value, $K, $V) {
+      var result = P.LinkedHashMap_LinkedHashMap$from(map1, $K, $V);
+      map2.forEach$1(0, new Y.mergeMaps_closure(result, value, $K, $V));
+      return result;
+    },
+    mapMap_closure: function mapMap_closure(t0, t1, t2) {
+      this.K2 = t0;
+      this.K1 = t1;
+      this.V1 = t2;
+    },
+    mapMap_closure0: function mapMap_closure0(t0, t1, t2, t3) {
+      var _ = this;
+      _._box_0 = t0;
+      _.result = t1;
+      _.K1 = t2;
+      _.V1 = t3;
+    },
+    mergeMaps_closure: function mergeMaps_closure(t0, t1, t2, t3) {
+      var _ = this;
+      _.result = t0;
+      _.value = t1;
+      _.K = t2;
+      _.V = t3;
+    },
+    UnionSetController$: function(disjoint, $E) {
+      var t1 = P.LinkedHashSet_LinkedHashSet($E._eval$1("Set<0>")),
+        t2 = new Y.UnionSetController(t1, $E._eval$1("UnionSetController<0>"));
+      t2.set$_union_set_controller$_set(new M.UnionSet(t1, true, $E._eval$1("UnionSet<0>")));
+      return t2;
+    },
+    UnionSetController: function UnionSetController(t0, t1) {
+      this._union_set_controller$_set = null;
+      this._union_set_controller$_sets = t0;
+      this.$ti = t1;
+    },
+    _IsTrue: function _IsTrue() {
+    },
+    _Predicate: function _Predicate(t0, t1, t2) {
+      this._matcher = t0;
+      this._core_matchers$_description = t1;
+      this.$ti = t2;
+    },
+    FileLocation$_: function(file, offset) {
+      if (offset < 0)
+        H.throwExpression(P.RangeError$("Offset may not be negative, was " + offset + "."));
+      else if (offset > file._decodedChars.length)
+        H.throwExpression(P.RangeError$("Offset " + offset + " must not be greater than the number of characters in the file, " + file.get$length(file) + "."));
+      return new Y.FileLocation(file, offset);
+    },
+    _FileSpan$: function(file, _start, _end) {
+      if (_end < _start)
+        H.throwExpression(P.ArgumentError$("End " + _end + " must come after start " + _start + "."));
+      else if (_end > file._decodedChars.length)
+        H.throwExpression(P.RangeError$("End " + _end + " must not be greater than the number of characters in the file, " + file.get$length(file) + "."));
+      else if (_start < 0)
+        H.throwExpression(P.RangeError$("Start may not be negative, was " + _start + "."));
+      return new Y._FileSpan(file, _start, _end);
+    },
+    SourceFile: function SourceFile(t0, t1, t2) {
+      var _ = this;
+      _.url = t0;
+      _._lineStarts = t1;
+      _._decodedChars = t2;
+      _._cachedLine = null;
+    },
+    FileLocation: function FileLocation(t0, t1) {
+      this.file = t0;
+      this.offset = t1;
+    },
+    _FileSpan: function _FileSpan(t0, t1, t2) {
+      this.file = t0;
+      this._file$_start = t1;
+      this._file$_end = t2;
+    },
+    SourceSpanMixin: function SourceSpanMixin() {
+    },
+    Trace_Trace$current: function(level) {
+      return new T.LazyTrace(new Y.Trace_Trace$current_closure(Y.Trace_Trace$from(P.StackTrace_current()), level));
+    },
+    Trace_Trace$from: function(trace) {
+      if (trace == null)
+        throw H.wrapException(P.ArgumentError$("Cannot create a Trace from null."));
+      if (type$.Trace._is(trace))
+        return trace;
+      if (type$.Chain._is(trace))
+        return trace.toTrace$0();
+      return new T.LazyTrace(new Y.Trace_Trace$from_closure(trace));
+    },
+    Trace_Trace$parse: function(trace) {
+      var error, t1, exception;
+      try {
+        if (trace.length === 0) {
+          t1 = P.List_List$unmodifiable(H.setRuntimeTypeInfo([], type$.JSArray_Frame), type$.Frame);
+          return new Y.Trace(t1, new P._StringStackTrace(null));
+        }
+        if (C.JSString_methods.contains$1(trace, $.$get$_v8Trace())) {
+          t1 = Y.Trace$parseV8(trace);
+          return t1;
+        }
+        if (C.JSString_methods.contains$1(trace, "\tat ")) {
+          t1 = Y.Trace$parseJSCore(trace);
+          return t1;
+        }
+        if (C.JSString_methods.contains$1(trace, $.$get$_firefoxSafariTrace())) {
+          t1 = Y.Trace$parseFirefox(trace);
+          return t1;
+        }
+        if (C.JSString_methods.contains$1(trace, "===== asynchronous gap ===========================\n")) {
+          t1 = U.Chain_Chain$parse(trace).toTrace$0();
+          return t1;
+        }
+        if (C.JSString_methods.contains$1(trace, $.$get$_friendlyTrace())) {
+          t1 = Y.Trace$parseFriendly(trace);
+          return t1;
+        }
+        t1 = P.List_List$unmodifiable(Y.Trace__parseVM(trace), type$.Frame);
+        return new Y.Trace(t1, new P._StringStackTrace(trace));
+      } catch (exception) {
+        t1 = H.unwrapException(exception);
+        if (type$.FormatException._is(t1)) {
+          error = t1;
+          throw H.wrapException(P.FormatException$(H.S(J.get$message$x(error)) + "\nStack trace:\n" + H.S(trace), null, null));
+        } else
+          throw exception;
+      }
+    },
+    Trace__parseVM: function(trace) {
+      var t2, $frames,
+        t1 = J.trim$0$s(trace),
+        lines = H.setRuntimeTypeInfo(H.stringReplaceAllUnchecked(t1, "<asynchronous suspension>\n", "").split("\n"), type$.JSArray_String);
+      t1 = H.SubListIterable$(lines, 0, lines.length - 1, type$.String);
+      t2 = t1.$ti;
+      $frames = new H.MappedListIterable(t1, t2._eval$1("Frame(ListIterable.E)")._check(new Y.Trace__parseVM_closure()), t2._eval$1("MappedListIterable<ListIterable.E,Frame>")).toList$0(0);
+      if (!J.endsWith$1$s(C.JSArray_methods.get$last(lines), ".da"))
+        C.JSArray_methods.add$1($frames, A.Frame_Frame$parseVM(C.JSArray_methods.get$last(lines)));
+      return $frames;
+    },
+    Trace$parseV8: function(trace) {
+      var t2, t3,
+        t1 = H.SubListIterable$(H.setRuntimeTypeInfo(trace.split("\n"), type$.JSArray_String), 1, null, type$.String);
+      t1 = t1.super$Iterable$skipWhile(0, t1.$ti._eval$1("bool(ListIterable.E)")._check(new Y.Trace$parseV8_closure()));
+      t2 = type$.Frame;
+      t3 = t1.$ti;
+      return new Y.Trace(P.List_List$unmodifiable(H.MappedIterable_MappedIterable(t1, t3._eval$1("Frame(Iterable.E)")._check(new Y.Trace$parseV8_closure0()), t3._eval$1("Iterable.E"), t2), t2), new P._StringStackTrace(trace));
+    },
+    Trace$parseJSCore: function(trace) {
+      return new Y.Trace(P.List_List$unmodifiable(new H.MappedIterable(new H.WhereIterable(H.setRuntimeTypeInfo(trace.split("\n"), type$.JSArray_String), type$.bool_Function_String._check(new Y.Trace$parseJSCore_closure()), type$.WhereIterable_String), type$.Frame_Function_String._check(new Y.Trace$parseJSCore_closure0()), type$.MappedIterable_String_Frame), type$.Frame), new P._StringStackTrace(trace));
+    },
+    Trace$parseFirefox: function(trace) {
+      return new Y.Trace(P.List_List$unmodifiable(new H.MappedIterable(new H.WhereIterable(H.setRuntimeTypeInfo(C.JSString_methods.trim$0(trace).split("\n"), type$.JSArray_String), type$.bool_Function_String._check(new Y.Trace$parseFirefox_closure()), type$.WhereIterable_String), type$.Frame_Function_String._check(new Y.Trace$parseFirefox_closure0()), type$.MappedIterable_String_Frame), type$.Frame), new P._StringStackTrace(trace));
+    },
+    Trace$parseFriendly: function(trace) {
+      var t1 = trace.length === 0 ? H.setRuntimeTypeInfo([], type$.JSArray_Frame) : new H.MappedIterable(new H.WhereIterable(H.setRuntimeTypeInfo(C.JSString_methods.trim$0(trace).split("\n"), type$.JSArray_String), type$.bool_Function_String._check(new Y.Trace$parseFriendly_closure()), type$.WhereIterable_String), type$.Frame_Function_String._check(new Y.Trace$parseFriendly_closure0()), type$.MappedIterable_String_Frame);
+      return new Y.Trace(P.List_List$unmodifiable(t1, type$.Frame), new P._StringStackTrace(trace));
+    },
+    Trace: function Trace(t0, t1) {
+      this.frames = t0;
+      this.original = t1;
+    },
+    Trace_Trace$current_closure: function Trace_Trace$current_closure(t0, t1) {
+      this.trace = t0;
+      this.level = t1;
+    },
+    Trace_Trace$from_closure: function Trace_Trace$from_closure(t0) {
+      this.trace = t0;
+    },
+    Trace__parseVM_closure: function Trace__parseVM_closure() {
+    },
+    Trace$parseV8_closure: function Trace$parseV8_closure() {
+    },
+    Trace$parseV8_closure0: function Trace$parseV8_closure0() {
+    },
+    Trace$parseJSCore_closure: function Trace$parseJSCore_closure() {
+    },
+    Trace$parseJSCore_closure0: function Trace$parseJSCore_closure0() {
+    },
+    Trace$parseFirefox_closure: function Trace$parseFirefox_closure() {
+    },
+    Trace$parseFirefox_closure0: function Trace$parseFirefox_closure0() {
+    },
+    Trace$parseFriendly_closure: function Trace$parseFriendly_closure() {
+    },
+    Trace$parseFriendly_closure0: function Trace$parseFriendly_closure0() {
+    },
+    Trace_foldFrames_closure: function Trace_foldFrames_closure(t0) {
+      this.oldPredicate = t0;
+    },
+    Trace_foldFrames_closure0: function Trace_foldFrames_closure0(t0) {
+      this._box_0 = t0;
+    },
+    Trace_toString_closure0: function Trace_toString_closure0() {
+    },
+    Trace_toString_closure: function Trace_toString_closure(t0) {
+      this.longest = t0;
+    },
+    RunnerSuite: function RunnerSuite(t0, t1, t2, t3) {
+      var _ = this;
+      _._runner_suite$_controller = t0;
+      _.platform = t1;
+      _.path = t2;
+      _.group = t3;
+    },
+    RunnerSuiteController: function RunnerSuiteController(t0, t1, t2, t3, t4) {
+      var _ = this;
+      _._config = t0;
+      _._runner_suite$_onClose = t1;
+      _._onDebuggingController = t2;
+      _._channelNames = t3;
+      _._closeMemo = t4;
+    },
+    RunnerSuiteController__close_closure: function RunnerSuiteController__close_closure(t0) {
+      this.$this = t0;
+    }
+  },
+  F = {FutureGroup: function FutureGroup(t0, t1, t2) {
+      var _ = this;
+      _._future_group$_pending = 0;
+      _._future_group$_closed = false;
+      _._future_group$_completer = t0;
+      _._values = t1;
+      _.$ti = t2;
+    }, FutureGroup_add_closure: function FutureGroup_add_closure(t0, t1) {
+      this.$this = t0;
+      this.index = t1;
+    }, FutureGroup_add_closure0: function FutureGroup_add_closure0(t0) {
+      this.$this = t0;
+    }, ValueResult: function ValueResult(t0, t1) {
+      this.value = t0;
+      this.$ti = t1;
+    },
+    PackageConfigResolver__normalizeMap: function(map) {
+      var t1 = type$.String,
+        t2 = type$.Uri;
+      return new P.UnmodifiableMapView(Y.mapMap(map, new F.PackageConfigResolver__normalizeMap_closure(), t1, t2, t1, t2), type$.UnmodifiableMapView_String_Uri);
+    },
+    PackageConfigResolver: function PackageConfigResolver(t0) {
+      this.packageConfigMap = t0;
+    },
+    PackageConfigResolver__normalizeMap_closure: function PackageConfigResolver__normalizeMap_closure() {
+    },
+    UrlStyle: function UrlStyle(t0, t1, t2, t3) {
+      var _ = this;
+      _.separatorPattern = t0;
+      _.needsSeparatorPattern = t1;
+      _.rootPattern = t2;
+      _.relativeRootPattern = t3;
+    }
+  },
+  V = {ErrorResult: function ErrorResult(t0, t1) {
+      this.error = t0;
+      this.stackTrace = t1;
+    },
+    SourceLocation$: function(offset, column, line, sourceUrl) {
+      var t2, t3, t4, t5,
+        t1 = typeof sourceUrl == "string" ? P.Uri_parse(sourceUrl) : sourceUrl;
+      type$.Uri._check(t1);
+      t2 = line == null;
+      t3 = t2 ? 0 : line;
+      t4 = column == null;
+      t5 = t4 ? offset : column;
+      if (offset < 0)
+        H.throwExpression(P.RangeError$("Offset may not be negative, was " + offset + "."));
+      else if (!t2 && line < 0)
+        H.throwExpression(P.RangeError$("Line may not be negative, was " + H.S(line) + "."));
+      else if (!t4 && column < 0)
+        H.throwExpression(P.RangeError$("Column may not be negative, was " + H.S(column) + "."));
+      return new V.SourceLocation(t1, offset, t3, t5);
+    },
+    SourceLocation: function SourceLocation(t0, t1, t2, t3) {
+      var _ = this;
+      _.sourceUrl = t0;
+      _.offset = t1;
+      _.line = t2;
+      _.column = t3;
+    },
+    SourceSpan: function SourceSpan() {
+    },
+    SourceSpanBase: function SourceSpanBase() {
+    },
+    GroupEntry: function GroupEntry() {
+    },
+    LiveTestController$: function(suite, _test, onRun, onClose, groups) {
+      var _null = null,
+        t1 = H.setRuntimeTypeInfo([], type$.JSArray_AsyncError),
+        t2 = $.Zone__current,
+        t3 = P.List_List$unmodifiable(groups, type$.Group);
+      t1 = new V.LiveTestController(suite, t3, _test, onRun, onClose, t1, C.State_Status_pending_Result_success, new P._SyncBroadcastStreamController(_null, _null, type$._SyncBroadcastStreamController_State), new P._SyncBroadcastStreamController(_null, _null, type$._SyncBroadcastStreamController_AsyncError), new P._SyncBroadcastStreamController(_null, _null, type$._SyncBroadcastStreamController_Message), new P._AsyncCompleter(new P._Future(t2, type$._Future_void), type$._AsyncCompleter_void));
+      t1._liveTest = new V._LiveTest(t1);
+      return t1;
+    },
+    _LiveTest: function _LiveTest(t0) {
+      this._live_test_controller$_controller = t0;
+    },
+    LiveTestController: function LiveTestController(t0, t1, t2, t3, t4, t5, t6, t7, t8, t9, t10) {
+      var _ = this;
+      _._liveTest = null;
+      _._live_test_controller$_suite = t0;
+      _._groups = t1;
+      _._test = t2;
+      _._onRun = t3;
+      _._onClose = t4;
+      _._errors = t5;
+      _._live_test_controller$_state = t6;
+      _._onStateChangeController = t7;
+      _._onErrorController = t8;
+      _._onMessageController = t9;
+      _.completer = t10;
+      _._runCalled = false;
+    },
+    Test: function Test() {
+    },
+    errorsDontStopTest: function(body) {
+      var t1 = $.Zone__current,
+        t2 = new P._Future(t1, type$._Future_dynamic),
+        t3 = type$.Invoker;
+      t3._as(t1.$index(0, C.Symbol_cQL)).addOutstandingCallback$0();
+      t3._as($.Zone__current.$index(0, C.Symbol_cQL)).waitForOutstandingCallbacks$1(new V.errorsDontStopTest_closure(body, new P._AsyncCompleter(t2, type$._AsyncCompleter_dynamic))).then$1$1(new V.errorsDontStopTest_closure0(), type$.void);
+      return t2;
+    },
+    errorsDontStopTest_closure: function errorsDontStopTest_closure(t0, t1) {
+      this.body = t0;
+      this.completer = t1;
+    },
+    errorsDontStopTest_closure0: function errorsDontStopTest_closure0() {
+    }
+  },
+  E = {Result: function Result() {
+    }, StringDescription: function StringDescription(t0) {
+      this._out = t0;
+    }, FeatureMatcher: function FeatureMatcher() {
+    }, PosixStyle: function PosixStyle(t0, t1, t2) {
+      this.separatorPattern = t0;
+      this.needsSeparatorPattern = t1;
+      this.rootPattern = t2;
+    },
+    StringScannerException$: function(message, span, source) {
+      return new E.StringScannerException(message, span);
+    },
+    StringScannerException: function StringScannerException(t0, t1) {
+      this._span_exception$_message = t0;
+      this._span_exception$_span = t1;
+    },
+    PlatformSelector$parse: function(selector) {
+      return new E.PlatformSelector(E.PlatformSelector__wrapFormatException(new E.PlatformSelector$parse_closure(selector), null, type$.BooleanSelector));
+    },
+    PlatformSelector__wrapFormatException: function(body, span, $T) {
+      var t1 = body.call$0();
+      return t1;
+    },
+    PlatformSelector: function PlatformSelector(t0) {
+      this._platform_selector$_inner = t0;
+    },
+    PlatformSelector$parse_closure: function PlatformSelector$parse_closure(t0) {
+      this.selector = t0;
+    },
+    PlatformSelector_validate_closure: function PlatformSelector_validate_closure(t0, t1) {
+      this.$this = t0;
+      this.validVariables = t1;
+    },
+    PlatformSelector_validate__closure: function PlatformSelector_validate__closure(t0) {
+      this.validVariables = t0;
+    },
+    PlatformSelector_evaluate_closure: function PlatformSelector_evaluate_closure(t0) {
+      this.platform = t0;
+    },
+    SuitePlatform$: function(runtime, inGoogle, os) {
+      var t1 = os == null ? C.OperatingSystem_none_none : os;
+      if (H.boolConversionCheck(runtime.isBrowser) && t1 !== C.OperatingSystem_none_none)
+        H.throwExpression(P.ArgumentError$('No OS should be passed for runtime "' + runtime.toString$0(0) + '".'));
+      return new E.SuitePlatform(runtime, t1, inGoogle);
+    },
+    SuitePlatform: function SuitePlatform(t0, t1, t2) {
+      this.runtime = t0;
+      this.os = t1;
+      this.inGoogle = t2;
+    },
+    StackTraceMapper: function StackTraceMapper() {
+    },
+    LiveSuite: function LiveSuite() {
+    },
+    JSStackTraceMapper_deserialize: function(serialized) {
+      var t1, t2, t3,
+        _s11_ = "packageRoot",
+        packageRoot = H._asStringNullable(serialized.$index(0, _s11_));
+      if (packageRoot == null)
+        packageRoot = "";
+      t1 = H._asStringNullable(serialized.$index(0, "mapContents"));
+      t2 = P.Uri_parse(H._asStringNullable(serialized.$index(0, "sdkRoot")));
+      if (packageRoot.length !== 0)
+        t3 = new D.PackageRootResolver(B.ensureTrailingSlash(B.asUri(P.Uri_parse(H._asStringNullable(serialized.$index(0, _s11_))), _s11_)));
+      else {
+        t3 = type$.String;
+        t3 = F.PackageConfigResolver__normalizeMap(E.JSStackTraceMapper__deserializePackageConfigMap(type$.Map_dynamic_dynamic._as(serialized.$index(0, "packageConfigMap")).cast$2$0(0, t3, t3)));
+        t3 = new F.PackageConfigResolver(t3);
+      }
+      return new E.JSStackTraceMapper(t3, t2, t1, P.Uri_parse(H._asStringNullable(serialized.$index(0, "mapUrl"))));
+    },
+    JSStackTraceMapper__deserializePackageConfigMap: function(serialized) {
+      return serialized.map$2$1(0, new E.JSStackTraceMapper__deserializePackageConfigMap_closure(), type$.String, type$.Uri);
+    },
+    JSStackTraceMapper: function JSStackTraceMapper(t0, t1, t2, t3) {
+      var _ = this;
+      _._mapping = null;
+      _._packageResolver = t0;
+      _._sdkRoot = t1;
+      _._mapContents = t2;
+      _._mapUrl = t3;
+    },
+    JSStackTraceMapper__deserializePackageConfigMap_closure: function JSStackTraceMapper__deserializePackageConfigMap_closure() {
+    }
+  },
+  L = {StreamGroup: function StreamGroup(t0, t1, t2) {
+      var _ = this;
+      _._stream_group$_controller = null;
+      _._stream_group$_closed = false;
+      _._stream_group$_state = t0;
+      _._stream_group$_subscriptions = t1;
+      _.$ti = t2;
+    }, StreamGroup_add_closure: function StreamGroup_add_closure() {
+    }, StreamGroup_add_closure0: function StreamGroup_add_closure0(t0, t1) {
+      this.$this = t0;
+      this.stream = t1;
+    }, StreamGroup__onListen_closure: function StreamGroup__onListen_closure(t0) {
+      this.$this = t0;
+    }, StreamGroup__onCancelBroadcast_closure: function StreamGroup__onCancelBroadcast_closure(t0) {
+      this.$this = t0;
+    }, StreamGroup__listenToStream_closure: function StreamGroup__listenToStream_closure(t0, t1) {
+      this.$this = t0;
+      this.stream = t1;
+    }, _StreamGroupState: function _StreamGroupState(t0) {
+      this.name = t0;
+    }, Token: function Token(t0, t1) {
+      this.type = t0;
+      this.span = t1;
+    }, IdentifierToken: function IdentifierToken(t0, t1) {
+      this.span = t0;
+      this.name = t1;
+    }, TokenType: function TokenType(t0) {
+      this.name = t0;
+    },
+    UnmodifiableSetView$: function(setBase, $E) {
+      return new L.UnmodifiableSetView(setBase, $E._eval$1("UnmodifiableSetView<0>"));
+    },
+    UnmodifiableSetView: function UnmodifiableSetView(t0, t1) {
+      this._base = t0;
+      this.$ti = t1;
+    },
+    UnmodifiableSetMixin: function UnmodifiableSetMixin() {
+    },
+    _UnmodifiableSetView_DelegatingSet_UnmodifiableSetMixin: function _UnmodifiableSetView_DelegatingSet_UnmodifiableSetMixin() {
+    },
+    WindowsStyle: function WindowsStyle(t0, t1, t2, t3) {
+      var _ = this;
+      _.separatorPattern = t0;
+      _.needsSeparatorPattern = t1;
+      _.rootPattern = t2;
+      _.relativeRootPattern = t3;
+    },
+    WindowsStyle_absolutePathToUri_closure: function WindowsStyle_absolutePathToUri_closure() {
+    },
+    decodeVlq: function(chars) {
+      var t1, t2, result, $stop, shift, t3, char, digit, result0, _null = null;
+      for (t1 = chars._parser$_length, t2 = chars._internal, result = 0, $stop = false, shift = 0; !$stop;) {
+        t3 = ++chars.index;
+        if (t3 >= t1)
+          throw H.wrapException(P.StateError$("incomplete VLQ value"));
+        if (t3 >= 0 && true) {
+          if (t3 < 0 || t3 >= t2.length)
+            return H.ioore(t2, t3);
+          char = t2[t3];
+        } else
+          char = _null;
+        t3 = $.$get$_digits();
+        if (!t3.containsKey$1(char))
+          throw H.wrapException(P.FormatException$("invalid character in VLQ encoding: " + H.S(char), _null, _null));
+        digit = t3.$index(0, char);
+        if (typeof digit !== "number")
+          return digit.$and();
+        $stop = (digit & 32) === 0;
+        result += C.JSInt_methods._shlPositive$1(digit & 31, shift);
+        shift += 5;
+      }
+      result0 = result >>> 1;
+      result = (result & 1) === 1 ? -result0 : result0;
+      if (result < $.$get$MIN_INT32() || result > $.$get$MAX_INT32())
+        throw H.wrapException(P.FormatException$("expected an encoded 32 bit int, but we got: " + result, _null, _null));
+      return result;
+    },
+    closure: function closure() {
+    },
+    internalBootstrapBrowserTest: function(getMain) {
+      var t2,
+        channel = S.RemoteListener_start(getMain, new L.internalBootstrapBrowserTest_closure(), false),
+        t1 = N.postMessageChannel();
+      t1.$ti._eval$1("StreamChannel<1>")._check(channel);
+      t1.get$stream(t1).pipe$1(channel._sink);
+      t2 = channel._streamController;
+      t2.toString;
+      new P._ControllerStream(t2, H._instanceType(t2)._eval$1("_ControllerStream<1>")).pipe$1(t1.get$sink());
+    },
+    internalBootstrapBrowserTest_closure: function internalBootstrapBrowserTest_closure() {
+    }
+  },
+  G = {StreamQueue: function StreamQueue(t0, t1, t2, t3) {
+      var _ = this;
+      _._stream_queue$_source = t0;
+      _._stream_queue$_subscription = null;
+      _._isClosed = _._isDone = false;
+      _._eventsReceived = 0;
+      _._eventQueue = t1;
+      _._requestQueue = t2;
+      _.$ti = t3;
+    }, StreamQueue__ensureListening_closure: function StreamQueue__ensureListening_closure(t0) {
+      this.$this = t0;
+    }, StreamQueue__ensureListening_closure1: function StreamQueue__ensureListening_closure1(t0) {
+      this.$this = t0;
+    }, StreamQueue__ensureListening_closure0: function StreamQueue__ensureListening_closure0(t0) {
+      this.$this = t0;
+    }, _EventRequest: function _EventRequest() {
+    }, _NextRequest: function _NextRequest(t0, t1) {
+      this._completer = t0;
+      this.$ti = t1;
+    }, _RestRequest: function _RestRequest(t0, t1, t2) {
+      this._completer = t0;
+      this._streamQueue = t1;
+      this.$ti = t2;
+    }, Parser: function Parser(t0) {
+      this._parser0$_scanner = t0;
+    }, Matcher: function Matcher() {
+    }, SourceMapSpan: function SourceMapSpan(t0, t1, t2, t3) {
+      var _ = this;
+      _.isIdentifier = t0;
+      _.start = t1;
+      _.end = t2;
+      _.text = t3;
+    },
+    SourceSpanFormatException$: function(message, span, _source) {
+      return new G.SourceSpanFormatException(message, span);
+    },
+    SourceSpanException: function SourceSpanException() {
+    },
+    SourceSpanFormatException: function SourceSpanFormatException(t0, t1) {
+      this._span_exception$_message = t0;
+      this._span_exception$_span = t1;
+    },
+    State: function State(t0, t1) {
+      this.status = t0;
+      this.result = t1;
+    },
+    Status: function Status(t0) {
+      this.name = t0;
+    },
+    Result0: function Result0(t0) {
+      this.name = t0;
+    },
+    expect: function(actual, matcher, reason) {
+      G._expect(true, matcher, null, reason, null, false);
+    },
+    _expect: function(actual, matcher, formatter, reason, skip, verbose) {
+      var matchState, e, trace, exception,
+        t1 = type$.Invoker;
+      if (t1._as($.Zone__current.$index(0, C.Symbol_cQL)) == null)
+        throw H.wrapException(P.StateError$("expect() may only be called within a test."));
+      t1 = t1._as($.Zone__current.$index(0, C.Symbol_cQL));
+      if (H.boolConversionCheck(H._asBoolNullable($.Zone__current.$index(0, t1._closableKey))) && t1._onCloseCompleter.future._state !== 0)
+        throw H.wrapException(K.ClosedException$());
+      matcher = M.wrapMatcher(matcher);
+      t1 = type$.dynamic;
+      matchState = P.LinkedHashMap_LinkedHashMap$_empty(t1, t1);
+      try {
+        if (matcher.matches$2(0, true, matchState)) {
+          t1 = P.Future_Future$sync(new G._expect_closure(), t1);
+          return t1;
+        }
+        t1 = reason;
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        trace = H.getTraceFromException(exception);
+        t1 = reason == null ? H.S(e) + " at " + H.S(trace) : reason;
+      }
+      G.fail(new G._expect_closure0().call$5(true, matcher, t1, matchState, false));
+    },
+    fail: function(message) {
+      return H.throwExpression(new G.TestFailure(message));
+    },
+    formatFailure: function(expected, actual, which, reason) {
+      var t2,
+        t1 = new E.StringDescription(new P.StringBuffer("")).addDescriptionOf$1(expected)._out._contents;
+      t1 = B.indent(t1.charCodeAt(0) == 0 ? t1 : t1, "Expected: ") + "\n";
+      t2 = new E.StringDescription(new P.StringBuffer("")).addDescriptionOf$1(true)._out._contents;
+      t2 = t1 + (B.indent(t2.charCodeAt(0) == 0 ? t2 : t2, "  Actual: ") + "\n");
+      t1 = which.length !== 0 ? t2 + (B.indent(which, "   Which: ") + "\n") : t2;
+      if (reason != null)
+        t1 += reason + "\n";
+      return t1.charCodeAt(0) == 0 ? t1 : t1;
+    },
+    TestFailure: function TestFailure(t0) {
+      this.message = t0;
+    },
+    _expect_closure0: function _expect_closure0() {
+    },
+    _expect_closure: function _expect_closure() {
+    },
+    method1: function() {
+      return $.x = $.x + 1;
+    },
+    method2: function() {
+      return $.x = $.x + 1;
+    },
+    main0: function() {
+      R.group("a group", new G.main_closure0());
+    },
+    main_closure0: function main_closure0() {
+    },
+    main__closure: function main__closure() {
+    }
+  },
+  T = {StreamSinkCompleter: function StreamSinkCompleter(t0, t1) {
+      this.sink = t0;
+      this.$ti = t1;
+    }, _CompleterSink: function _CompleterSink(t0) {
+      var _ = this;
+      _._destinationSink = _._stream_sink_completer$_doneCompleter = _._stream_sink_completer$_controller = null;
+      _.$ti = t0;
+    }, _CompleterSink__setDestinationSink_closure: function _CompleterSink__setDestinationSink_closure() {
+    }, SubscriptionStream: function SubscriptionStream(t0, t1) {
+      this._subscription_stream$_source = t0;
+      this.$ti = t1;
+    }, _CancelOnErrorSubscriptionWrapper: function _CancelOnErrorSubscriptionWrapper(t0, t1) {
+      this._stream_subscription$_source = t0;
+      this.$ti = t1;
+    }, _CancelOnErrorSubscriptionWrapper_onError_closure: function _CancelOnErrorSubscriptionWrapper_onError_closure(t0, t1) {
+      this.$this = t0;
+      this.handleError = t1;
+    }, _CancelOnErrorSubscriptionWrapper_onError__closure: function _CancelOnErrorSubscriptionWrapper_onError__closure(t0, t1, t2) {
+      this.handleError = t0;
+      this.error = t1;
+      this.stackTrace = t2;
+    }, Evaluator: function Evaluator(t0) {
+      this._semantics = t0;
+    },
+    parseJsonExtended: function(json, mapUrl, otherMaps) {
+      if (type$.List_dynamic._is(json))
+        return T.MappingBundle$fromJson(json, H._checkStringNullable(mapUrl));
+      return T.parseJson(type$.Map_dynamic_dynamic._as(json), null, null);
+    },
+    parseJson: function(map, mapUrl, otherMaps) {
+      var _s8_ = "sections";
+      if (!J.$eq$(map.$index(0, "version"), 3))
+        throw H.wrapException(P.ArgumentError$("unexpected source map version: " + H.S(map.$index(0, "version")) + ". Only version 3 is supported."));
+      if (map.containsKey$1(_s8_)) {
+        if (map.containsKey$1("mappings") || map.containsKey$1("sources") || map.containsKey$1("names"))
+          throw H.wrapException(P.FormatException$('map containing "sections" cannot contain "mappings", "sources", or "names".', null, null));
+        return T.MultiSectionMapping$fromJson(type$.List_dynamic._check(map.$index(0, _s8_)), otherMaps, mapUrl);
+      }
+      return T.SingleMapping$fromJson(map, mapUrl);
+    },
+    MultiSectionMapping$fromJson: function(sections, otherMaps, mapUrl) {
+      var t1 = type$.JSArray_int;
+      t1 = new T.MultiSectionMapping(H.setRuntimeTypeInfo([], t1), H.setRuntimeTypeInfo([], t1), H.setRuntimeTypeInfo([], type$.JSArray_Mapping));
+      t1.MultiSectionMapping$fromJson$3$mapUrl(sections, otherMaps, mapUrl);
+      return t1;
+    },
+    MappingBundle$fromJson: function(json, mapUrl) {
+      var t1 = new T.MappingBundle(P.LinkedHashMap_LinkedHashMap$_empty(type$.String, type$.SingleMapping));
+      t1.MappingBundle$fromJson$2$mapUrl(json, mapUrl);
+      return t1;
+    },
+    SingleMapping$fromJson: function(map, mapUrl) {
+      var t5, t6, t7, t8,
+        t1 = H._checkStringNullable(map.$index(0, "file")),
+        t2 = type$.Iterable_dynamic,
+        t3 = type$.String,
+        t4 = P.List_List$from(t2._check(map.$index(0, "sources")), true, t3);
+      t2 = P.List_List$from(t2._check(map.$index(0, "names")), true, t3);
+      t5 = H._checkIntNullable(J.get$length$asx(map.$index(0, "sources")));
+      if (typeof t5 !== "number")
+        return H.iae(t5);
+      t5 = new Array(t5);
+      t5.fixed$length = Array;
+      t5 = H.setRuntimeTypeInfo(t5, type$.JSArray_SourceFile);
+      t6 = H._checkStringNullable(map.$index(0, "sourceRoot"));
+      t7 = H.setRuntimeTypeInfo([], type$.JSArray_TargetLineEntry);
+      t8 = typeof mapUrl == "string" ? P.Uri_parse(mapUrl) : mapUrl;
+      t3 = new T.SingleMapping(t4, t2, t5, t7, t1, t6, type$.Uri._check(t8), P.LinkedHashMap_LinkedHashMap$_empty(t3, type$.dynamic));
+      t3.SingleMapping$fromJson$2$mapUrl(map, mapUrl);
+      return t3;
+    },
+    Mapping: function Mapping() {
+    },
+    MultiSectionMapping: function MultiSectionMapping(t0, t1, t2) {
+      this._lineStart = t0;
+      this._columnStart = t1;
+      this._maps = t2;
+    },
+    MappingBundle: function MappingBundle(t0) {
+      this._mappings = t0;
+    },
+    SingleMapping: function SingleMapping(t0, t1, t2, t3, t4, t5, t6, t7) {
+      var _ = this;
+      _.urls = t0;
+      _.names = t1;
+      _.files = t2;
+      _.lines = t3;
+      _.targetUrl = t4;
+      _.sourceRoot = t5;
+      _._parser$_mapUrl = t6;
+      _.extensions = t7;
+    },
+    SingleMapping$fromJson_closure: function SingleMapping$fromJson_closure(t0) {
+      this.$this = t0;
+    },
+    SingleMapping__findLine_closure: function SingleMapping__findLine_closure(t0) {
+      this.line = t0;
+    },
+    SingleMapping__findColumn_closure: function SingleMapping__findColumn_closure(t0) {
+      this.column = t0;
+    },
+    TargetLineEntry: function TargetLineEntry(t0, t1) {
+      this.line = t0;
+      this.entries = t1;
+    },
+    TargetEntry: function TargetEntry(t0, t1, t2, t3, t4) {
+      var _ = this;
+      _.column = t0;
+      _.sourceUrlId = t1;
+      _.sourceLine = t2;
+      _.sourceColumn = t3;
+      _.sourceNameId = t4;
+    },
+    _MappingTokenizer: function _MappingTokenizer(t0, t1) {
+      this._internal = t0;
+      this._parser$_length = t1;
+      this.index = -1;
+    },
+    _TokenKind: function _TokenKind(t0, t1, t2) {
+      this.isNewLine = t0;
+      this.isNewSegment = t1;
+      this.isEof = t2;
+    },
+    LazyTrace: function LazyTrace(t0) {
+      this._lazy_trace$_thunk = t0;
+      this._lazy_trace$_inner = null;
+    },
+    LazyTrace_foldFrames_closure: function LazyTrace_foldFrames_closure(t0, t1, t2) {
+      this.$this = t0;
+      this.predicate = t1;
+      this.terse = t2;
+    },
+    RuntimeSelection: function RuntimeSelection() {
+    }
+  },
+  X = {BooleanSelector: function BooleanSelector() {
+    }, All: function All() {
+    },
+    ParsedPath_ParsedPath$parse: function(path, style) {
+      var t1, parts, separators, start, i,
+        root = style.getRoot$1(path);
+      style.isRootRelative$1(path);
+      if (root != null)
+        path = J.substring$1$s(path, root.length);
+      t1 = type$.JSArray_String;
+      parts = H.setRuntimeTypeInfo([], t1);
+      separators = H.setRuntimeTypeInfo([], t1);
+      t1 = path.length;
+      if (t1 !== 0 && style.isSeparator$1(C.JSString_methods._codeUnitAt$1(path, 0))) {
+        if (0 >= t1)
+          return H.ioore(path, 0);
+        C.JSArray_methods.add$1(separators, path[0]);
+        start = 1;
+      } else {
+        C.JSArray_methods.add$1(separators, "");
+        start = 0;
+      }
+      for (i = start; i < t1; ++i)
+        if (style.isSeparator$1(C.JSString_methods._codeUnitAt$1(path, i))) {
+          C.JSArray_methods.add$1(parts, C.JSString_methods.substring$2(path, start, i));
+          C.JSArray_methods.add$1(separators, path[i]);
+          start = i + 1;
+        }
+      if (start < t1) {
+        C.JSArray_methods.add$1(parts, C.JSString_methods.substring$1(path, start));
+        C.JSArray_methods.add$1(separators, "");
+      }
+      return new X.ParsedPath(style, root, parts, separators);
+    },
+    ParsedPath: function ParsedPath(t0, t1, t2, t3) {
+      var _ = this;
+      _.style = t0;
+      _.root = t1;
+      _.parts = t2;
+      _.separators = t3;
+    },
+    ParsedPath_normalize_closure: function ParsedPath_normalize_closure(t0) {
+      this.$this = t0;
+    },
+    PathException$: function(message) {
+      return new X.PathException(message);
+    },
+    PathException: function PathException(t0) {
+      this.message = t0;
+    },
+    SourceSpanWithContext$: function(start, end, text, _context) {
+      var t1 = new X.SourceSpanWithContext(_context, start, end, text);
+      t1.SourceSpanBase$3(start, end, text);
+      if (!C.JSString_methods.contains$1(_context, text))
+        H.throwExpression(P.ArgumentError$('The context line "' + _context + '" must contain "' + text + '".'));
+      if (B.findLineStart(_context, text, start.get$column()) == null)
+        H.throwExpression(P.ArgumentError$('The span text "' + text + '" must start at column ' + (start.get$column() + 1) + ' in a line within "' + _context + '".'));
+      return t1;
+    },
+    SourceSpanWithContext: function SourceSpanWithContext(t0, t1, t2, t3) {
+      var _ = this;
+      _._context = t0;
+      _.start = t1;
+      _.end = t2;
+      _.text = t3;
+    },
+    LazyChain: function LazyChain(t0) {
+      this._thunk = t0;
+      this._lazy_chain$_inner = null;
+    },
+    LazyChain_foldFrames_closure: function LazyChain_foldFrames_closure(t0, t1, t2) {
+      this.$this = t0;
+      this.predicate = t1;
+      this.terse = t2;
+    },
+    LazyChain_toTrace_closure: function LazyChain_toTrace_closure(t0) {
+      this.$this = t0;
+    },
+    StringScanner: function StringScanner() {
+    },
+    Declarer$: function(collectTraces, metadata, noRetry, platformVariables) {
+      var _null = null,
+        t1 = metadata == null ? O.Metadata_Metadata(_null, _null, _null, _null, _null, _null, _null, _null, _null, _null) : metadata,
+        t2 = platformVariables == null ? C.C_EmptyUnmodifiableSet : platformVariables,
+        t3 = type$.JSArray_of_dynamic_Function,
+        t4 = type$.JSArray_GroupEntry;
+      return new X.Declarer(_null, _null, t1, t2, _null, collectTraces, noRetry, H.setRuntimeTypeInfo([], t3), H.setRuntimeTypeInfo([], t3), H.setRuntimeTypeInfo([], t3), new R.Timeout(P.Duration$(0, 12), _null), H.setRuntimeTypeInfo([], t3), H.setRuntimeTypeInfo([], t4), H.setRuntimeTypeInfo([], t4));
+    },
+    Declarer: function Declarer(t0, t1, t2, t3, t4, t5, t6, t7, t8, t9, t10, t11, t12, t13) {
+      var _ = this;
+      _._declarer$_parent = t0;
+      _._declarer$_name = t1;
+      _._metadata = t2;
+      _._platformVariables = t3;
+      _._declarer$_trace = t4;
+      _._collectTraces = t5;
+      _._noRetry = t6;
+      _._setUps = t7;
+      _._tearDowns = t8;
+      _._setUpAlls = t9;
+      _._timeout = t10;
+      _._tearDownAlls = t11;
+      _._entries = t12;
+      _._built = false;
+      _._soloEntries = t13;
+    },
+    Declarer_test_closure: function Declarer_test_closure(t0, t1) {
+      this.$this = t0;
+      this.body = t1;
+    },
+    Declarer_test__closure: function Declarer_test__closure(t0, t1) {
+      this.$this = t0;
+      this.body = t1;
+    },
+    Declarer_test___closure: function Declarer_test___closure(t0, t1) {
+      this.$this = t0;
+      this.body = t1;
+    },
+    Declarer_group_closure: function Declarer_group_closure(t0) {
+      this.body = t0;
+    },
+    Declarer_build_closure: function Declarer_build_closure(t0) {
+      this.$this = t0;
+    },
+    Declarer__runSetUps_closure: function Declarer__runSetUps_closure() {
+    },
+    Declarer__tearDownAll_closure: function Declarer__tearDownAll_closure(t0) {
+      this.$this = t0;
+    },
+    Declarer__tearDownAll__closure: function Declarer__tearDownAll__closure(t0) {
+      this.$this = t0;
+    },
+    Declarer__tearDownAll___closure: function Declarer__tearDownAll___closure(t0) {
+      this.$this = t0;
+    },
+    PrintSink: function PrintSink(t0) {
+      this._print_sink$_buffer = t0;
+    }
+  },
+  U = {
+    _expandSafe: function(start, end) {
+      if (start == null || end == null)
+        return null;
+      if (start.file !== end.file)
+        return null;
+      return start.expand$1(0, end);
+    },
+    VariableNode: function VariableNode(t0, t1) {
+      this.span = t0;
+      this.name = t1;
+    },
+    NotNode: function NotNode(t0, t1) {
+      this.span = t0;
+      this.child = t1;
+    },
+    OrNode: function OrNode(t0, t1) {
+      this.left = t0;
+      this.right = t1;
+    },
+    AndNode: function AndNode(t0, t1) {
+      this.left = t0;
+      this.right = t1;
+    },
+    ConditionalNode: function ConditionalNode(t0, t1, t2) {
+      this.condition = t0;
+      this.whenTrue = t1;
+      this.whenFalse = t2;
+    },
+    Highlighter__normalizeNewlines: function(span) {
+      var t1, endOffset, i, t2, t3, t4,
+        text = span.get$text();
+      if (!C.JSString_methods.contains$1(text, "\r\n"))
+        return span;
+      t1 = span.get$end();
+      endOffset = t1.get$offset(t1);
+      for (t1 = text.length - 1, i = 0; i < t1; ++i)
+        if (C.JSString_methods._codeUnitAt$1(text, i) === 13 && C.JSString_methods._codeUnitAt$1(text, i + 1) === 10)
+          --endOffset;
+      t1 = span.get$start();
+      t2 = span.get$sourceUrl();
+      t3 = span.get$end().get$line();
+      t2 = V.SourceLocation$(endOffset, span.get$end().get$column(), t3, t2);
+      t3 = H.stringReplaceAllUnchecked(text, "\r\n", "\n");
+      t4 = span.get$context();
+      return X.SourceSpanWithContext$(t1, t2, t3, H.stringReplaceAllUnchecked(t4, "\r\n", "\n"));
+    },
+    Highlighter__normalizeTrailingNewline: function(span) {
+      var context, text, start, end, t1, t2, t3;
+      if (!C.JSString_methods.endsWith$1(span.get$context(), "\n"))
+        return span;
+      if (C.JSString_methods.endsWith$1(span.get$text(), "\n\n"))
+        return span;
+      context = C.JSString_methods.substring$2(span.get$context(), 0, span.get$context().length - 1);
+      text = span.get$text();
+      start = span.get$start();
+      end = span.get$end();
+      if (C.JSString_methods.endsWith$1(span.get$text(), "\n")) {
+        t1 = B.findLineStart(span.get$context(), span.get$text(), span.get$start().get$column());
+        t2 = span.get$start().get$column();
+        if (typeof t1 !== "number")
+          return t1.$add();
+        t2 = t1 + t2 + span.get$length(span) === span.get$context().length;
+        t1 = t2;
+      } else
+        t1 = false;
+      if (t1) {
+        text = C.JSString_methods.substring$2(span.get$text(), 0, span.get$text().length - 1);
+        t1 = span.get$end();
+        t1 = t1.get$offset(t1);
+        t2 = span.get$sourceUrl();
+        t3 = span.get$end().get$line();
+        if (typeof t3 !== "number")
+          return t3.$sub();
+        end = V.SourceLocation$(t1 - 1, U.Highlighter__lastLineLength(text), t3 - 1, t2);
+        t1 = span.get$start();
+        t1 = t1.get$offset(t1);
+        t2 = span.get$end();
+        start = t1 === t2.get$offset(t2) ? end : span.get$start();
+      }
+      return X.SourceSpanWithContext$(start, end, text, context);
+    },
+    Highlighter__normalizeEndOfLine: function(span) {
+      var text, t1, t2, t3, t4;
+      if (span.get$end().get$column() !== 0)
+        return span;
+      if (span.get$end().get$line() == span.get$start().get$line())
+        return span;
+      text = C.JSString_methods.substring$2(span.get$text(), 0, span.get$text().length - 1);
+      t1 = span.get$start();
+      t2 = span.get$end();
+      t2 = t2.get$offset(t2);
+      t3 = span.get$sourceUrl();
+      t4 = span.get$end().get$line();
+      if (typeof t4 !== "number")
+        return t4.$sub();
+      return X.SourceSpanWithContext$(t1, V.SourceLocation$(t2 - 1, U.Highlighter__lastLineLength(text), t4 - 1, t3), text, span.get$context());
+    },
+    Highlighter__lastLineLength: function(text) {
+      var t1 = text.length;
+      if (t1 === 0)
+        return 0;
+      if (C.JSString_methods.codeUnitAt$1(text, t1 - 1) === 10)
+        return t1 === 1 ? 0 : t1 - C.JSString_methods.lastIndexOf$2(text, "\n", t1 - 2) - 1;
+      else
+        return t1 - C.JSString_methods.lastIndexOf$1(text, "\n") - 1;
+    },
+    Highlighter: function Highlighter(t0, t1, t2, t3, t4) {
+      var _ = this;
+      _._span = t0;
+      _._color = t1;
+      _._multiline = t2;
+      _._paddingBeforeSidebar = t3;
+      _._highlighter$_buffer = t4;
+    },
+    Highlighter__writeFirstLine_closure: function Highlighter__writeFirstLine_closure(t0, t1) {
+      this.$this = t0;
+      this.line = t1;
+    },
+    Highlighter__writeFirstLine_closure0: function Highlighter__writeFirstLine_closure0(t0, t1) {
+      this.$this = t0;
+      this.textInside = t1;
+    },
+    Highlighter__writeFirstLine_closure1: function Highlighter__writeFirstLine_closure1(t0, t1) {
+      this._box_0 = t0;
+      this.$this = t1;
+    },
+    Highlighter__writeFirstLine_closure2: function Highlighter__writeFirstLine_closure2(t0, t1) {
+      this._box_0 = t0;
+      this.$this = t1;
+    },
+    Highlighter__writeIntermediateLines_closure: function Highlighter__writeIntermediateLines_closure(t0, t1) {
+      this.$this = t0;
+      this.line = t1;
+    },
+    Highlighter__writeLastLine_closure: function Highlighter__writeLastLine_closure(t0, t1) {
+      this.$this = t0;
+      this.line = t1;
+    },
+    Highlighter__writeLastLine_closure0: function Highlighter__writeLastLine_closure0(t0, t1) {
+      this.$this = t0;
+      this.textInside = t1;
+    },
+    Highlighter__writeLastLine_closure1: function Highlighter__writeLastLine_closure1(t0, t1) {
+      this._box_0 = t0;
+      this.$this = t1;
+    },
+    Highlighter__writeSidebar_closure: function Highlighter__writeSidebar_closure(t0, t1, t2) {
+      this.$this = t0;
+      this.line = t1;
+      this.end = t2;
+    },
+    Chain_capture: function(callback, errorZone, when, $T) {
+      var t1, spec, _null = null;
+      if (!when)
+        return P.runZoned(callback, _null, _null, _null, $T);
+      if (typeof WeakMap == "function")
+        t1 = new WeakMap();
+      else {
+        t1 = $.Expando__keyCount;
+        $.Expando__keyCount = t1 + 1;
+        t1 = "expando$key$" + t1;
+      }
+      spec = new O.StackZoneSpecification(new P.Expando(t1, "stack chains", type$.Expando__Node), _null, false);
+      t1 = type$.dynamic;
+      return P.runZoned(new U.Chain_capture_closure(callback, $T), _null, P._ZoneSpecification$(_null, _null, spec.get$_stack_zone_specification$_errorCallback(), _null, _null, _null, spec.get$_stack_zone_specification$_registerBinaryCallback(), spec.get$_stack_zone_specification$_registerCallback(), spec.get$_stack_zone_specification$_registerUnaryCallback(), _null, _null, _null, _null), P.LinkedHashMap_LinkedHashMap$_literal([$.$get$_specKey(), spec, $.$get$StackZoneSpecification_disableKey(), false], t1, t1), $T);
+    },
+    Chain_Chain$current: function() {
+      var t1 = $.Zone__current,
+        t2 = $.$get$_specKey(),
+        t3 = type$.StackZoneSpecification;
+      if (t3._check(t1.$index(0, t2)) != null) {
+        t1 = t3._check($.Zone__current.$index(0, t2));
+        t2 = t1._currentTrace$1(3);
+        t1 = t1._currentNode;
+        return new O._Node(Y.Trace_Trace$from(t2), t1).toChain$0();
+      }
+      return new X.LazyChain(new U.Chain_Chain$current_closure(U.Chain_Chain$forTrace(P.StackTrace_current()), 0));
+    },
+    Chain_Chain$forTrace: function(trace) {
+      var t1, t2, t3;
+      if (type$.Chain._is(trace))
+        return trace;
+      t1 = $.Zone__current;
+      t2 = $.$get$_specKey();
+      t3 = type$.StackZoneSpecification;
+      if (t3._check(t1.$index(0, t2)) != null)
+        return t3._check($.Zone__current.$index(0, t2)).chainFor$1(trace);
+      t1 = type$.Trace;
+      if (t1._is(trace))
+        return new U.Chain(P.List_List$unmodifiable(H.setRuntimeTypeInfo([trace], type$.JSArray_Trace), t1));
+      return new X.LazyChain(new U.Chain_Chain$forTrace_closure(trace));
+    },
+    Chain_Chain$parse: function(chain) {
+      var _s26_ = "<asynchronous suspension>\n",
+        _s51_ = "===== asynchronous gap ===========================\n";
+      if (chain.length === 0)
+        return new U.Chain(P.List_List$unmodifiable(H.setRuntimeTypeInfo([], type$.JSArray_Trace), type$.Trace));
+      if (C.JSString_methods.contains$1(chain, _s26_))
+        return new U.Chain(P.List_List$unmodifiable(new H.MappedListIterable(H.setRuntimeTypeInfo(chain.split(_s26_), type$.JSArray_String), type$.Trace_Function_String._check(new U.Chain_Chain$parse_closure()), type$.MappedListIterable_String_Trace), type$.Trace));
+      if (!C.JSString_methods.contains$1(chain, _s51_))
+        return new U.Chain(P.List_List$unmodifiable(H.setRuntimeTypeInfo([Y.Trace_Trace$parse(chain)], type$.JSArray_Trace), type$.Trace));
+      return new U.Chain(P.List_List$unmodifiable(new H.MappedListIterable(H.setRuntimeTypeInfo(chain.split(_s51_), type$.JSArray_String), type$.Trace_Function_String._check(new U.Chain_Chain$parse_closure0()), type$.MappedListIterable_String_Trace), type$.Trace));
+    },
+    Chain: function Chain(t0) {
+      this.traces = t0;
+    },
+    Chain_capture_closure: function Chain_capture_closure(t0, t1) {
+      this.callback = t0;
+      this.T = t1;
+    },
+    Chain_Chain$current_closure: function Chain_Chain$current_closure(t0, t1) {
+      this.chain = t0;
+      this.level = t1;
+    },
+    Chain_Chain$forTrace_closure: function Chain_Chain$forTrace_closure(t0) {
+      this.trace = t0;
+    },
+    Chain_Chain$parse_closure: function Chain_Chain$parse_closure() {
+    },
+    Chain_Chain$parse_closure0: function Chain_Chain$parse_closure0() {
+    },
+    Chain_foldFrames_closure: function Chain_foldFrames_closure(t0, t1) {
+      this.predicate = t0;
+      this.terse = t1;
+    },
+    Chain_foldFrames_closure0: function Chain_foldFrames_closure0(t0) {
+      this.terse = t0;
+    },
+    Chain_toTrace_closure: function Chain_toTrace_closure() {
+    },
+    Chain_toString_closure0: function Chain_toString_closure0() {
+    },
+    Chain_toString__closure0: function Chain_toString__closure0() {
+    },
+    Chain_toString_closure: function Chain_toString_closure(t0) {
+      this.longest = t0;
+    },
+    Chain_toString__closure: function Chain_toString__closure(t0) {
+      this.longest = t0;
+    },
+    Invoker_guard: function(callback, $T) {
+      var _null = null;
+      return P.runZoned(callback, _null, P._ZoneSpecification$(_null, _null, _null, _null, new U.Invoker_guard_closure(), _null, _null, _null, _null, _null, _null, _null, _null), _null, $T);
+    },
+    LocalTest: function LocalTest(t0, t1, t2, t3, t4, t5) {
+      var _ = this;
+      _.name = t0;
+      _.metadata = t1;
+      _.trace = t2;
+      _.isScaffoldAll = t3;
+      _._body = t4;
+      _._guarded = t5;
+    },
+    Invoker: function Invoker(t0, t1, t2, t3, t4, t5, t6) {
+      var _ = this;
+      _._invoker$_controller = null;
+      _._guarded = t0;
+      _._closableKey = t1;
+      _._onCloseCompleter = t2;
+      _._outstandingCallbackZones = t3;
+      _._counterKey = t4;
+      _._runCount = 0;
+      _._timeoutTimer = _._invokerZone = null;
+      _._invoker$_tearDowns = t5;
+      _._printsOnFailure = t6;
+    },
+    Invoker_guard_closure: function Invoker_guard_closure() {
+    },
+    Invoker_guard__closure: function Invoker_guard__closure(t0, t1, t2, t3) {
+      var _ = this;
+      _.invoker = t0;
+      _.zone = t1;
+      _.error = t2;
+      _.stackTrace = t3;
+    },
+    Invoker_waitForOutstandingCallbacks_closure: function Invoker_waitForOutstandingCallbacks_closure(t0, t1, t2, t3) {
+      var _ = this;
+      _._box_0 = t0;
+      _.$this = t1;
+      _.fn = t2;
+      _.counter = t3;
+    },
+    Invoker_waitForOutstandingCallbacks_closure0: function Invoker_waitForOutstandingCallbacks_closure0(t0, t1) {
+      this._box_0 = t0;
+      this.$this = t1;
+    },
+    Invoker_heartbeat_message: function Invoker_heartbeat_message(t0) {
+      this.timeout = t0;
+    },
+    Invoker_heartbeat_closure: function Invoker_heartbeat_closure(t0, t1, t2) {
+      this.$this = t0;
+      this.message = t1;
+      this.timeout = t2;
+    },
+    Invoker_heartbeat__closure: function Invoker_heartbeat__closure(t0, t1, t2) {
+      this.$this = t0;
+      this.message = t1;
+      this.timeout = t2;
+    },
+    Invoker__handleError_closure: function Invoker__handleError_closure(t0) {
+      this._box_0 = t0;
+    },
+    Invoker__handleError_closure0: function Invoker__handleError_closure0(t0) {
+      this.$this = t0;
+    },
+    Invoker__onRun_closure: function Invoker__onRun_closure(t0, t1) {
+      this.$this = t0;
+      this.outstandingCallbacksForBody = t1;
+    },
+    Invoker__onRun__closure: function Invoker__onRun__closure(t0, t1) {
+      this.$this = t0;
+      this.outstandingCallbacksForBody = t1;
+    },
+    Invoker__onRun___closure: function Invoker__onRun___closure(t0) {
+      this.$this = t0;
+    },
+    Invoker__onRun____closure: function Invoker__onRun____closure(t0) {
+      this.$this = t0;
+    },
+    Invoker__onRun___closure0: function Invoker__onRun___closure0(t0) {
+      this.$this = t0;
+    },
+    _AsyncCounter: function _AsyncCounter(t0) {
+      this._count = 1;
+      this._invoker$_completer = t0;
+    },
+    StackTraceFormatter: function StackTraceFormatter(t0, t1) {
+      this._mapper = null;
+      this._except = t0;
+      this._only = t1;
+    },
+    StackTraceFormatter_formatStackTrace_closure: function StackTraceFormatter_formatStackTrace_closure(t0) {
+      this.$this = t0;
+    },
+    Suite__filterGroup: function(group, platform) {
+      var t1, _null = null,
+        filtered = group.forPlatform$1(platform);
+      if (filtered != null)
+        return filtered;
+      t1 = P.List_List$unmodifiable(H.setRuntimeTypeInfo([], type$.JSArray_GroupEntry), type$.GroupEntry);
+      return new O.Group(_null, group.metadata, _null, t1, _null, _null);
+    },
+    Suite: function Suite(t0, t1, t2) {
+      this.platform = t0;
+      this.path = t1;
+      this.group = t2;
+    },
+    SuiteConfiguration__list: function(input, $T) {
+      return null;
+    },
+    SuiteConfiguration__map: function(input, $K, $V) {
+      return C.Map_empty1;
+    },
+    SuiteConfiguration: function SuiteConfiguration() {
+    },
+    RemoteException_serialize: function(error, stackTrace) {
+      var exception, supertype, t1, message = null;
+      if (typeof error == "string")
+        message = error;
+      else
+        try {
+          message = J.toString$0$(J.get$message$x(error));
+        } catch (exception) {
+          if (!type$.NoSuchMethodError._is(H.unwrapException(exception)))
+            throw exception;
+        }
+      supertype = error instanceof G.TestFailure ? "TestFailure" : null;
+      t1 = J.getInterceptor$(error);
+      return P.LinkedHashMap_LinkedHashMap$_literal(["message", message, "type", t1.get$runtimeType(error).toString$0(0), "supertype", supertype, "toString", t1.toString$0(error), "stackChain", J.toString$0$(U.Chain_Chain$forTrace(stackTrace))], type$.String, type$.dynamic);
+    }
+  },
+  R = {IntersectionSelector: function IntersectionSelector(t0, t1) {
+      this._selector1 = t0;
+      this._selector2 = t1;
+    }, StreamChannel: function StreamChannel() {
+    }, _StreamChannel: function _StreamChannel(t0, t1, t2) {
+      this.stream = t0;
+      this.sink = t1;
+      this.$ti = t2;
+    }, StreamChannelMixin: function StreamChannelMixin() {
+    }, Timeout: function Timeout(t0, t1) {
+      this.duration = t0;
+      this.scaleFactor = t1;
+    }, ExpandedReporter: function ExpandedReporter(t0, t1, t2, t3, t4, t5, t6, t7, t8, t9, t10, t11, t12) {
+      var _ = this;
+      _._expanded$_color = t0;
+      _._green = t1;
+      _._red = t2;
+      _._yellow = t3;
+      _._gray = t4;
+      _._bold = t5;
+      _._noColor = t6;
+      _._engine = t7;
+      _._printPath = t8;
+      _._printPlatform = t9;
+      _._stopwatch = t10;
+      _._lastProgressSuffix = _._lastProgressMessage = _._lastProgressFailed = _._lastProgressSkipped = _._lastProgressPassed = null;
+      _._subscriptions = t11;
+      _._expanded$_sink = t12;
+    }, ExpandedReporter__onTestStarted_closure: function ExpandedReporter__onTestStarted_closure(t0, t1) {
+      this.$this = t0;
+      this.liveTest = t1;
+    }, ExpandedReporter__onTestStarted_closure0: function ExpandedReporter__onTestStarted_closure0(t0, t1) {
+      this.$this = t0;
+      this.liveTest = t1;
+    }, ExpandedReporter__onTestStarted_closure1: function ExpandedReporter__onTestStarted_closure1(t0, t1) {
+      this.$this = t0;
+      this.liveTest = t1;
+    },
+    _declarer: function() {
+      var t1,
+        declarer = type$.Declarer._as($.Zone__current.$index(0, C.Symbol_Drw));
+      if (declarer != null)
+        return declarer;
+      t1 = $._globalDeclarer;
+      if (t1 != null)
+        return t1;
+      $._globalDeclarer = X.Declarer$(false, null, false, null);
+      P.scheduleMicrotask(new R._declarer_closure());
+      return $._globalDeclarer;
+    },
+    test: function(description, body) {
+      var _null = null;
+      R._declarer().test$9$onPlatform$retry$skip$solo$tags$testOn$timeout(description, body, _null, _null, _null, false, _null, _null, _null);
+      return;
+    },
+    group: function(description, body) {
+      var _null = null;
+      R._declarer().group$9$onPlatform$retry$skip$solo$tags$testOn$timeout(description, body, _null, _null, _null, false, _null, _null, _null);
+      return;
+    },
+    _declarer_closure: function _declarer_closure() {
+    },
+    _declarer__closure: function _declarer__closure(t0) {
+      this.engine = t0;
+    },
+    main: function() {
+      L.internalBootstrapBrowserTest(new R.main_closure());
+    },
+    main_closure: function main_closure() {
+    }
+  },
+  B = {RecursiveVisitor: function RecursiveVisitor() {
+    }, InternalStyle: function InternalStyle() {
+    },
+    StreamChannelController$: function(allowForeignErrors, sync, $T) {
+      var _null = null,
+        t1 = new B.StreamChannelController($T._eval$1("StreamChannelController<0>")),
+        localToForeignController = P.StreamController_StreamController(_null, _null, true, $T),
+        foreignToLocalController = P.StreamController_StreamController(_null, _null, true, $T),
+        t2 = H._instanceType(foreignToLocalController),
+        t3 = H._instanceType(localToForeignController);
+      t1.set$_local(K.GuaranteeChannel$(new P._ControllerStream(foreignToLocalController, t2._eval$1("_ControllerStream<1>")), new P._StreamSinkWrapper(localToForeignController, t3._eval$1("_StreamSinkWrapper<1>")), true, $T));
+      t1.set$_foreign(K.GuaranteeChannel$(new P._ControllerStream(localToForeignController, t3._eval$1("_ControllerStream<1>")), new P._StreamSinkWrapper(foreignToLocalController, t2._eval$1("_StreamSinkWrapper<1>")), allowForeignErrors, $T));
+      return t1;
+    },
+    StreamChannelController: function StreamChannelController(t0) {
+      this._foreign = this._local = null;
+      this.$ti = t0;
+    },
+    Runtime_Runtime$deserialize: function(serialized) {
+      var $parent, t1, t2, t3,
+        _s10_ = "identifier";
+      if (typeof serialized == "string")
+        return C.JSArray_methods.firstWhere$1(C.List_m7e, new B.Runtime_Runtime$deserialize_closure(serialized));
+      type$.Map_dynamic_dynamic._as(serialized);
+      $parent = serialized.$index(0, "parent");
+      if ($parent != null) {
+        t1 = H._asStringNullable(serialized.$index(0, "name"));
+        t2 = H._asStringNullable(serialized.$index(0, _s10_));
+        t3 = B.Runtime_Runtime$deserialize($parent);
+        return new B.Runtime(t1, t2, t3, t3.isDartVM, t3.isBrowser, t3.isJS, t3.isBlink, t3.isHeadless);
+      }
+      return new B.Runtime(H._asStringNullable(serialized.$index(0, "name")), H._asStringNullable(serialized.$index(0, _s10_)), null, H._asBoolNullable(serialized.$index(0, "isDartVM")), H._asBoolNullable(serialized.$index(0, "isBrowser")), H._asBoolNullable(serialized.$index(0, "isJS")), H._asBoolNullable(serialized.$index(0, "isBlink")), H._asBoolNullable(serialized.$index(0, "isHeadless")));
+    },
+    Runtime: function Runtime(t0, t1, t2, t3, t4, t5, t6, t7) {
+      var _ = this;
+      _.name = t0;
+      _.identifier = t1;
+      _.parent = t2;
+      _.isDartVM = t3;
+      _.isBrowser = t4;
+      _.isJS = t5;
+      _.isBlink = t6;
+      _.isHeadless = t7;
+    },
+    Runtime_Runtime$deserialize_closure: function Runtime_Runtime$deserialize_closure(t0) {
+      this.serialized = t0;
+    },
+    indent: function(string, first) {
+      var size = first == null ? 2 : first.length;
+      return B.prefixLines(string, C.JSString_methods.$mul(" ", size), first);
+    },
+    toSentence: function(iter) {
+      var result,
+        t1 = iter.length;
+      if (t1 === 1)
+        return J.toString$0$(C.JSArray_methods.get$first(iter));
+      result = H.SubListIterable$(iter, 0, t1 - 1, H._arrayInstanceType(iter)._precomputed1).join$1(0, ", ");
+      if (iter.length > 2)
+        result += ",";
+      return result + " and " + H.S(C.JSArray_methods.get$last(iter));
+    },
+    pluralize: function($name, number) {
+      if (number === 1)
+        return $name;
+      return $name + "s";
+    },
+    prefixLines: function(text, prefix, first) {
+      var single, lines, t1, t2;
+      if (first == null)
+        first = prefix;
+      single = first;
+      lines = H.setRuntimeTypeInfo(text.split("\n"), type$.JSArray_String);
+      if (lines.length === 1)
+        return single + text;
+      t1 = first + H.S(C.JSArray_methods.get$first(lines)) + "\n";
+      for (t2 = H.SubListIterable$(lines, 1, null, type$.String).take$1(0, lines.length - 2), t2 = new H.ListIterator(t2, t2.get$length(t2), t2.$ti._eval$1("ListIterator<ListIterable.E>")); t2.moveNext$0();)
+        t1 += prefix + H.S(t2.__internal$_current) + "\n";
+      t1 += prefix + H.S(C.JSArray_methods.get$last(lines));
+      return t1.charCodeAt(0) == 0 ? t1 : t1;
+    },
+    closure0: function closure0() {
+    },
+    LiveSuiteController$: function(_suite) {
+      var t1 = $.Zone__current,
+        t2 = H.setRuntimeTypeInfo([], type$.JSArray_dynamic),
+        t3 = $.Zone__current,
+        t4 = type$._Future_dynamic,
+        t5 = type$._AsyncCompleter_dynamic,
+        t6 = type$.LiveTest;
+      t5 = new B.LiveSuiteController(_suite, new F.FutureGroup(new P._AsyncCompleter(new P._Future(t1, type$._Future_List_dynamic), type$._AsyncCompleter_List_dynamic), t2, type$.FutureGroup_dynamic), new P._AsyncCompleter(new P._Future(t3, t4), t5), new P._SyncBroadcastStreamController(null, null, type$._SyncBroadcastStreamController_LiveTest), P.LinkedHashSet_LinkedHashSet$_empty(t6), P.LinkedHashSet_LinkedHashSet$_empty(t6), P.LinkedHashSet_LinkedHashSet$_empty(t6), new S.AsyncMemoizer(new P._AsyncCompleter(new P._Future(t3, t4), t5), type$.AsyncMemoizer_dynamic));
+      t5.LiveSuiteController$1(_suite);
+      return t5;
+    },
+    _LiveSuite: function _LiveSuite(t0) {
+      this._live_suite_controller$_controller = t0;
+    },
+    LiveSuiteController: function LiveSuiteController(t0, t1, t2, t3, t4, t5, t6, t7) {
+      var _ = this;
+      _._liveSuite = null;
+      _._live_suite_controller$_suite = t0;
+      _._onCompleteGroup = t1;
+      _._live_suite_controller$_onCloseCompleter = t2;
+      _._onTestStartedController = t3;
+      _._passed = t4;
+      _._skipped = t5;
+      _._failed = t6;
+      _._live_suite_controller$_active = null;
+      _._live_suite_controller$_closeMemo = t7;
+    },
+    LiveSuiteController_closure: function LiveSuiteController_closure(t0) {
+      this.$this = t0;
+    },
+    LiveSuiteController_closure0: function LiveSuiteController_closure0() {
+    },
+    LiveSuiteController_reportLiveTest_closure: function LiveSuiteController_reportLiveTest_closure(t0, t1, t2) {
+      this.$this = t0;
+      this.liveTest = t1;
+      this.countSuccess = t2;
+    },
+    LiveSuiteController_close_closure: function LiveSuiteController_close_closure(t0) {
+      this.$this = t0;
+    },
+    asUri: function(uri, $name) {
+      if (type$.Uri._is(uri))
+        return uri;
+      throw H.wrapException(P.ArgumentError$value(uri, $name, "Must be a String or a Uri."));
+    },
+    ensureTrailingSlash: function(uri) {
+      var t1;
+      if (uri.get$pathSegments().length === 0)
+        return uri.replace$1$path(0, "/");
+      t1 = C.JSArray_methods.get$last(uri.get$pathSegments());
+      t1.toString;
+      if (J.get$length$asx(t1) === 0)
+        return uri;
+      t1 = uri.get$pathSegments();
+      t1 = H.setRuntimeTypeInfo(t1.slice(0), H._arrayInstanceType(t1)._eval$1("JSArray<1>"));
+      C.JSArray_methods.add$1(t1, "");
+      return uri.replace$1$pathSegments(0, t1);
+    },
+    isAlphabetic: function(char) {
+      var t1;
+      if (!(char >= 65 && char <= 90))
+        t1 = char >= 97 && char <= 122;
+      else
+        t1 = true;
+      return t1;
+    },
+    isDriveLetter: function(path, index) {
+      var t1 = path.length,
+        t2 = index + 2;
+      if (t1 < t2)
+        return false;
+      if (!B.isAlphabetic(C.JSString_methods.codeUnitAt$1(path, index)))
+        return false;
+      if (C.JSString_methods.codeUnitAt$1(path, index + 1) !== 58)
+        return false;
+      if (t1 === t2)
+        return true;
+      return C.JSString_methods.codeUnitAt$1(path, t2) === 47;
+    },
+    countCodeUnits: function(string, codeUnit) {
+      var t1, count;
+      for (t1 = new H.CodeUnits(string), t1 = new H.ListIterator(t1, t1.get$length(t1), type$.CodeUnits._eval$1("ListIterator<ListMixin.E>")), count = 0; t1.moveNext$0();)
+        if (t1.__internal$_current === codeUnit)
+          ++count;
+      return count;
+    },
+    findLineStart: function(context, text, column) {
+      var beginningOfLine, index, lineStart;
+      if (text.length === 0)
+        for (beginningOfLine = 0; true;) {
+          index = C.JSString_methods.indexOf$2(context, "\n", beginningOfLine);
+          if (index === -1)
+            return context.length - beginningOfLine >= column ? beginningOfLine : null;
+          if (index - beginningOfLine >= column)
+            return beginningOfLine;
+          beginningOfLine = index + 1;
+        }
+      index = C.JSString_methods.indexOf$1(context, text);
+      for (; index !== -1;) {
+        lineStart = index === 0 ? 0 : C.JSString_methods.lastIndexOf$2(context, "\n", index - 1) + 1;
+        if (column === index - lineStart)
+          return lineStart;
+        index = C.JSString_methods.indexOf$2(context, text, index + 1);
+      }
+      return null;
+    },
+    validateErrorArgs: function(string, match, position, $length) {
+      var t1;
+      if (position < 0)
+        throw H.wrapException(P.RangeError$("position must be greater than or equal to 0."));
+      else if (position > string.length)
+        throw H.wrapException(P.RangeError$("position must be less than or equal to the string length."));
+      t1 = position + $length > string.length;
+      if (t1)
+        throw H.wrapException(P.RangeError$("position plus length must not go beyond the end of the string."));
+    }
+  },
+  Q = {
+    QueueList$: function($E) {
+      var t1 = new Q.QueueList($E._eval$1("QueueList<0>")),
+        t2 = new Array(8);
+      t2.fixed$length = Array;
+      t1.set$_queue_list$_table(H.setRuntimeTypeInfo(t2, $E._eval$1("JSArray<0>")));
+      return t1;
+    },
+    QueueList__nextPowerOf2: function(number) {
+      var nextNumber;
+      H.assertHelper(number > 0);
+      number = (number << 1 >>> 0) - 1;
+      for (; true; number = nextNumber) {
+        nextNumber = (number & number - 1) >>> 0;
+        if (nextNumber === 0)
+          return number;
+      }
+    },
+    QueueList: function QueueList(t0) {
+      var _ = this;
+      _._queue_list$_table = null;
+      _._queue_list$_tail = _._queue_list$_head = 0;
+      _.$ti = t0;
+    },
+    _QueueList_Object_ListMixin: function _QueueList_Object_ListMixin() {
+    }
+  },
+  M = {UnionSet: function UnionSet(t0, t1, t2) {
+      this._sets = t0;
+      this._disjoint = t1;
+      this.$ti = t2;
+    }, UnionSet_length_closure: function UnionSet_length_closure(t0) {
+      this.$this = t0;
+    }, UnionSet__iterable_closure: function UnionSet__iterable_closure(t0) {
+      this.$this = t0;
+    }, _UnionSet_SetBase_UnmodifiableSetMixin: function _UnionSet_SetBase_UnmodifiableSetMixin() {
+    }, _DelegatingIterableBase: function _DelegatingIterableBase() {
+    }, DelegatingIterable: function DelegatingIterable() {
+    }, DelegatingSet: function DelegatingSet(t0, t1) {
+      this._base = t0;
+      this.$ti = t1;
+    }, TypeMatcher: function TypeMatcher() {
+    },
+    wrapMatcher: function(x) {
+      var _s18_ = "satisfies function";
+      if (x instanceof G.Matcher)
+        return x;
+      else if (type$.bool_Function_Object._is(x))
+        return new Y._Predicate(x, _s18_, type$._Predicate_Object);
+      else if (type$.bool_Function_Null._is(x))
+        return new Y._Predicate(new M.wrapMatcher_closure(x), _s18_, type$._Predicate_dynamic);
+      else
+        return typeof x == "string" ? new D._StringEqualsMatcher(x) : new D._DeepMatcher(x, 100);
+    },
+    escape: function(str) {
+      str.toString;
+      return C.JSString_methods.splitMapJoin$2$onMatch(H.stringReplaceAllUnchecked(str, "\\", "\\\\"), $.$get$_escapeRegExp(), type$.String_Function_Match._check(new M.escape_closure()));
+    },
+    _getHexLiteral: function(input) {
+      var t1, it, result;
+      H._checkStringNullable(input);
+      input.toString;
+      t1 = new P.Runes(input);
+      it = t1.get$iterator(t1);
+      if (!it.moveNext$0())
+        H.throwExpression(H.IterableElementError_noElement());
+      result = it.get$current();
+      if (it.moveNext$0())
+        H.throwExpression(H.IterableElementError_tooMany());
+      return "\\x" + C.JSString_methods.padLeft$2(J.toRadixString$1$n(result, 16).toUpperCase(), 2, "0");
+    },
+    wrapMatcher_closure: function wrapMatcher_closure(t0) {
+      this.x = t0;
+    },
+    escape_closure: function escape_closure() {
+    },
+    Context_Context: function(style) {
+      var current = style == null ? D.current() : ".";
+      if (style == null)
+        style = $.$get$Style_platform();
+      return new M.Context(style, current);
+    },
+    _parseUri: function(uri) {
+      if (type$.Uri._is(uri))
+        return uri;
+      throw H.wrapException(P.ArgumentError$value(uri, "uri", "Value must be a String or a Uri"));
+    },
+    _validateArgList: function(method, args) {
+      var numArgs, i, numArgs0, message, t1, t2, t3;
+      for (numArgs = args.length, i = 1; i < numArgs; ++i) {
+        if (args[i] == null || args[i - 1] != null)
+          continue;
+        for (; numArgs >= 1; numArgs = numArgs0) {
+          numArgs0 = numArgs - 1;
+          if (args[numArgs0] != null)
+            break;
+        }
+        message = new P.StringBuffer("");
+        t1 = method + "(";
+        message._contents = t1;
+        t2 = H.SubListIterable$(args, 0, numArgs, H._arrayInstanceType(args)._precomputed1);
+        t3 = t2.$ti;
+        t3 = t1 + new H.MappedListIterable(t2, t3._eval$1("String(ListIterable.E)")._check(new M._validateArgList_closure()), t3._eval$1("MappedListIterable<ListIterable.E,String>")).join$1(0, ", ");
+        message._contents = t3;
+        message._contents = t3 + ("): part " + (i - 1) + " was null, but part " + i + " was not.");
+        throw H.wrapException(P.ArgumentError$(message.toString$0(0)));
+      }
+    },
+    Context: function Context(t0, t1) {
+      this.style = t0;
+      this._context$_current = t1;
+    },
+    Context_join_closure: function Context_join_closure() {
+    },
+    Context_joinAll_closure: function Context_joinAll_closure() {
+    },
+    Context_split_closure: function Context_split_closure() {
+    },
+    _validateArgList_closure: function _validateArgList_closure() {
+    },
+    _PathDirection: function _PathDirection(t0) {
+      this.name = t0;
+    },
+    _PathRelation: function _PathRelation(t0) {
+      this.name = t0;
+    }
+  },
+  D = {
+    _StringEqualsMatcher__writeLeading: function(buff, s, start) {
+      var t1 = buff._contents;
+      if (start > 10) {
+        t1 += "... ";
+        buff._contents = t1;
+        buff._contents = t1 + C.JSString_methods.substring$2(s, start - 10, start);
+      } else
+        buff._contents = t1 + C.JSString_methods.substring$2(s, 0, start);
+    },
+    _StringEqualsMatcher__writeTrailing: function(buff, s, start) {
+      var t1 = start + 10,
+        t2 = buff._contents;
+      if (t1 > s.length)
+        buff._contents = t2 + C.JSString_methods.substring$1(s, start);
+      else {
+        t1 = t2 + C.JSString_methods.substring$2(s, start, t1);
+        buff._contents = t1;
+        buff._contents = t1 + " ...";
+      }
+    },
+    _StringEqualsMatcher: function _StringEqualsMatcher(t0) {
+      this._equals_matcher$_value = t0;
+    },
+    _DeepMatcher: function _DeepMatcher(t0, t1) {
+      this._expected = t0;
+      this._limit = t1;
+    },
+    _DeepMatcher__compareSets_closure: function _DeepMatcher__compareSets_closure(t0, t1, t2, t3) {
+      var _ = this;
+      _.matcher = t0;
+      _.expectedElement = t1;
+      _.location = t2;
+      _.depth = t3;
+    },
+    PackageRootResolver: function PackageRootResolver(t0) {
+      this.packageRoot = t0;
+    },
+    SourceLocationMixin: function SourceLocationMixin() {
+    },
+    _MultiChannel$: function(_inner, $T) {
+      var t1 = type$.int;
+      t1 = new D._MultiChannel(_inner, B.StreamChannelController$(true, true, $T), P.LinkedHashMap_LinkedHashMap$_empty(t1, $T._eval$1("StreamChannelController<0>")), P.LinkedHashSet_LinkedHashSet(t1), P.LinkedHashSet_LinkedHashSet(t1), $T._eval$1("_MultiChannel<0>"));
+      t1._MultiChannel$1(_inner, $T);
+      return t1;
+    },
+    _MultiChannel: function _MultiChannel(t0, t1, t2, t3, t4, t5) {
+      var _ = this;
+      _._multi_channel$_inner = t0;
+      _._innerStreamSubscription = null;
+      _._mainController = t1;
+      _._controllers = t2;
+      _._pendingIds = t3;
+      _._closedIds = t4;
+      _._nextId = 1;
+      _.$ti = t5;
+    },
+    _MultiChannel_closure: function _MultiChannel_closure(t0, t1) {
+      this.$this = t0;
+      this.T = t1;
+    },
+    _MultiChannel_closure0: function _MultiChannel_closure0(t0) {
+      this.$this = t0;
+    },
+    _MultiChannel_closure1: function _MultiChannel_closure1(t0, t1) {
+      this.$this = t0;
+      this.T = t1;
+    },
+    _MultiChannel__closure: function _MultiChannel__closure(t0, t1, t2) {
+      this.$this = t0;
+      this.id = t1;
+      this.T = t2;
+    },
+    _MultiChannel_virtualChannel_closure: function _MultiChannel_virtualChannel_closure(t0, t1) {
+      this._box_0 = t0;
+      this.$this = t1;
+    },
+    _MultiChannel_virtualChannel_closure0: function _MultiChannel_virtualChannel_closure0(t0, t1) {
+      this._box_0 = t0;
+      this.$this = t1;
+    },
+    VirtualChannel: function VirtualChannel(t0, t1, t2, t3, t4) {
+      var _ = this;
+      _._multi_channel$_parent = t0;
+      _.id = t1;
+      _.stream = t2;
+      _.sink = t3;
+      _.$ti = t4;
+    },
+    Message: function Message(t0, t1) {
+      this.type = t0;
+      this.text = t1;
+    },
+    MessageType: function MessageType(t0) {
+      this.name = t0;
+    },
+    current: function() {
+      var exception, t1, path, lastIndex, uri = null;
+      try {
+        uri = P.Uri_base();
+      } catch (exception) {
+        if (type$.Exception._is(H.unwrapException(exception))) {
+          t1 = $._current;
+          if (t1 != null)
+            return t1;
+          throw exception;
+        } else
+          throw exception;
+      }
+      if (J.$eq$(uri, $._currentUriBase))
+        return $._current;
+      $._currentUriBase = uri;
+      if ($.$get$Style_platform() == $.$get$Style_url())
+        return $._current = uri.resolve$1(".").toString$0(0);
+      else {
+        path = uri.toFilePath$0();
+        t1 = path.length;
+        lastIndex = t1 - 1;
+        if (lastIndex < 0)
+          return H.ioore(path, lastIndex);
+        t1 = path[lastIndex];
+        H.assertHelper(t1 === "/" || t1 === "\\");
+        return $._current = lastIndex === 0 ? path : C.JSString_methods.substring$2(path, 0, lastIndex);
+      }
+    }
+  },
+  Z = {
+    prettyPrint: function(object, maxItems, maxLineLength) {
+      return new Z.prettyPrint__prettyPrint(maxItems, maxLineLength).call$4(object, 0, P.LinkedHashSet_LinkedHashSet$_empty(type$.Object), true);
+    },
+    _typeName: function(x) {
+      if (type$.Type._is(x))
+        return "Type";
+      if (type$.Uri._is(x))
+        return "Uri";
+      if (type$.Set_dynamic._is(x))
+        return "Set";
+      return J.get$runtimeType$(x).toString$0(0);
+    },
+    _escapeString: function(source) {
+      var t1 = M.escape(H._checkStringNullable(source));
+      return H.stringReplaceAllUnchecked(t1, "'", "\\'");
+    },
+    prettyPrint__prettyPrint: function prettyPrint__prettyPrint(t0, t1) {
+      this.maxItems = t0;
+      this.maxLineLength = t1;
+    },
+    prettyPrint__prettyPrint_pp: function prettyPrint__prettyPrint_pp(t0, t1, t2) {
+      this._box_0 = t0;
+      this._prettyPrint = t1;
+      this.indent = t2;
+    },
+    prettyPrint__prettyPrint_closure: function prettyPrint__prettyPrint_closure(t0) {
+      this.indent = t0;
+    },
+    prettyPrint__prettyPrint_closure0: function prettyPrint__prettyPrint_closure0(t0, t1) {
+      this.pp = t0;
+      this.object = t1;
+    },
+    prettyPrint__prettyPrint_closure1: function prettyPrint__prettyPrint_closure1(t0) {
+      this.indent = t0;
+    },
+    LiveTest: function LiveTest() {
+    }
+  },
+  A = {
+    Frame_Frame$parseVM: function(frame) {
+      return A.Frame__catchFormatException(frame, new A.Frame_Frame$parseVM_closure(frame));
+    },
+    Frame_Frame$parseV8: function(frame) {
+      return A.Frame__catchFormatException(frame, new A.Frame_Frame$parseV8_closure(frame));
+    },
+    Frame_Frame$parseFirefox: function(frame) {
+      return A.Frame__catchFormatException(frame, new A.Frame_Frame$parseFirefox_closure(frame));
+    },
+    Frame_Frame$parseFriendly: function(frame) {
+      return A.Frame__catchFormatException(frame, new A.Frame_Frame$parseFriendly_closure(frame));
+    },
+    Frame__uriOrPathToUri: function(uriOrPath) {
+      if (J.getInterceptor$asx(uriOrPath).contains$1(uriOrPath, $.$get$Frame__uriRegExp()))
+        return P.Uri_parse(uriOrPath);
+      else if (C.JSString_methods.contains$1(uriOrPath, $.$get$Frame__windowsRegExp()))
+        return P._Uri__Uri$file(uriOrPath, true);
+      else if (C.JSString_methods.startsWith$1(uriOrPath, "/"))
+        return P._Uri__Uri$file(uriOrPath, false);
+      if (C.JSString_methods.contains$1(uriOrPath, "\\"))
+        return $.$get$windows().toUri$1(uriOrPath);
+      return P.Uri_parse(uriOrPath);
+    },
+    Frame__catchFormatException: function(text, body) {
+      var t1, exception;
+      try {
+        t1 = body.call$0();
+        return t1;
+      } catch (exception) {
+        if (type$.FormatException._is(H.unwrapException(exception)))
+          return new N.UnparsedFrame(P._Uri__Uri(null, "unparsed", null, null), text);
+        else
+          throw exception;
+      }
+    },
+    Frame: function Frame(t0, t1, t2, t3) {
+      var _ = this;
+      _.uri = t0;
+      _.line = t1;
+      _.column = t2;
+      _.member = t3;
+    },
+    Frame_Frame$parseVM_closure: function Frame_Frame$parseVM_closure(t0) {
+      this.frame = t0;
+    },
+    Frame_Frame$parseV8_closure: function Frame_Frame$parseV8_closure(t0) {
+      this.frame = t0;
+    },
+    Frame_Frame$parseV8_closure_parseLocation: function Frame_Frame$parseV8_closure_parseLocation(t0) {
+      this.frame = t0;
+    },
+    Frame_Frame$parseFirefox_closure: function Frame_Frame$parseFirefox_closure(t0) {
+      this.frame = t0;
+    },
+    Frame_Frame$parseFriendly_closure: function Frame_Frame$parseFriendly_closure(t0) {
+      this.frame = t0;
+    },
+    AsciiGlyphSet: function AsciiGlyphSet() {
+    }
+  },
+  N = {UnparsedFrame: function UnparsedFrame(t0, t1) {
+      this.uri = t0;
+      this.member = t1;
+    }, StreamChannelCompleter: function StreamChannelCompleter(t0, t1, t2) {
+      var _ = this;
+      _._streamCompleter = t0;
+      _._sinkCompleter = t1;
+      _._stream_channel_completer$_channel = null;
+      _._stream_channel_completer$_set = false;
+      _.$ti = t2;
+    },
+    postMessageChannel: function() {
+      var t1, t2,
+        controller = B.StreamChannelController$(true, true, type$.dynamic);
+      new W._EventStream(window, "message", false, type$._EventStream_MessageEvent).firstWhere$1(0, new N.postMessageChannel_closure()).then$1$1(new N.postMessageChannel_closure0(controller), type$.Null);
+      t1 = P.LinkedHashMap_LinkedHashMap$_literal(["href", window.location.href, "ready", true], type$.String, type$.Object);
+      t1 = P._convertDataTree(t1);
+      t2 = window.location;
+      self.window.parent.postMessage(t1, (t2 && C.Location_methods).get$origin(t2));
+      return controller._foreign;
+    },
+    postMessageChannel_closure: function postMessageChannel_closure() {
+    },
+    postMessageChannel_closure0: function postMessageChannel_closure0(t0) {
+      this.controller = t0;
+    },
+    postMessageChannel__closure: function postMessageChannel__closure(t0) {
+      this.controller = t0;
+    },
+    postMessageChannel__closure0: function postMessageChannel__closure0(t0) {
+      this.port = t0;
+    },
+    postMessageChannel__closure1: function postMessageChannel__closure1(t0, t1) {
+      this.port = t0;
+      this.portSubscription = t1;
+    },
+    OperatingSystem_find: function(identifier) {
+      return C.JSArray_methods.firstWhere$2$orElse(C.List_opx, new N.OperatingSystem_find_closure(identifier), new N.OperatingSystem_find_closure0());
+    },
+    OperatingSystem: function OperatingSystem(t0, t1) {
+      this.name = t0;
+      this.identifier = t1;
+    },
+    OperatingSystem_find_closure: function OperatingSystem_find_closure(t0) {
+      this.identifier = t0;
+    },
+    OperatingSystem_find_closure0: function OperatingSystem_find_closure0() {
+    },
+    SuiteChannelManager: function SuiteChannelManager(t0, t1, t2) {
+      this._incomingConnections = t0;
+      this._outgoingConnections = t1;
+      this._names = t2;
+    }
+  },
+  K = {
+    GuaranteeChannel$: function(innerStream, innerSink, allowSinkErrors, $T) {
+      var t2, t1 = {};
+      t1.innerStream = innerStream;
+      t2 = new K.GuaranteeChannel($T._eval$1("GuaranteeChannel<0>"));
+      t2.GuaranteeChannel$3$allowSinkErrors(innerSink, allowSinkErrors, t1, $T);
+      return t2;
+    },
+    GuaranteeChannel: function GuaranteeChannel(t0) {
+      var _ = this;
+      _._subscription = _._streamController = _._sink = null;
+      _._disconnected = false;
+      _.$ti = t0;
+    },
+    GuaranteeChannel_closure: function GuaranteeChannel_closure(t0, t1) {
+      this._box_0 = t0;
+      this.$this = t1;
+    },
+    GuaranteeChannel__closure: function GuaranteeChannel__closure(t0) {
+      this.$this = t0;
+    },
+    _GuaranteeSink: function _GuaranteeSink(t0, t1, t2, t3, t4) {
+      var _ = this;
+      _._inner = t0;
+      _._channel = t1;
+      _._doneCompleter = t2;
+      _._closed = _._disconnected = false;
+      _._addStreamCompleter = _._addStreamSubscription = null;
+      _._allowErrors = t3;
+      _.$ti = t4;
+    },
+    _GuaranteeSink__addError_closure: function _GuaranteeSink__addError_closure() {
+    },
+    _GuaranteeSink_addStream_closure: function _GuaranteeSink_addStream_closure(t0) {
+      this.$this = t0;
+    },
+    UnicodeGlyphSet: function UnicodeGlyphSet() {
+    },
+    ClosedException$: function() {
+      return new K.ClosedException();
+    },
+    ClosedException: function ClosedException() {
+    }
+  };
+  var holders = [C, H, J, P, W, S, O, Y, F, V, E, L, G, T, X, U, R, B, Q, M, D, Z, A, N, K];
+  hunkHelpers.setFunctionNamesIfNecessary(holders);
+  var $ = {};
+  H.JS_CONST.prototype = {};
+  J.Interceptor.prototype = {
+    $eq: function(receiver, other) {
+      return receiver === other;
+    },
+    get$hashCode: function(receiver) {
+      return H.Primitives_objectHashCode(receiver);
+    },
+    toString$0: function(receiver) {
+      return "Instance of '" + H.S(H.Primitives_objectTypeName(receiver)) + "'";
+    },
+    get$runtimeType: function(receiver) {
+      return H.getRuntimeType(receiver);
+    }
+  };
+  J.JSBool.prototype = {
+    toString$0: function(receiver) {
+      return String(receiver);
+    },
+    get$hashCode: function(receiver) {
+      return receiver ? 519018 : 218159;
+    },
+    get$runtimeType: function(receiver) {
+      return C.Type_bool_lhE;
+    },
+    $isbool: 1
+  };
+  J.JSNull.prototype = {
+    $eq: function(receiver, other) {
+      return null == other;
+    },
+    toString$0: function(receiver) {
+      return "null";
+    },
+    get$hashCode: function(receiver) {
+      return 0;
+    },
+    get$runtimeType: function(receiver) {
+      return C.Type_Null_Yyn;
+    },
+    $isNull: 1
+  };
+  J.JSObject.prototype = {};
+  J.JavaScriptObject.prototype = {
+    get$hashCode: function(receiver) {
+      return 0;
+    },
+    get$runtimeType: function(receiver) {
+      return C.Type_JSObject_8k0;
+    },
+    toString$0: function(receiver) {
+      return String(receiver);
+    },
+    $isJSObject: 1
+  };
+  J.PlainJavaScriptObject.prototype = {};
+  J.UnknownJavaScriptObject.prototype = {};
+  J.JavaScriptFunction.prototype = {
+    toString$0: function(receiver) {
+      var dartClosure = receiver[$.$get$DART_CLOSURE_PROPERTY_NAME()];
+      if (dartClosure == null)
+        return this.super$JavaScriptObject$toString(receiver);
+      return "JavaScript function for " + H.S(J.toString$0$(dartClosure));
+    },
+    $signature: function() {
+      return {func: 1, opt: [,,,,,,,,,,,,,,,,]};
+    },
+    $isFunction: 1
+  };
+  J.JSArray.prototype = {
+    add$1: function(receiver, value) {
+      H._arrayInstanceType(receiver)._precomputed1._check(value);
+      if (!!receiver.fixed$length)
+        H.throwExpression(P.UnsupportedError$("add"));
+      receiver.push(value);
+    },
+    removeAt$1: function(receiver, index) {
+      var t1;
+      if (!!receiver.fixed$length)
+        H.throwExpression(P.UnsupportedError$("removeAt"));
+      t1 = receiver.length;
+      if (index >= t1)
+        throw H.wrapException(P.RangeError$value(index, null));
+      return receiver.splice(index, 1)[0];
+    },
+    insert$2: function(receiver, index, value) {
+      var t1;
+      H._arrayInstanceType(receiver)._precomputed1._check(value);
+      if (!!receiver.fixed$length)
+        H.throwExpression(P.UnsupportedError$("insert"));
+      t1 = receiver.length;
+      if (index > t1)
+        throw H.wrapException(P.RangeError$value(index, null));
+      receiver.splice(index, 0, value);
+    },
+    insertAll$2: function(receiver, index, iterable) {
+      var t1, insertionLength, end;
+      H._arrayInstanceType(receiver)._eval$1("Iterable<1>")._check(iterable);
+      if (!!receiver.fixed$length)
+        H.throwExpression(P.UnsupportedError$("insertAll"));
+      t1 = receiver.length;
+      P.RangeError_checkValueInInterval(index, 0, t1, "index");
+      insertionLength = iterable.length;
+      this.set$length(receiver, t1 + insertionLength);
+      end = index + insertionLength;
+      this.setRange$4(receiver, end, receiver.length, receiver, index);
+      this.setRange$3(receiver, index, end, iterable);
+    },
+    removeLast$0: function(receiver) {
+      if (!!receiver.fixed$length)
+        H.throwExpression(P.UnsupportedError$("removeLast"));
+      if (receiver.length === 0)
+        throw H.wrapException(H.diagnoseIndexError(receiver, -1));
+      return receiver.pop();
+    },
+    remove$1: function(receiver, element) {
+      var i;
+      if (!!receiver.fixed$length)
+        H.throwExpression(P.UnsupportedError$("remove"));
+      for (i = 0; i < receiver.length; ++i)
+        if (J.$eq$(receiver[i], element)) {
+          receiver.splice(i, 1);
+          return true;
+        }
+      return false;
+    },
+    addAll$1: function(receiver, collection) {
+      var i, t1, e, i0;
+      H._arrayInstanceType(receiver)._eval$1("Iterable<1>")._check(collection);
+      i = receiver.length;
+      if (!!receiver.fixed$length)
+        H.throwExpression(P.UnsupportedError$("addAll"));
+      for (t1 = J.get$iterator$ax(collection); t1.moveNext$0(); i = i0) {
+        e = t1.get$current();
+        i0 = i + 1;
+        H.assertHelper(i === receiver.length || H.throwExpression(P.ConcurrentModificationError$(receiver)));
+        receiver.push(e);
+      }
+    },
+    forEach$1: function(receiver, f) {
+      var end, i;
+      H._arrayInstanceType(receiver)._eval$1("~(1)")._check(f);
+      end = receiver.length;
+      for (i = 0; i < end; ++i) {
+        f.call$1(receiver[i]);
+        if (receiver.length !== end)
+          throw H.wrapException(P.ConcurrentModificationError$(receiver));
+      }
+    },
+    map$1$1: function(receiver, f, $T) {
+      var t1 = H._arrayInstanceType(receiver);
+      return new H.MappedListIterable(receiver, t1._bind$1($T)._eval$1("1(2)")._check(f), t1._eval$1("@<1>")._bind$1($T)._eval$1("MappedListIterable<1,2>"));
+    },
+    join$1: function(receiver, separator) {
+      var i,
+        list = new Array(receiver.length);
+      list.fixed$length = Array;
+      for (i = 0; i < receiver.length; ++i)
+        this.$indexSet(list, i, H.S(receiver[i]));
+      return list.join(separator);
+    },
+    join$0: function($receiver) {
+      return this.join$1($receiver, "");
+    },
+    fold$1$2: function(receiver, initialValue, combine, $T) {
+      var $length, value, i;
+      $T._check(initialValue);
+      H._arrayInstanceType(receiver)._bind$1($T)._eval$1("1(1,2)")._check(combine);
+      $length = receiver.length;
+      for (value = initialValue, i = 0; i < $length; ++i) {
+        value = combine.call$2(value, receiver[i]);
+        if (receiver.length !== $length)
+          throw H.wrapException(P.ConcurrentModificationError$(receiver));
+      }
+      return value;
+    },
+    firstWhere$2$orElse: function(receiver, test, orElse) {
+      var end, i, element,
+        t1 = H._arrayInstanceType(receiver);
+      t1._eval$1("bool(1)")._check(test);
+      t1._eval$1("1()")._check(orElse);
+      end = receiver.length;
+      for (i = 0; i < end; ++i) {
+        element = receiver[i];
+        if (H.boolConversionCheck(test.call$1(element)))
+          return element;
+        if (receiver.length !== end)
+          throw H.wrapException(P.ConcurrentModificationError$(receiver));
+      }
+      if (orElse != null)
+        return orElse.call$0();
+      throw H.wrapException(H.IterableElementError_noElement());
+    },
+    firstWhere$1: function($receiver, test) {
+      return this.firstWhere$2$orElse($receiver, test, null);
+    },
+    elementAt$1: function(receiver, index) {
+      if (index < 0 || index >= receiver.length)
+        return H.ioore(receiver, index);
+      return receiver[index];
+    },
+    sublist$2: function(receiver, start, end) {
+      if (start < 0 || start > receiver.length)
+        throw H.wrapException(P.RangeError$range(start, 0, receiver.length, "start", null));
+      if (end < start || end > receiver.length)
+        throw H.wrapException(P.RangeError$range(end, start, receiver.length, "end", null));
+      if (start === end)
+        return H.setRuntimeTypeInfo([], H._arrayInstanceType(receiver));
+      return H.setRuntimeTypeInfo(receiver.slice(start, end), H._arrayInstanceType(receiver));
+    },
+    get$first: function(receiver) {
+      if (receiver.length > 0)
+        return receiver[0];
+      throw H.wrapException(H.IterableElementError_noElement());
+    },
+    get$last: function(receiver) {
+      var t1 = receiver.length;
+      if (t1 > 0)
+        return receiver[t1 - 1];
+      throw H.wrapException(H.IterableElementError_noElement());
+    },
+    get$single: function(receiver) {
+      var t1 = receiver.length;
+      if (t1 === 1) {
+        if (0 >= t1)
+          return H.ioore(receiver, 0);
+        return receiver[0];
+      }
+      if (t1 === 0)
+        throw H.wrapException(H.IterableElementError_noElement());
+      throw H.wrapException(H.IterableElementError_tooMany());
+    },
+    setRange$4: function(receiver, start, end, iterable, skipCount) {
+      var $length, i,
+        t1 = H._arrayInstanceType(receiver);
+      t1._eval$1("Iterable<1>")._check(iterable);
+      if (!!receiver.immutable$list)
+        H.throwExpression(P.UnsupportedError$("setRange"));
+      P.RangeError_checkValidRange(start, end, receiver.length);
+      $length = end - start;
+      if ($length === 0)
+        return;
+      P.RangeError_checkNotNegative(skipCount, "skipCount");
+      t1._eval$1("List<1>")._check(iterable);
+      t1 = J.getInterceptor$asx(iterable);
+      if (skipCount + $length > t1.get$length(iterable))
+        throw H.wrapException(H.IterableElementError_tooFew());
+      if (skipCount < start)
+        for (i = $length - 1; i >= 0; --i)
+          receiver[start + i] = t1.$index(iterable, skipCount + i);
+      else
+        for (i = 0; i < $length; ++i)
+          receiver[start + i] = t1.$index(iterable, skipCount + i);
+    },
+    setRange$3: function($receiver, start, end, iterable) {
+      return this.setRange$4($receiver, start, end, iterable, 0);
+    },
+    fillRange$3: function(receiver, start, end, fillValue) {
+      var i;
+      H._arrayInstanceType(receiver)._precomputed1._check(fillValue);
+      if (!!receiver.immutable$list)
+        H.throwExpression(P.UnsupportedError$("fill range"));
+      P.RangeError_checkValidRange(start, end, receiver.length);
+      for (i = start; i < end; ++i)
+        receiver[i] = fillValue;
+    },
+    replaceRange$3: function(receiver, start, end, replacement) {
+      var t1, removeLength, insertEnd, delta, newLength, _this = this;
+      H._arrayInstanceType(receiver)._eval$1("Iterable<1>")._check(replacement);
+      if (!!receiver.fixed$length)
+        H.throwExpression(P.UnsupportedError$("replaceRange"));
+      t1 = receiver.length;
+      P.RangeError_checkValidRange(start, end, t1);
+      removeLength = end - start;
+      insertEnd = start + 1;
+      if (removeLength >= 1) {
+        delta = removeLength - 1;
+        newLength = t1 - delta;
+        _this.setRange$3(receiver, start, insertEnd, replacement);
+        if (delta !== 0) {
+          _this.setRange$4(receiver, insertEnd, newLength, receiver, end);
+          _this.set$length(receiver, newLength);
+        }
+      } else {
+        newLength = t1 + (1 - removeLength);
+        _this.set$length(receiver, newLength);
+        _this.setRange$4(receiver, insertEnd, newLength, receiver, end);
+        _this.setRange$3(receiver, start, insertEnd, replacement);
+      }
+    },
+    contains$1: function(receiver, other) {
+      var i;
+      for (i = 0; i < receiver.length; ++i)
+        if (J.$eq$(receiver[i], other))
+          return true;
+      return false;
+    },
+    get$isEmpty: function(receiver) {
+      return receiver.length === 0;
+    },
+    toString$0: function(receiver) {
+      return P.IterableBase_iterableToFullString(receiver, "[", "]");
+    },
+    toSet$0: function(receiver) {
+      return P.LinkedHashSet_LinkedHashSet$from(receiver, H._arrayInstanceType(receiver)._precomputed1);
+    },
+    get$iterator: function(receiver) {
+      return new J.ArrayIterator(receiver, receiver.length, H._arrayInstanceType(receiver)._eval$1("ArrayIterator<1>"));
+    },
+    get$hashCode: function(receiver) {
+      return H.Primitives_objectHashCode(receiver);
+    },
+    get$length: function(receiver) {
+      return receiver.length;
+    },
+    set$length: function(receiver, newLength) {
+      var _s9_ = "newLength";
+      if (!!receiver.fixed$length)
+        H.throwExpression(P.UnsupportedError$("set length"));
+      if (!H._isInt(newLength))
+        throw H.wrapException(P.ArgumentError$value(newLength, _s9_, null));
+      if (newLength < 0)
+        throw H.wrapException(P.RangeError$range(newLength, 0, null, _s9_, null));
+      receiver.length = newLength;
+    },
+    $index: function(receiver, index) {
+      H._checkIntNullable(index);
+      if (!H._isInt(index))
+        throw H.wrapException(H.diagnoseIndexError(receiver, index));
+      if (index >= receiver.length || index < 0)
+        throw H.wrapException(H.diagnoseIndexError(receiver, index));
+      return receiver[index];
+    },
+    $indexSet: function(receiver, index, value) {
+      H._checkIntNullable(index);
+      H._arrayInstanceType(receiver)._precomputed1._check(value);
+      if (!!receiver.immutable$list)
+        H.throwExpression(P.UnsupportedError$("indexed set"));
+      if (!H._isInt(index))
+        throw H.wrapException(H.diagnoseIndexError(receiver, index));
+      if (index >= receiver.length || index < 0)
+        throw H.wrapException(H.diagnoseIndexError(receiver, index));
+      receiver[index] = value;
+    },
+    $isEfficientLengthIterable: 1,
+    $isIterable: 1,
+    $isList: 1
+  };
+  J.JSUnmodifiableArray.prototype = {};
+  J.ArrayIterator.prototype = {
+    get$current: function() {
+      return this._current;
+    },
+    moveNext$0: function() {
+      var t2, _this = this,
+        t1 = _this._iterable,
+        $length = t1.length;
+      if (_this._length !== $length)
+        throw H.wrapException(H.throwConcurrentModificationError(t1));
+      t2 = _this._index;
+      if (t2 >= $length) {
+        _this.set$_current(null);
+        return false;
+      }
+      _this.set$_current(t1[t2]);
+      ++_this._index;
+      return true;
+    },
+    set$_current: function(_current) {
+      this._current = this.$ti._precomputed1._check(_current);
+    },
+    $isIterator: 1
+  };
+  J.JSNumber.prototype = {
+    floor$0: function(receiver) {
+      var truncated, d;
+      if (receiver >= 0) {
+        if (receiver <= 2147483647)
+          return receiver | 0;
+      } else if (receiver >= -2147483648) {
+        truncated = receiver | 0;
+        return receiver === truncated ? truncated : truncated - 1;
+      }
+      d = Math.floor(receiver);
+      if (isFinite(d))
+        return d;
+      throw H.wrapException(P.UnsupportedError$("" + receiver + ".floor()"));
+    },
+    round$0: function(receiver) {
+      if (receiver > 0) {
+        if (receiver !== 1 / 0)
+          return Math.round(receiver);
+      } else if (receiver > -1 / 0)
+        return 0 - Math.round(0 - receiver);
+      throw H.wrapException(P.UnsupportedError$("" + receiver + ".round()"));
+    },
+    toRadixString$1: function(receiver, radix) {
+      var result, match, t1, exponent;
+      if (radix < 2 || radix > 36)
+        throw H.wrapException(P.RangeError$range(radix, 2, 36, "radix", null));
+      result = receiver.toString(radix);
+      if (C.JSString_methods.codeUnitAt$1(result, result.length - 1) !== 41)
+        return result;
+      match = /^([\da-z]+)(?:\.([\da-z]+))?\(e\+(\d+)\)$/.exec(result);
+      if (match == null)
+        H.throwExpression(P.UnsupportedError$("Unexpected toString result: " + result));
+      t1 = match.length;
+      if (1 >= t1)
+        return H.ioore(match, 1);
+      result = match[1];
+      if (3 >= t1)
+        return H.ioore(match, 3);
+      exponent = +match[3];
+      t1 = match[2];
+      if (t1 != null) {
+        result += t1;
+        exponent -= t1.length;
+      }
+      return result + C.JSString_methods.$mul("0", exponent);
+    },
+    toString$0: function(receiver) {
+      if (receiver === 0 && 1 / receiver < 0)
+        return "-0.0";
+      else
+        return "" + receiver;
+    },
+    get$hashCode: function(receiver) {
+      var absolute, floorLog2, factor, scaled,
+        intValue = receiver | 0;
+      if (receiver === intValue)
+        return 536870911 & intValue;
+      absolute = Math.abs(receiver);
+      floorLog2 = Math.log(absolute) / 0.6931471805599453 | 0;
+      factor = Math.pow(2, floorLog2);
+      scaled = absolute < 1 ? absolute / factor : factor / absolute;
+      return 536870911 & ((scaled * 9007199254740992 | 0) + (scaled * 3542243181176521 | 0)) * 599197 + floorLog2 * 1259;
+    },
+    $mod: function(receiver, other) {
+      var result = receiver % other;
+      if (result === 0)
+        return 0;
+      if (result > 0)
+        return result;
+      if (other < 0)
+        return result - other;
+      else
+        return result + other;
+    },
+    $tdiv: function(receiver, other) {
+      if ((receiver | 0) === receiver)
+        if (other >= 1 || other < -1)
+          return receiver / other | 0;
+      return this._tdivSlow$1(receiver, other);
+    },
+    _tdivFast$1: function(receiver, other) {
+      return (receiver | 0) === receiver ? receiver / other | 0 : this._tdivSlow$1(receiver, other);
+    },
+    _tdivSlow$1: function(receiver, other) {
+      var quotient = receiver / other;
+      if (quotient >= -2147483648 && quotient <= 2147483647)
+        return quotient | 0;
+      if (quotient > 0) {
+        if (quotient !== 1 / 0)
+          return Math.floor(quotient);
+      } else if (quotient > -1 / 0)
+        return Math.ceil(quotient);
+      throw H.wrapException(P.UnsupportedError$("Result of truncating division is " + H.S(quotient) + ": " + H.S(receiver) + " ~/ " + other));
+    },
+    _shlPositive$1: function(receiver, other) {
+      return other > 31 ? 0 : receiver << other >>> 0;
+    },
+    _shrOtherPositive$1: function(receiver, other) {
+      var t1;
+      if (receiver > 0)
+        t1 = this._shrBothPositive$1(receiver, other);
+      else {
+        t1 = other > 31 ? 31 : other;
+        t1 = receiver >> t1 >>> 0;
+      }
+      return t1;
+    },
+    _shrReceiverPositive$1: function(receiver, other) {
+      if (other < 0)
+        throw H.wrapException(H.argumentErrorValue(other));
+      return this._shrBothPositive$1(receiver, other);
+    },
+    _shrBothPositive$1: function(receiver, other) {
+      return other > 31 ? 0 : receiver >>> other;
+    },
+    get$runtimeType: function(receiver) {
+      return C.Type_num_cv7;
+    },
+    $isdouble: 1,
+    $isnum: 1
+  };
+  J.JSInt.prototype = {
+    get$runtimeType: function(receiver) {
+      return C.Type_int_tHn;
+    },
+    $isint: 1
+  };
+  J.JSDouble.prototype = {
+    get$runtimeType: function(receiver) {
+      return C.Type_double_K1J;
+    }
+  };
+  J.JSString.prototype = {
+    codeUnitAt$1: function(receiver, index) {
+      if (index < 0)
+        throw H.wrapException(H.diagnoseIndexError(receiver, index));
+      if (index >= receiver.length)
+        H.throwExpression(H.diagnoseIndexError(receiver, index));
+      return receiver.charCodeAt(index);
+    },
+    _codeUnitAt$1: function(receiver, index) {
+      if (index >= receiver.length)
+        throw H.wrapException(H.diagnoseIndexError(receiver, index));
+      return receiver.charCodeAt(index);
+    },
+    allMatches$2: function(receiver, string, start) {
+      var t1;
+      if (typeof string != "string")
+        H.throwExpression(H.argumentErrorValue(string));
+      t1 = string.length;
+      if (start > t1)
+        throw H.wrapException(P.RangeError$range(start, 0, t1, null, null));
+      return new H._StringAllMatchesIterable(string, receiver, start);
+    },
+    allMatches$1: function($receiver, string) {
+      return this.allMatches$2($receiver, string, 0);
+    },
+    matchAsPrefix$2: function(receiver, string, start) {
+      var t1, t2, i, _null = null;
+      if (start < 0 || start > string.length)
+        throw H.wrapException(P.RangeError$range(start, 0, string.length, _null, _null));
+      t1 = receiver.length;
+      if (start + t1 > string.length)
+        return _null;
+      for (t2 = J.getInterceptor$s(string), i = 0; i < t1; ++i)
+        if (t2.codeUnitAt$1(string, start + i) !== this._codeUnitAt$1(receiver, i))
+          return _null;
+      return new H.StringMatch(start, receiver);
+    },
+    $add: function(receiver, other) {
+      if (typeof other != "string")
+        throw H.wrapException(P.ArgumentError$value(other, null, null));
+      return receiver + other;
+    },
+    endsWith$1: function(receiver, other) {
+      var otherLength = other.length,
+        t1 = receiver.length;
+      if (otherLength > t1)
+        return false;
+      return other === this.substring$1(receiver, t1 - otherLength);
+    },
+    splitMapJoin$2$onMatch: function(receiver, from, onMatch) {
+      return H.stringReplaceAllFuncUnchecked(receiver, from, type$.String_Function_Match._check(onMatch), type$.String_Function_String._check(null));
+    },
+    replaceFirst$2: function(receiver, from, to) {
+      P.RangeError_checkValueInInterval(0, 0, receiver.length, "startIndex");
+      return H.stringReplaceFirstUnchecked(receiver, from, to, 0);
+    },
+    replaceRange$3: function(receiver, start, end, replacement) {
+      end = P.RangeError_checkValidRange(start, end, receiver.length);
+      return H.stringReplaceRangeUnchecked(receiver, start, end, replacement);
+    },
+    startsWith$2: function(receiver, pattern, index) {
+      var endIndex;
+      type$.Pattern._check(pattern);
+      if (index < 0 || index > receiver.length)
+        throw H.wrapException(P.RangeError$range(index, 0, receiver.length, null, null));
+      if (typeof pattern == "string") {
+        endIndex = index + pattern.length;
+        if (endIndex > receiver.length)
+          return false;
+        return pattern === receiver.substring(index, endIndex);
+      }
+      return J.matchAsPrefix$2$s(pattern, receiver, index) != null;
+    },
+    startsWith$1: function($receiver, pattern) {
+      return this.startsWith$2($receiver, pattern, 0);
+    },
+    substring$2: function(receiver, startIndex, endIndex) {
+      if (endIndex == null)
+        endIndex = receiver.length;
+      if (startIndex < 0)
+        throw H.wrapException(P.RangeError$value(startIndex, null));
+      if (startIndex > endIndex)
+        throw H.wrapException(P.RangeError$value(startIndex, null));
+      if (endIndex > receiver.length)
+        throw H.wrapException(P.RangeError$value(endIndex, null));
+      return receiver.substring(startIndex, endIndex);
+    },
+    substring$1: function($receiver, startIndex) {
+      return this.substring$2($receiver, startIndex, null);
+    },
+    trim$0: function(receiver) {
+      var startIndex, t1, endIndex0,
+        result = receiver.trim(),
+        endIndex = result.length;
+      if (endIndex === 0)
+        return result;
+      if (this._codeUnitAt$1(result, 0) === 133) {
+        startIndex = J.JSString__skipLeadingWhitespace(result, 1);
+        if (startIndex === endIndex)
+          return "";
+      } else
+        startIndex = 0;
+      t1 = endIndex - 1;
+      endIndex0 = this.codeUnitAt$1(result, t1) === 133 ? J.JSString__skipTrailingWhitespace(result, t1) : endIndex;
+      if (startIndex === 0 && endIndex0 === endIndex)
+        return result;
+      return result.substring(startIndex, endIndex0);
+    },
+    $mul: function(receiver, times) {
+      var s, result;
+      if (0 >= times)
+        return "";
+      if (times === 1 || receiver.length === 0)
+        return receiver;
+      if (times !== times >>> 0)
+        throw H.wrapException(C.C_OutOfMemoryError);
+      for (s = receiver, result = ""; true;) {
+        if ((times & 1) === 1)
+          result = s + result;
+        times = times >>> 1;
+        if (times === 0)
+          break;
+        s += s;
+      }
+      return result;
+    },
+    padLeft$2: function(receiver, width, padding) {
+      var delta = width - receiver.length;
+      if (delta <= 0)
+        return receiver;
+      return this.$mul(padding, delta) + receiver;
+    },
+    padRight$1: function(receiver, width) {
+      var delta;
+      if (typeof width !== "number")
+        return width.$sub();
+      delta = width - receiver.length;
+      if (delta <= 0)
+        return receiver;
+      return receiver + this.$mul(" ", delta);
+    },
+    indexOf$2: function(receiver, pattern, start) {
+      var t1;
+      if (start < 0 || start > receiver.length)
+        throw H.wrapException(P.RangeError$range(start, 0, receiver.length, null, null));
+      t1 = receiver.indexOf(pattern, start);
+      return t1;
+    },
+    indexOf$1: function($receiver, pattern) {
+      return this.indexOf$2($receiver, pattern, 0);
+    },
+    lastIndexOf$2: function(receiver, pattern, start) {
+      var t1, t2;
+      if (start == null)
+        start = receiver.length;
+      else if (start < 0 || start > receiver.length)
+        throw H.wrapException(P.RangeError$range(start, 0, receiver.length, null, null));
+      t1 = pattern.length;
+      t2 = receiver.length;
+      if (start + t1 > t2)
+        start = t2 - t1;
+      return receiver.lastIndexOf(pattern, start);
+    },
+    lastIndexOf$1: function($receiver, pattern) {
+      return this.lastIndexOf$2($receiver, pattern, null);
+    },
+    contains$1: function(receiver, other) {
+      if (other == null)
+        H.throwExpression(H.argumentErrorValue(other));
+      return H.stringContainsUnchecked(receiver, other, 0);
+    },
+    toString$0: function(receiver) {
+      return receiver;
+    },
+    get$hashCode: function(receiver) {
+      var t1, hash, i;
+      for (t1 = receiver.length, hash = 0, i = 0; i < t1; ++i) {
+        hash = 536870911 & hash + receiver.charCodeAt(i);
+        hash = 536870911 & hash + ((524287 & hash) << 10);
+        hash ^= hash >> 6;
+      }
+      hash = 536870911 & hash + ((67108863 & hash) << 3);
+      hash ^= hash >> 11;
+      return 536870911 & hash + ((16383 & hash) << 15);
+    },
+    get$runtimeType: function(receiver) {
+      return C.Type_String_k8F;
+    },
+    get$length: function(receiver) {
+      return receiver.length;
+    },
+    $index: function(receiver, index) {
+      H._checkIntNullable(index);
+      if (index >= receiver.length || index < 0)
+        throw H.wrapException(H.diagnoseIndexError(receiver, index));
+      return receiver[index];
+    },
+    $isPattern: 1,
+    $isString: 1
+  };
+  H._CastIterableBase.prototype = {
+    get$iterator: function(_) {
+      var t1 = this._source,
+        t2 = H._instanceType(this);
+      return new H.CastIterator(t1.get$iterator(t1), t2._eval$1("@<1>")._bind$1(t2._rest[1])._eval$1("CastIterator<1,2>"));
+    },
+    get$length: function(_) {
+      var t1 = this._source;
+      return t1.get$length(t1);
+    },
+    get$isEmpty: function(_) {
+      var t1 = this._source;
+      return t1.get$isEmpty(t1);
+    },
+    get$first: function(_) {
+      var t1 = this._source;
+      return H._instanceType(this)._rest[1]._as(t1.get$first(t1));
+    },
+    get$last: function(_) {
+      var t1 = this._source;
+      return H._instanceType(this)._rest[1]._as(t1.get$last(t1));
+    },
+    contains$1: function(_, other) {
+      return this._source.contains$1(0, other);
+    },
+    toString$0: function(_) {
+      return this._source.toString$0(0);
+    }
+  };
+  H.CastIterator.prototype = {
+    moveNext$0: function() {
+      return this._source.moveNext$0();
+    },
+    get$current: function() {
+      return this.$ti._rest[1]._as(this._source.get$current());
+    },
+    $isIterator: 1
+  };
+  H.CastIterable.prototype = {};
+  H._EfficientLengthCastIterable.prototype = {$isEfficientLengthIterable: 1};
+  H.CastMap.prototype = {
+    cast$2$0: function(_, RK, RV) {
+      var t1 = this.$ti;
+      return new H.CastMap(this._source, t1._eval$1("@<1>")._bind$1(t1._rest[1])._bind$1(RK)._bind$1(RV)._eval$1("CastMap<1,2,3,4>"));
+    },
+    containsKey$1: function(key) {
+      return this._source.containsKey$1(key);
+    },
+    $index: function(_, key) {
+      return this.$ti._rest[3]._as(this._source.$index(0, key));
+    },
+    remove$1: function(_, key) {
+      return this.$ti._rest[3]._as(this._source.remove$1(0, key));
+    },
+    forEach$1: function(_, f) {
+      this._source.forEach$1(0, new H.CastMap_forEach_closure(this, this.$ti._eval$1("~(3,4)")._check(f)));
+    },
+    get$keys: function() {
+      var t1 = this.$ti;
+      return H.CastIterable_CastIterable(this._source.get$keys(), t1._precomputed1, t1._rest[2]);
+    },
+    get$length: function(_) {
+      var t1 = this._source;
+      return t1.get$length(t1);
+    },
+    get$isEmpty: function(_) {
+      var t1 = this._source;
+      return t1.get$isEmpty(t1);
+    }
+  };
+  H.CastMap_forEach_closure.prototype = {
+    call$2: function(key, value) {
+      var t1 = this.$this.$ti;
+      t1._precomputed1._check(key);
+      t1._rest[1]._check(value);
+      this.f.call$2(t1._rest[2]._as(key), t1._rest[3]._as(value));
+    },
+    $signature: function() {
+      return this.$this.$ti._eval$1("Null(1,2)");
+    }
+  };
+  H.CodeUnits.prototype = {
+    get$length: function(_) {
+      return this._string.length;
+    },
+    $index: function(_, i) {
+      return C.JSString_methods.codeUnitAt$1(this._string, H._checkIntNullable(i));
+    }
+  };
+  H.EfficientLengthIterable.prototype = {};
+  H.ListIterable.prototype = {
+    get$iterator: function(_) {
+      var _this = this;
+      return new H.ListIterator(_this, _this.get$length(_this), H._instanceType(_this)._eval$1("ListIterator<ListIterable.E>"));
+    },
+    get$isEmpty: function(_) {
+      return this.get$length(this) === 0;
+    },
+    get$first: function(_) {
+      if (this.get$length(this) === 0)
+        throw H.wrapException(H.IterableElementError_noElement());
+      return this.elementAt$1(0, 0);
+    },
+    get$last: function(_) {
+      var _this = this;
+      if (_this.get$length(_this) === 0)
+        throw H.wrapException(H.IterableElementError_noElement());
+      return _this.elementAt$1(0, _this.get$length(_this) - 1);
+    },
+    contains$1: function(_, element) {
+      var i, _this = this,
+        $length = _this.get$length(_this);
+      for (i = 0; i < $length; ++i) {
+        if (J.$eq$(_this.elementAt$1(0, i), element))
+          return true;
+        if ($length !== _this.get$length(_this))
+          throw H.wrapException(P.ConcurrentModificationError$(_this));
+      }
+      return false;
+    },
+    join$1: function(_, separator) {
+      var first, t1, i, _this = this,
+        $length = _this.get$length(_this);
+      if (separator.length !== 0) {
+        if ($length === 0)
+          return "";
+        first = H.S(_this.elementAt$1(0, 0));
+        if ($length !== _this.get$length(_this))
+          throw H.wrapException(P.ConcurrentModificationError$(_this));
+        for (t1 = first, i = 1; i < $length; ++i) {
+          t1 = t1 + separator + H.S(_this.elementAt$1(0, i));
+          if ($length !== _this.get$length(_this))
+            throw H.wrapException(P.ConcurrentModificationError$(_this));
+        }
+        return t1.charCodeAt(0) == 0 ? t1 : t1;
+      } else {
+        for (i = 0, t1 = ""; i < $length; ++i) {
+          t1 += H.S(_this.elementAt$1(0, i));
+          if ($length !== _this.get$length(_this))
+            throw H.wrapException(P.ConcurrentModificationError$(_this));
+        }
+        return t1.charCodeAt(0) == 0 ? t1 : t1;
+      }
+    },
+    join$0: function($receiver) {
+      return this.join$1($receiver, "");
+    },
+    map$1$1: function(_, f, $T) {
+      var t1 = H._instanceType(this);
+      return new H.MappedListIterable(this, t1._bind$1($T)._eval$1("1(ListIterable.E)")._check(f), t1._eval$1("@<ListIterable.E>")._bind$1($T)._eval$1("MappedListIterable<1,2>"));
+    },
+    fold$1$2: function(_, initialValue, combine, $T) {
+      var $length, value, i, _this = this;
+      $T._check(initialValue);
+      H._instanceType(_this)._bind$1($T)._eval$1("1(1,ListIterable.E)")._check(combine);
+      $length = _this.get$length(_this);
+      for (value = initialValue, i = 0; i < $length; ++i) {
+        value = combine.call$2(value, _this.elementAt$1(0, i));
+        if ($length !== _this.get$length(_this))
+          throw H.wrapException(P.ConcurrentModificationError$(_this));
+      }
+      return value;
+    },
+    toList$1$growable: function(_, growable) {
+      var i, _this = this,
+        result = H.setRuntimeTypeInfo([], H._instanceType(_this)._eval$1("JSArray<ListIterable.E>"));
+      C.JSArray_methods.set$length(result, _this.get$length(_this));
+      for (i = 0; i < _this.get$length(_this); ++i)
+        C.JSArray_methods.$indexSet(result, i, _this.elementAt$1(0, i));
+      return result;
+    },
+    toList$0: function($receiver) {
+      return this.toList$1$growable($receiver, true);
+    },
+    toSet$0: function(_) {
+      var i, _this = this,
+        result = P.LinkedHashSet_LinkedHashSet(H._instanceType(_this)._eval$1("ListIterable.E"));
+      for (i = 0; i < _this.get$length(_this); ++i)
+        result.add$1(0, _this.elementAt$1(0, i));
+      return result;
+    }
+  };
+  H.SubListIterable.prototype = {
+    get$_endIndex: function() {
+      var $length = J.get$length$asx(this.__internal$_iterable),
+        t1 = this._endOrLength;
+      if (t1 == null || t1 > $length)
+        return $length;
+      return t1;
+    },
+    get$_startIndex: function() {
+      var $length = J.get$length$asx(this.__internal$_iterable),
+        t1 = this.__internal$_start;
+      if (t1 > $length)
+        return $length;
+      return t1;
+    },
+    get$length: function(_) {
+      var t2,
+        $length = J.get$length$asx(this.__internal$_iterable),
+        t1 = this.__internal$_start;
+      if (t1 >= $length)
+        return 0;
+      t2 = this._endOrLength;
+      if (t2 == null || t2 >= $length)
+        return $length - t1;
+      if (typeof t2 !== "number")
+        return t2.$sub();
+      return t2 - t1;
+    },
+    elementAt$1: function(_, index) {
+      var t1, _this = this,
+        realIndex = _this.get$_startIndex() + index;
+      if (index >= 0) {
+        t1 = _this.get$_endIndex();
+        if (typeof t1 !== "number")
+          return H.iae(t1);
+        t1 = realIndex >= t1;
+      } else
+        t1 = true;
+      if (t1)
+        throw H.wrapException(P.IndexError$(index, _this, "index", null, null));
+      return J.elementAt$1$ax(_this.__internal$_iterable, realIndex);
+    },
+    take$1: function(_, count) {
+      var t1, t2, newEnd, _this = this;
+      P.RangeError_checkNotNegative(count, "count");
+      t1 = _this._endOrLength;
+      t2 = _this.__internal$_start;
+      newEnd = t2 + count;
+      if (t1 == null)
+        return H.SubListIterable$(_this.__internal$_iterable, t2, newEnd, _this.$ti._precomputed1);
+      else {
+        if (t1 < newEnd)
+          return _this;
+        return H.SubListIterable$(_this.__internal$_iterable, t2, newEnd, _this.$ti._precomputed1);
+      }
+    }
+  };
+  H.ListIterator.prototype = {
+    get$current: function() {
+      return this.__internal$_current;
+    },
+    moveNext$0: function() {
+      var t3, _this = this,
+        t1 = _this.__internal$_iterable,
+        t2 = J.getInterceptor$asx(t1),
+        $length = t2.get$length(t1);
+      if (_this.__internal$_length !== $length)
+        throw H.wrapException(P.ConcurrentModificationError$(t1));
+      t3 = _this.__internal$_index;
+      if (t3 >= $length) {
+        _this.set$__internal$_current(null);
+        return false;
+      }
+      _this.set$__internal$_current(t2.elementAt$1(t1, t3));
+      ++_this.__internal$_index;
+      return true;
+    },
+    set$__internal$_current: function(_current) {
+      this.__internal$_current = this.$ti._precomputed1._check(_current);
+    },
+    $isIterator: 1
+  };
+  H.MappedIterable.prototype = {
+    get$iterator: function(_) {
+      var t1 = H._instanceType(this);
+      return new H.MappedIterator(J.get$iterator$ax(this.__internal$_iterable), this._f, t1._eval$1("@<1>")._bind$1(t1._rest[1])._eval$1("MappedIterator<1,2>"));
+    },
+    get$length: function(_) {
+      return J.get$length$asx(this.__internal$_iterable);
+    },
+    get$isEmpty: function(_) {
+      return J.get$isEmpty$asx(this.__internal$_iterable);
+    },
+    get$first: function(_) {
+      return this._f.call$1(J.get$first$ax(this.__internal$_iterable));
+    },
+    get$last: function(_) {
+      return this._f.call$1(J.get$last$ax(this.__internal$_iterable));
+    }
+  };
+  H.EfficientLengthMappedIterable.prototype = {$isEfficientLengthIterable: 1};
+  H.MappedIterator.prototype = {
+    moveNext$0: function() {
+      var _this = this,
+        t1 = _this._iterator;
+      if (t1.moveNext$0()) {
+        _this.set$__internal$_current(_this._f.call$1(t1.get$current()));
+        return true;
+      }
+      _this.set$__internal$_current(null);
+      return false;
+    },
+    get$current: function() {
+      return this.__internal$_current;
+    },
+    set$__internal$_current: function(_current) {
+      this.__internal$_current = this.$ti._rest[1]._check(_current);
+    }
+  };
+  H.MappedListIterable.prototype = {
+    get$length: function(_) {
+      return J.get$length$asx(this._source);
+    },
+    elementAt$1: function(_, index) {
+      return this._f.call$1(J.elementAt$1$ax(this._source, index));
+    }
+  };
+  H.WhereIterable.prototype = {
+    get$iterator: function(_) {
+      return new H.WhereIterator(J.get$iterator$ax(this.__internal$_iterable), this._f, this.$ti._eval$1("WhereIterator<1>"));
+    },
+    map$1$1: function(_, f, $T) {
+      var t1 = this.$ti;
+      return new H.MappedIterable(this, t1._bind$1($T)._eval$1("1(2)")._check(f), t1._eval$1("@<1>")._bind$1($T)._eval$1("MappedIterable<1,2>"));
+    }
+  };
+  H.WhereIterator.prototype = {
+    moveNext$0: function() {
+      var t1, t2;
+      for (t1 = this._iterator, t2 = this._f; t1.moveNext$0();)
+        if (H.boolConversionCheck(t2.call$1(t1.get$current())))
+          return true;
+      return false;
+    },
+    get$current: function() {
+      return this._iterator.get$current();
+    }
+  };
+  H.ExpandIterable.prototype = {
+    get$iterator: function(_) {
+      var t1 = this.$ti;
+      return new H.ExpandIterator(J.get$iterator$ax(this.__internal$_iterable), this._f, C.C_EmptyIterator, t1._eval$1("@<1>")._bind$1(t1._rest[1])._eval$1("ExpandIterator<1,2>"));
+    }
+  };
+  H.ExpandIterator.prototype = {
+    get$current: function() {
+      return this.__internal$_current;
+    },
+    moveNext$0: function() {
+      var t1, t2, _this = this;
+      if (_this._currentExpansion == null)
+        return false;
+      for (t1 = _this._iterator, t2 = _this._f; !_this._currentExpansion.moveNext$0();) {
+        _this.set$__internal$_current(null);
+        if (t1.moveNext$0()) {
+          _this.set$_currentExpansion(null);
+          _this.set$_currentExpansion(J.get$iterator$ax(t2.call$1(t1.get$current())));
+        } else
+          return false;
+      }
+      _this.set$__internal$_current(_this._currentExpansion.get$current());
+      return true;
+    },
+    set$_currentExpansion: function(_currentExpansion) {
+      this._currentExpansion = this.$ti._eval$1("Iterator<2>")._check(_currentExpansion);
+    },
+    set$__internal$_current: function(_current) {
+      this.__internal$_current = this.$ti._rest[1]._check(_current);
+    },
+    $isIterator: 1
+  };
+  H.SkipWhileIterable.prototype = {
+    get$iterator: function(_) {
+      return new H.SkipWhileIterator(J.get$iterator$ax(this.__internal$_iterable), this._f, this.$ti._eval$1("SkipWhileIterator<1>"));
+    }
+  };
+  H.SkipWhileIterator.prototype = {
+    moveNext$0: function() {
+      var t1, t2, _this = this;
+      if (!_this._hasSkipped) {
+        _this._hasSkipped = true;
+        for (t1 = _this._iterator, t2 = _this._f; t1.moveNext$0();)
+          if (!H.boolConversionCheck(t2.call$1(t1.get$current())))
+            return true;
+      }
+      return _this._iterator.moveNext$0();
+    },
+    get$current: function() {
+      return this._iterator.get$current();
+    }
+  };
+  H.EmptyIterator.prototype = {
+    moveNext$0: function() {
+      return false;
+    },
+    get$current: function() {
+      return null;
+    },
+    $isIterator: 1
+  };
+  H.FixedLengthListMixin.prototype = {
+    set$length: function(receiver, newLength) {
+      throw H.wrapException(P.UnsupportedError$("Cannot change the length of a fixed-length list"));
+    }
+  };
+  H.UnmodifiableListMixin.prototype = {
+    $indexSet: function(_, index, value) {
+      H._checkIntNullable(index);
+      H._instanceType(this)._eval$1("UnmodifiableListMixin.E")._check(value);
+      throw H.wrapException(P.UnsupportedError$("Cannot modify an unmodifiable list"));
+    },
+    set$length: function(_, newLength) {
+      throw H.wrapException(P.UnsupportedError$("Cannot change the length of an unmodifiable list"));
+    }
+  };
+  H.UnmodifiableListBase.prototype = {};
+  H.ReversedListIterable.prototype = {
+    get$length: function(_) {
+      return J.get$length$asx(this._source);
+    },
+    elementAt$1: function(_, index) {
+      var t1 = this._source,
+        t2 = J.getInterceptor$asx(t1);
+      return t2.elementAt$1(t1, t2.get$length(t1) - 1 - index);
+    }
+  };
+  H.Symbol.prototype = {
+    get$hashCode: function(_) {
+      var hash = this._hashCode;
+      if (hash != null)
+        return hash;
+      hash = 536870911 & 664597 * J.get$hashCode$(this.__internal$_name);
+      this._hashCode = hash;
+      return hash;
+    },
+    toString$0: function(_) {
+      return 'Symbol("' + H.S(this.__internal$_name) + '")';
+    },
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      return other instanceof H.Symbol && this.__internal$_name == other.__internal$_name;
+    }
+  };
+  H.ConstantMap.prototype = {
+    cast$2$0: function(_, RK, RV) {
+      var t1 = H._instanceType(this);
+      return P.Map_castFrom(this, t1._precomputed1, t1._rest[1], RK, RV);
+    },
+    get$isEmpty: function(_) {
+      return this.get$length(this) === 0;
+    },
+    toString$0: function(_) {
+      return P.MapBase_mapToString(this);
+    },
+    remove$1: function(_, key) {
+      return H.ConstantMap__throwUnmodifiable();
+    },
+    map$2$1: function(_, transform, K2, V2) {
+      var result = P.LinkedHashMap_LinkedHashMap$_empty(K2, V2);
+      this.forEach$1(0, new H.ConstantMap_map_closure(this, H._instanceType(this)._bind$1(K2)._bind$1(V2)._eval$1("MapEntry<1,2>(3,4)")._check(transform), result));
+      return result;
+    },
+    $isMap: 1
+  };
+  H.ConstantMap_map_closure.prototype = {
+    call$2: function(key, value) {
+      var t1 = H._instanceType(this.$this),
+        entry = this.transform.call$2(t1._precomputed1._check(key), t1._rest[1]._check(value));
+      this.result.$indexSet(0, entry.key, entry.value);
+    },
+    $signature: function() {
+      return H._instanceType(this.$this)._eval$1("Null(1,2)");
+    }
+  };
+  H.ConstantStringMap.prototype = {
+    get$length: function(_) {
+      return this.__js_helper$_length;
+    },
+    containsKey$1: function(key) {
+      if (typeof key != "string")
+        return false;
+      if ("__proto__" === key)
+        return false;
+      return this._jsObject.hasOwnProperty(key);
+    },
+    $index: function(_, key) {
+      if (!this.containsKey$1(key))
+        return null;
+      return this._fetch$1(key);
+    },
+    _fetch$1: function(key) {
+      return this._jsObject[H._checkStringNullable(key)];
+    },
+    forEach$1: function(_, f) {
+      var keys, t2, i, key,
+        t1 = H._instanceType(this);
+      t1._eval$1("~(1,2)")._check(f);
+      keys = this.__js_helper$_keys;
+      for (t2 = keys.length, t1 = t1._rest[1], i = 0; i < t2; ++i) {
+        key = keys[i];
+        f.call$2(key, t1._check(this._fetch$1(key)));
+      }
+    },
+    get$keys: function() {
+      return new H._ConstantMapKeyIterable(this, H._instanceType(this)._eval$1("_ConstantMapKeyIterable<1>"));
+    }
+  };
+  H._ConstantMapKeyIterable.prototype = {
+    get$iterator: function(_) {
+      var t1 = this.__js_helper$_map.__js_helper$_keys;
+      return new J.ArrayIterator(t1, t1.length, H._arrayInstanceType(t1)._eval$1("ArrayIterator<1>"));
+    },
+    get$length: function(_) {
+      return this.__js_helper$_map.__js_helper$_keys.length;
+    }
+  };
+  H.Instantiation.prototype = {
+    Instantiation$1: function(_genericClosure) {
+      if (false)
+        H.instantiatedGenericFunctionType(0, 0);
+    },
+    toString$0: function(_) {
+      var types = "<" + C.JSArray_methods.join$1([H.createRuntimeType(this.$ti._precomputed1)], ", ") + ">";
+      return H.S(this._genericClosure) + " with " + types;
+    }
+  };
+  H.Instantiation1.prototype = {
+    call$2: function(a0, a1) {
+      return this._genericClosure.call$1$2(a0, a1, this.$ti._rest[0]);
+    },
+    call$4: function(a0, a1, a2, a3) {
+      return this._genericClosure.call$1$4(a0, a1, a2, a3, this.$ti._rest[0]);
+    },
+    $signature: function() {
+      return H.instantiatedGenericFunctionType(H.closureFunctionType(this._genericClosure), this.$ti);
+    }
+  };
+  H.Primitives_initTicker_closure.prototype = {
+    call$0: function() {
+      return C.JSNumber_methods.floor$0(1000 * this.performance.now());
+    },
+    $signature: 36
+  };
+  H.TypeErrorDecoder.prototype = {
+    matchTypeError$1: function(message) {
+      var result, t1, _this = this,
+        match = new RegExp(_this._pattern).exec(message);
+      if (match == null)
+        return null;
+      result = Object.create(null);
+      t1 = _this._arguments;
+      if (t1 !== -1)
+        result.arguments = match[t1 + 1];
+      t1 = _this._argumentsExpr;
+      if (t1 !== -1)
+        result.argumentsExpr = match[t1 + 1];
+      t1 = _this._expr;
+      if (t1 !== -1)
+        result.expr = match[t1 + 1];
+      t1 = _this._method;
+      if (t1 !== -1)
+        result.method = match[t1 + 1];
+      t1 = _this._receiver;
+      if (t1 !== -1)
+        result.receiver = match[t1 + 1];
+      return result;
+    }
+  };
+  H.NullError.prototype = {
+    toString$0: function(_) {
+      var t1 = this._method;
+      if (t1 == null)
+        return "NoSuchMethodError: " + H.S(this.__js_helper$_message);
+      return "NoSuchMethodError: method not found: '" + t1 + "' on null";
+    },
+    $isNoSuchMethodError: 1
+  };
+  H.JsNoSuchMethodError.prototype = {
+    toString$0: function(_) {
+      var t2, _this = this,
+        _s38_ = "NoSuchMethodError: method not found: '",
+        t1 = _this._method;
+      if (t1 == null)
+        return "NoSuchMethodError: " + H.S(_this.__js_helper$_message);
+      t2 = _this._receiver;
+      if (t2 == null)
+        return _s38_ + t1 + "' (" + H.S(_this.__js_helper$_message) + ")";
+      return _s38_ + t1 + "' on '" + t2 + "' (" + H.S(_this.__js_helper$_message) + ")";
+    },
+    $isNoSuchMethodError: 1
+  };
+  H.UnknownJsTypeError.prototype = {
+    toString$0: function(_) {
+      var t1 = this.__js_helper$_message;
+      return t1.length === 0 ? "Error" : "Error: " + t1;
+    }
+  };
+  H.ExceptionAndStackTrace.prototype = {};
+  H.unwrapException_saveStackTrace.prototype = {
+    call$1: function(error) {
+      if (type$.Error._is(error))
+        if (error.$thrownJsError == null)
+          error.$thrownJsError = this.ex;
+      return error;
+    },
+    $signature: 18
+  };
+  H._StackTrace.prototype = {
+    toString$0: function(_) {
+      var trace,
+        t1 = this._trace;
+      if (t1 != null)
+        return t1;
+      t1 = this._exception;
+      trace = t1 !== null && typeof t1 === "object" ? t1.stack : null;
+      return this._trace = trace == null ? "" : trace;
+    },
+    $isStackTrace: 1
+  };
+  H.Closure.prototype = {
+    toString$0: function(_) {
+      var $constructor = this.constructor,
+        $name = $constructor == null ? null : $constructor.name;
+      return "Closure '" + H.unminifyOrTag($name == null ? "unknown" : $name) + "'";
+    },
+    $isFunction: 1,
+    get$$call: function() {
+      return this;
+    },
+    "call*": "call$1",
+    $requiredArgCount: 1,
+    $defaultValues: null
+  };
+  H.TearOffClosure.prototype = {};
+  H.StaticClosure.prototype = {
+    toString$0: function(_) {
+      var $name = this.$static_name;
+      if ($name == null)
+        return "Closure of unknown static method";
+      return "Closure '" + H.unminifyOrTag($name) + "'";
+    }
+  };
+  H.BoundClosure.prototype = {
+    $eq: function(_, other) {
+      var _this = this;
+      if (other == null)
+        return false;
+      if (_this === other)
+        return true;
+      if (!(other instanceof H.BoundClosure))
+        return false;
+      return _this._self === other._self && _this._target === other._target && _this._receiver === other._receiver;
+    },
+    get$hashCode: function(_) {
+      var receiverHashCode,
+        t1 = this._receiver;
+      if (t1 == null)
+        receiverHashCode = H.Primitives_objectHashCode(this._self);
+      else
+        receiverHashCode = typeof t1 !== "object" ? J.get$hashCode$(t1) : H.Primitives_objectHashCode(t1);
+      return (receiverHashCode ^ H.Primitives_objectHashCode(this._target)) >>> 0;
+    },
+    toString$0: function(_) {
+      var receiver = this._receiver;
+      if (receiver == null)
+        receiver = this._self;
+      return "Closure '" + H.S(this._name) + "' of " + ("Instance of '" + H.S(H.Primitives_objectTypeName(receiver)) + "'");
+    }
+  };
+  H.TypeErrorImplementation.prototype = {
+    toString$0: function(_) {
+      return this.message;
+    },
+    get$message: function(receiver) {
+      return this.message;
+    }
+  };
+  H.RuntimeError.prototype = {
+    toString$0: function(_) {
+      return "RuntimeError: " + H.S(this.message);
+    },
+    get$message: function(receiver) {
+      return this.message;
+    }
+  };
+  H._AssertionError.prototype = {
+    toString$0: function(_) {
+      return "Assertion failed: " + P.Error_safeToString(this.message);
+    }
+  };
+  H.JsLinkedHashMap.prototype = {
+    get$length: function(_) {
+      return this.__js_helper$_length;
+    },
+    get$isEmpty: function(_) {
+      return this.__js_helper$_length === 0;
+    },
+    get$keys: function() {
+      return new H.LinkedHashMapKeyIterable(this, H._instanceType(this)._eval$1("LinkedHashMapKeyIterable<1>"));
+    },
+    get$values: function() {
+      var t1 = H._instanceType(this);
+      return H.MappedIterable_MappedIterable(this.get$keys(), new H.JsLinkedHashMap_values_closure(this), t1._precomputed1, t1._rest[1]);
+    },
+    containsKey$1: function(key) {
+      var strings, nums, _this = this;
+      if (typeof key == "string") {
+        strings = _this.__js_helper$_strings;
+        if (strings == null)
+          return false;
+        return _this._containsTableEntry$2(strings, key);
+      } else if (typeof key == "number" && (key & 0x3ffffff) === key) {
+        nums = _this.__js_helper$_nums;
+        if (nums == null)
+          return false;
+        return _this._containsTableEntry$2(nums, key);
+      } else
+        return _this.internalContainsKey$1(key);
+    },
+    internalContainsKey$1: function(key) {
+      var _this = this,
+        rest = _this.__js_helper$_rest;
+      if (rest == null)
+        return false;
+      return _this.internalFindBucketIndex$2(_this._getTableBucket$2(rest, _this.internalComputeHashCode$1(key)), key) >= 0;
+    },
+    addAll$1: function(_, other) {
+      H._instanceType(this)._eval$1("Map<1,2>")._check(other).forEach$1(0, new H.JsLinkedHashMap_addAll_closure(this));
+    },
+    $index: function(_, key) {
+      var strings, cell, t1, nums, _this = this, _null = null;
+      if (typeof key == "string") {
+        strings = _this.__js_helper$_strings;
+        if (strings == null)
+          return _null;
+        cell = _this._getTableCell$2(strings, key);
+        t1 = cell == null ? _null : cell.hashMapCellValue;
+        return t1;
+      } else if (typeof key == "number" && (key & 0x3ffffff) === key) {
+        nums = _this.__js_helper$_nums;
+        if (nums == null)
+          return _null;
+        cell = _this._getTableCell$2(nums, key);
+        t1 = cell == null ? _null : cell.hashMapCellValue;
+        return t1;
+      } else
+        return _this.internalGet$1(key);
+    },
+    internalGet$1: function(key) {
+      var bucket, index, _this = this,
+        rest = _this.__js_helper$_rest;
+      if (rest == null)
+        return null;
+      bucket = _this._getTableBucket$2(rest, _this.internalComputeHashCode$1(key));
+      index = _this.internalFindBucketIndex$2(bucket, key);
+      if (index < 0)
+        return null;
+      return bucket[index].hashMapCellValue;
+    },
+    $indexSet: function(_, key, value) {
+      var strings, nums, _this = this,
+        t1 = H._instanceType(_this);
+      t1._precomputed1._check(key);
+      t1._rest[1]._check(value);
+      if (typeof key == "string") {
+        strings = _this.__js_helper$_strings;
+        _this.__js_helper$_addHashTableEntry$3(strings == null ? _this.__js_helper$_strings = _this._newHashTable$0() : strings, key, value);
+      } else if (typeof key == "number" && (key & 0x3ffffff) === key) {
+        nums = _this.__js_helper$_nums;
+        _this.__js_helper$_addHashTableEntry$3(nums == null ? _this.__js_helper$_nums = _this._newHashTable$0() : nums, key, value);
+      } else
+        _this.internalSet$2(key, value);
+    },
+    internalSet$2: function(key, value) {
+      var rest, hash, bucket, index, _this = this,
+        t1 = H._instanceType(_this);
+      t1._precomputed1._check(key);
+      t1._rest[1]._check(value);
+      rest = _this.__js_helper$_rest;
+      if (rest == null)
+        rest = _this.__js_helper$_rest = _this._newHashTable$0();
+      hash = _this.internalComputeHashCode$1(key);
+      bucket = _this._getTableBucket$2(rest, hash);
+      if (bucket == null)
+        _this._setTableEntry$3(rest, hash, [_this._newLinkedCell$2(key, value)]);
+      else {
+        index = _this.internalFindBucketIndex$2(bucket, key);
+        if (index >= 0)
+          bucket[index].hashMapCellValue = value;
+        else
+          bucket.push(_this._newLinkedCell$2(key, value));
+      }
+    },
+    putIfAbsent$2: function(key, ifAbsent) {
+      var value, _this = this,
+        t1 = H._instanceType(_this);
+      t1._precomputed1._check(key);
+      t1._eval$1("2()")._check(ifAbsent);
+      if (_this.containsKey$1(key))
+        return _this.$index(0, key);
+      value = ifAbsent.call$0();
+      _this.$indexSet(0, key, value);
+      return value;
+    },
+    remove$1: function(_, key) {
+      var _this = this;
+      if (typeof key == "string")
+        return _this.__js_helper$_removeHashTableEntry$2(_this.__js_helper$_strings, key);
+      else if (typeof key == "number" && (key & 0x3ffffff) === key)
+        return _this.__js_helper$_removeHashTableEntry$2(_this.__js_helper$_nums, key);
+      else
+        return _this.internalRemove$1(key);
+    },
+    internalRemove$1: function(key) {
+      var hash, bucket, index, cell, _this = this,
+        rest = _this.__js_helper$_rest;
+      if (rest == null)
+        return null;
+      hash = _this.internalComputeHashCode$1(key);
+      bucket = _this._getTableBucket$2(rest, hash);
+      index = _this.internalFindBucketIndex$2(bucket, key);
+      if (index < 0)
+        return null;
+      cell = bucket.splice(index, 1)[0];
+      _this.__js_helper$_unlinkCell$1(cell);
+      if (bucket.length === 0)
+        _this._deleteTableEntry$2(rest, hash);
+      return cell.hashMapCellValue;
+    },
+    clear$0: function(_) {
+      var _this = this;
+      if (_this.__js_helper$_length > 0) {
+        _this.__js_helper$_strings = _this.__js_helper$_nums = _this.__js_helper$_rest = _this._first = _this._last = null;
+        _this.__js_helper$_length = 0;
+        _this._modified$0();
+      }
+    },
+    forEach$1: function(_, action) {
+      var cell, modifications, _this = this;
+      H._instanceType(_this)._eval$1("~(1,2)")._check(action);
+      cell = _this._first;
+      modifications = _this._modifications;
+      for (; cell != null;) {
+        action.call$2(cell.hashMapCellKey, cell.hashMapCellValue);
+        if (modifications !== _this._modifications)
+          throw H.wrapException(P.ConcurrentModificationError$(_this));
+        cell = cell._next;
+      }
+    },
+    __js_helper$_addHashTableEntry$3: function(table, key, value) {
+      var cell, _this = this,
+        t1 = H._instanceType(_this);
+      t1._precomputed1._check(key);
+      t1._rest[1]._check(value);
+      cell = _this._getTableCell$2(table, key);
+      if (cell == null)
+        _this._setTableEntry$3(table, key, _this._newLinkedCell$2(key, value));
+      else
+        cell.hashMapCellValue = value;
+    },
+    __js_helper$_removeHashTableEntry$2: function(table, key) {
+      var cell;
+      if (table == null)
+        return null;
+      cell = this._getTableCell$2(table, key);
+      if (cell == null)
+        return null;
+      this.__js_helper$_unlinkCell$1(cell);
+      this._deleteTableEntry$2(table, key);
+      return cell.hashMapCellValue;
+    },
+    _modified$0: function() {
+      this._modifications = this._modifications + 1 & 67108863;
+    },
+    _newLinkedCell$2: function(key, value) {
+      var last, _this = this,
+        t1 = H._instanceType(_this),
+        cell = new H.LinkedHashMapCell(t1._precomputed1._check(key), t1._rest[1]._check(value));
+      if (_this._first == null)
+        _this._first = _this._last = cell;
+      else {
+        last = _this._last;
+        cell._previous = last;
+        _this._last = last._next = cell;
+      }
+      ++_this.__js_helper$_length;
+      _this._modified$0();
+      return cell;
+    },
+    __js_helper$_unlinkCell$1: function(cell) {
+      var _this = this,
+        previous = cell._previous,
+        next = cell._next;
+      if (previous == null) {
+        H.assertHelper(cell == _this._first);
+        _this._first = next;
+      } else
+        previous._next = next;
+      if (next == null) {
+        H.assertHelper(cell == _this._last);
+        _this._last = previous;
+      } else
+        next._previous = previous;
+      --_this.__js_helper$_length;
+      _this._modified$0();
+    },
+    internalComputeHashCode$1: function(key) {
+      return J.get$hashCode$(key) & 0x3ffffff;
+    },
+    internalFindBucketIndex$2: function(bucket, key) {
+      var $length, i;
+      if (bucket == null)
+        return -1;
+      $length = bucket.length;
+      for (i = 0; i < $length; ++i)
+        if (J.$eq$(bucket[i].hashMapCellKey, key))
+          return i;
+      return -1;
+    },
+    toString$0: function(_) {
+      return P.MapBase_mapToString(this);
+    },
+    _getTableCell$2: function(table, key) {
+      return table[key];
+    },
+    _getTableBucket$2: function(table, key) {
+      return table[key];
+    },
+    _setTableEntry$3: function(table, key, value) {
+      H.assertHelper(value != null);
+      table[key] = value;
+    },
+    _deleteTableEntry$2: function(table, key) {
+      delete table[key];
+    },
+    _containsTableEntry$2: function(table, key) {
+      return this._getTableCell$2(table, key) != null;
+    },
+    _newHashTable$0: function() {
+      var _s20_ = "<non-identifier-key>",
+        table = Object.create(null);
+      this._setTableEntry$3(table, _s20_, table);
+      this._deleteTableEntry$2(table, _s20_);
+      return table;
+    },
+    $isLinkedHashMap: 1
+  };
+  H.JsLinkedHashMap_values_closure.prototype = {
+    call$1: function(each) {
+      var t1 = this.$this;
+      return t1.$index(0, H._instanceType(t1)._precomputed1._check(each));
+    },
+    $signature: function() {
+      return H._instanceType(this.$this)._eval$1("2(1)");
+    }
+  };
+  H.JsLinkedHashMap_addAll_closure.prototype = {
+    call$2: function(key, value) {
+      var t1 = this.$this,
+        t2 = H._instanceType(t1);
+      t1.$indexSet(0, t2._precomputed1._check(key), t2._rest[1]._check(value));
+    },
+    $signature: function() {
+      return H._instanceType(this.$this)._eval$1("Null(1,2)");
+    }
+  };
+  H.LinkedHashMapCell.prototype = {};
+  H.LinkedHashMapKeyIterable.prototype = {
+    get$length: function(_) {
+      return this.__js_helper$_map.__js_helper$_length;
+    },
+    get$isEmpty: function(_) {
+      return this.__js_helper$_map.__js_helper$_length === 0;
+    },
+    get$iterator: function(_) {
+      var t1 = this.__js_helper$_map,
+        t2 = new H.LinkedHashMapKeyIterator(t1, t1._modifications, this.$ti._eval$1("LinkedHashMapKeyIterator<1>"));
+      t2._cell = t1._first;
+      return t2;
+    },
+    contains$1: function(_, element) {
+      return this.__js_helper$_map.containsKey$1(element);
+    }
+  };
+  H.LinkedHashMapKeyIterator.prototype = {
+    get$current: function() {
+      return this.__js_helper$_current;
+    },
+    moveNext$0: function() {
+      var _this = this,
+        t1 = _this.__js_helper$_map;
+      if (_this._modifications !== t1._modifications)
+        throw H.wrapException(P.ConcurrentModificationError$(t1));
+      else {
+        t1 = _this._cell;
+        if (t1 == null) {
+          _this.set$__js_helper$_current(null);
+          return false;
+        } else {
+          _this.set$__js_helper$_current(t1.hashMapCellKey);
+          _this._cell = _this._cell._next;
+          return true;
+        }
+      }
+    },
+    set$__js_helper$_current: function(_current) {
+      this.__js_helper$_current = this.$ti._precomputed1._check(_current);
+    },
+    $isIterator: 1
+  };
+  H.initHooks_closure.prototype = {
+    call$1: function(o) {
+      return this.getTag(o);
+    },
+    $signature: 18
+  };
+  H.initHooks_closure0.prototype = {
+    call$2: function(o, tag) {
+      return this.getUnknownTag(o, tag);
+    },
+    $signature: 104
+  };
+  H.initHooks_closure1.prototype = {
+    call$1: function(tag) {
+      return this.prototypeForTag(H._checkStringNullable(tag));
+    },
+    $signature: 94
+  };
+  H.JSSyntaxRegExp.prototype = {
+    toString$0: function(_) {
+      return "RegExp/" + this.pattern + "/" + this._nativeRegExp.flags;
+    },
+    get$_nativeGlobalVersion: function() {
+      var _this = this,
+        t1 = _this._nativeGlobalRegExp;
+      if (t1 != null)
+        return t1;
+      t1 = _this._nativeRegExp;
+      return _this._nativeGlobalRegExp = H.JSSyntaxRegExp_makeNative(_this.pattern, t1.multiline, !t1.ignoreCase, t1.unicode, t1.dotAll, true);
+    },
+    get$_nativeAnchoredVersion: function() {
+      var _this = this,
+        t1 = _this._nativeAnchoredRegExp;
+      if (t1 != null)
+        return t1;
+      t1 = _this._nativeRegExp;
+      return _this._nativeAnchoredRegExp = H.JSSyntaxRegExp_makeNative(_this.pattern + "|()", t1.multiline, !t1.ignoreCase, t1.unicode, t1.dotAll, true);
+    },
+    firstMatch$1: function(string) {
+      var m;
+      if (typeof string != "string")
+        H.throwExpression(H.argumentErrorValue(string));
+      m = this._nativeRegExp.exec(string);
+      if (m == null)
+        return null;
+      return H._MatchImplementation$(this, m);
+    },
+    allMatches$2: function(_, string, start) {
+      var t1 = string.length;
+      if (start > t1)
+        throw H.wrapException(P.RangeError$range(start, 0, t1, null, null));
+      return new H._AllMatchesIterable(this, string, start);
+    },
+    allMatches$1: function($receiver, string) {
+      return this.allMatches$2($receiver, string, 0);
+    },
+    _execGlobal$2: function(string, start) {
+      var match,
+        regexp = this.get$_nativeGlobalVersion();
+      regexp.lastIndex = start;
+      match = regexp.exec(string);
+      if (match == null)
+        return null;
+      return H._MatchImplementation$(this, match);
+    },
+    _execAnchored$2: function(string, start) {
+      var match,
+        regexp = this.get$_nativeAnchoredVersion();
+      regexp.lastIndex = start;
+      match = regexp.exec(string);
+      if (match == null)
+        return null;
+      if (0 >= match.length)
+        return H.ioore(match, -1);
+      if (match.pop() != null)
+        return null;
+      return H._MatchImplementation$(this, match);
+    },
+    matchAsPrefix$2: function(_, string, start) {
+      if (start < 0 || start > string.length)
+        throw H.wrapException(P.RangeError$range(start, 0, string.length, null, null));
+      return this._execAnchored$2(string, start);
+    },
+    $isPattern: 1,
+    $isRegExp: 1
+  };
+  H._MatchImplementation.prototype = {
+    get$start: function() {
+      return this._match.index;
+    },
+    get$end: function() {
+      var t1 = this._match;
+      return t1.index + t1[0].length;
+    },
+    $index: function(_, index) {
+      var t1;
+      H._checkIntNullable(index);
+      t1 = this._match;
+      if (index >= t1.length)
+        return H.ioore(t1, index);
+      return t1[index];
+    },
+    $isMatch: 1,
+    $isRegExpMatch: 1
+  };
+  H._AllMatchesIterable.prototype = {
+    get$iterator: function(_) {
+      return new H._AllMatchesIterator(this._re, this.__js_helper$_string, this._start);
+    }
+  };
+  H._AllMatchesIterator.prototype = {
+    get$current: function() {
+      return this.__js_helper$_current;
+    },
+    moveNext$0: function() {
+      var t2, t3, match, nextIndex, _this = this,
+        t1 = _this.__js_helper$_string;
+      if (t1 == null)
+        return false;
+      t2 = _this._nextIndex;
+      if (t2 <= t1.length) {
+        t3 = _this._regExp;
+        match = t3._execGlobal$2(t1, t2);
+        if (match != null) {
+          _this.__js_helper$_current = match;
+          nextIndex = match.get$end();
+          if (match._match.index === nextIndex) {
+            if (t3._nativeRegExp.unicode) {
+              t1 = _this._nextIndex;
+              t2 = t1 + 1;
+              t3 = _this.__js_helper$_string;
+              if (t2 < t3.length) {
+                t1 = J.getInterceptor$s(t3).codeUnitAt$1(t3, t1);
+                if (t1 >= 55296 && t1 <= 56319) {
+                  t1 = C.JSString_methods.codeUnitAt$1(t3, t2);
+                  t1 = t1 >= 56320 && t1 <= 57343;
+                } else
+                  t1 = false;
+              } else
+                t1 = false;
+            } else
+              t1 = false;
+            nextIndex = (t1 ? nextIndex + 1 : nextIndex) + 1;
+          }
+          _this._nextIndex = nextIndex;
+          return true;
+        }
+      }
+      _this.__js_helper$_string = _this.__js_helper$_current = null;
+      return false;
+    },
+    $isIterator: 1
+  };
+  H.StringMatch.prototype = {
+    get$end: function() {
+      return this.start + this.pattern.length;
+    },
+    $index: function(_, g) {
+      H._checkIntNullable(g);
+      if (g !== 0)
+        H.throwExpression(P.RangeError$value(g, null));
+      return this.pattern;
+    },
+    $isMatch: 1,
+    get$start: function() {
+      return this.start;
+    }
+  };
+  H._StringAllMatchesIterable.prototype = {
+    get$iterator: function(_) {
+      return new H._StringAllMatchesIterator(this._input, this._pattern, this.__js_helper$_index);
+    },
+    get$first: function(_) {
+      var t1 = this._pattern,
+        index = this._input.indexOf(t1, this.__js_helper$_index);
+      if (index >= 0)
+        return new H.StringMatch(index, t1);
+      throw H.wrapException(H.IterableElementError_noElement());
+    }
+  };
+  H._StringAllMatchesIterator.prototype = {
+    moveNext$0: function() {
+      var index, end, _this = this,
+        t1 = _this.__js_helper$_index,
+        t2 = _this._pattern,
+        t3 = t2.length,
+        t4 = _this._input,
+        t5 = t4.length;
+      if (t1 + t3 > t5) {
+        _this.__js_helper$_current = null;
+        return false;
+      }
+      index = t4.indexOf(t2, t1);
+      if (index < 0) {
+        _this.__js_helper$_index = t5 + 1;
+        _this.__js_helper$_current = null;
+        return false;
+      }
+      end = index + t3;
+      _this.__js_helper$_current = new H.StringMatch(index, t2);
+      _this.__js_helper$_index = end === _this.__js_helper$_index ? end + 1 : end;
+      return true;
+    },
+    get$current: function() {
+      return this.__js_helper$_current;
+    },
+    $isIterator: 1
+  };
+  H.NativeByteBuffer.prototype = {
+    get$runtimeType: function(receiver) {
+      return C.Type_ByteBuffer_RkP;
+    },
+    $isNativeByteBuffer: 1,
+    $isByteBuffer: 1
+  };
+  H.NativeTypedData.prototype = {$isNativeTypedData: 1};
+  H.NativeByteData.prototype = {
+    get$runtimeType: function(receiver) {
+      return C.Type_ByteData_zNC;
+    }
+  };
+  H.NativeTypedArray.prototype = {
+    get$length: function(receiver) {
+      return receiver.length;
+    },
+    $isJavaScriptIndexingBehavior: 1
+  };
+  H.NativeTypedArrayOfDouble.prototype = {
+    $index: function(receiver, index) {
+      H._checkIntNullable(index);
+      H._checkValidIndex(index, receiver, receiver.length);
+      return receiver[index];
+    },
+    $indexSet: function(receiver, index, value) {
+      H._checkIntNullable(index);
+      H._checkDoubleNullable(value);
+      H._checkValidIndex(index, receiver, receiver.length);
+      receiver[index] = value;
+    },
+    $isEfficientLengthIterable: 1,
+    $isIterable: 1,
+    $isList: 1
+  };
+  H.NativeTypedArrayOfInt.prototype = {
+    $indexSet: function(receiver, index, value) {
+      H._checkIntNullable(index);
+      H._checkIntNullable(value);
+      H._checkValidIndex(index, receiver, receiver.length);
+      receiver[index] = value;
+    },
+    $isEfficientLengthIterable: 1,
+    $isIterable: 1,
+    $isList: 1
+  };
+  H.NativeFloat32List.prototype = {
+    get$runtimeType: function(receiver) {
+      return C.Type_Float32List_LB7;
+    }
+  };
+  H.NativeFloat64List.prototype = {
+    get$runtimeType: function(receiver) {
+      return C.Type_Float64List_LB7;
+    }
+  };
+  H.NativeInt16List.prototype = {
+    get$runtimeType: function(receiver) {
+      return C.Type_Int16List_uXf;
+    },
+    $index: function(receiver, index) {
+      H._checkIntNullable(index);
+      H._checkValidIndex(index, receiver, receiver.length);
+      return receiver[index];
+    }
+  };
+  H.NativeInt32List.prototype = {
+    get$runtimeType: function(receiver) {
+      return C.Type_Int32List_O50;
+    },
+    $index: function(receiver, index) {
+      H._checkIntNullable(index);
+      H._checkValidIndex(index, receiver, receiver.length);
+      return receiver[index];
+    }
+  };
+  H.NativeInt8List.prototype = {
+    get$runtimeType: function(receiver) {
+      return C.Type_Int8List_ekJ;
+    },
+    $index: function(receiver, index) {
+      H._checkIntNullable(index);
+      H._checkValidIndex(index, receiver, receiver.length);
+      return receiver[index];
+    }
+  };
+  H.NativeUint16List.prototype = {
+    get$runtimeType: function(receiver) {
+      return C.Type_Uint16List_2bx;
+    },
+    $index: function(receiver, index) {
+      H._checkIntNullable(index);
+      H._checkValidIndex(index, receiver, receiver.length);
+      return receiver[index];
+    }
+  };
+  H.NativeUint32List.prototype = {
+    get$runtimeType: function(receiver) {
+      return C.Type_Uint32List_2bx;
+    },
+    $index: function(receiver, index) {
+      H._checkIntNullable(index);
+      H._checkValidIndex(index, receiver, receiver.length);
+      return receiver[index];
+    },
+    sublist$2: function(receiver, start, end) {
+      return new Uint32Array(receiver.subarray(start, H._checkValidRange(start, end, receiver.length)));
+    },
+    $isUint32List: 1
+  };
+  H.NativeUint8ClampedList.prototype = {
+    get$runtimeType: function(receiver) {
+      return C.Type_Uint8ClampedList_Jik;
+    },
+    get$length: function(receiver) {
+      return receiver.length;
+    },
+    $index: function(receiver, index) {
+      H._checkIntNullable(index);
+      H._checkValidIndex(index, receiver, receiver.length);
+      return receiver[index];
+    }
+  };
+  H.NativeUint8List.prototype = {
+    get$runtimeType: function(receiver) {
+      return C.Type_Uint8List_WLA;
+    },
+    get$length: function(receiver) {
+      return receiver.length;
+    },
+    $index: function(receiver, index) {
+      H._checkIntNullable(index);
+      H._checkValidIndex(index, receiver, receiver.length);
+      return receiver[index];
+    },
+    sublist$2: function(receiver, start, end) {
+      return new Uint8Array(receiver.subarray(start, H._checkValidRange(start, end, receiver.length)));
+    },
+    $isNativeUint8List: 1,
+    $isUint8List: 1
+  };
+  H._NativeTypedArrayOfDouble_NativeTypedArray_ListMixin.prototype = {};
+  H._NativeTypedArrayOfDouble_NativeTypedArray_ListMixin_FixedLengthListMixin.prototype = {};
+  H._NativeTypedArrayOfInt_NativeTypedArray_ListMixin.prototype = {};
+  H._NativeTypedArrayOfInt_NativeTypedArray_ListMixin_FixedLengthListMixin.prototype = {};
+  H.Rti.prototype = {
+    _eval$1: function(recipe) {
+      return H._Universe_evalInEnvironment(init.typeUniverse, this, recipe);
+    },
+    _bind$1: function(typeOrTuple) {
+      return H._Universe_bind(init.typeUniverse, this, typeOrTuple);
+    }
+  };
+  H._FunctionParameters.prototype = {};
+  H._Type.prototype = {
+    get$hashCode: function(_) {
+      var s,
+        t1 = this._hashCode;
+      if (t1 == null) {
+        s = this._rti._canonicalRecipe;
+        if (H.assertTest(typeof s == "string"))
+          H.assertThrow("Missing canonical recipe");
+        t1 = this._hashCode = C.JSString_methods.get$hashCode(s);
+      }
+      return t1;
+    },
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      return other instanceof H._Type && this._rti == other._rti;
+    },
+    toString$0: function(_) {
+      return H._rtiToString(this._rti, null);
+    },
+    $isType: 1
+  };
+  H._Error.prototype = {
+    toString$0: function(_) {
+      return this._message;
+    }
+  };
+  H._CastError.prototype = {};
+  H._TypeError.prototype = {
+    get$message: function(_) {
+      return this._message;
+    }
+  };
+  P._AsyncRun__initializeScheduleImmediate_internalCallback.prototype = {
+    call$1: function(_) {
+      var t1 = this._box_0,
+        f = t1.storedCallback;
+      t1.storedCallback = null;
+      f.call$0();
+    },
+    $signature: 3
+  };
+  P._AsyncRun__initializeScheduleImmediate_closure.prototype = {
+    call$1: function(callback) {
+      var t1, t2;
+      type$.void_Function._check(callback);
+      t1 = this._box_0;
+      H.assertHelper(t1.storedCallback == null);
+      t1.storedCallback = callback;
+      t1 = this.div;
+      t2 = this.span;
+      t1.firstChild ? t1.removeChild(t2) : t1.appendChild(t2);
+    },
+    $signature: 91
+  };
+  P._AsyncRun__scheduleImmediateJsOverride_internalCallback.prototype = {
+    call$0: function() {
+      this.callback.call$0();
+    },
+    $signature: 0
+  };
+  P._AsyncRun__scheduleImmediateWithSetImmediate_internalCallback.prototype = {
+    call$0: function() {
+      this.callback.call$0();
+    },
+    $signature: 0
+  };
+  P._TimerImpl.prototype = {
+    _TimerImpl$2: function(milliseconds, callback) {
+      if (self.setTimeout != null)
+        this._handle = self.setTimeout(H.convertDartClosureToJS(new P._TimerImpl_internalCallback(this, callback), 0), milliseconds);
+      else
+        throw H.wrapException(P.UnsupportedError$("`setTimeout()` not found."));
+    },
+    _TimerImpl$periodic$2: function(milliseconds, callback) {
+      if (self.setTimeout != null)
+        this._handle = self.setInterval(H.convertDartClosureToJS(new P._TimerImpl$periodic_closure(this, milliseconds, Date.now(), callback), 0), milliseconds);
+      else
+        throw H.wrapException(P.UnsupportedError$("Periodic timer."));
+    },
+    cancel$0: function() {
+      if (self.setTimeout != null) {
+        var t1 = this._handle;
+        if (t1 == null)
+          return;
+        if (this._once)
+          self.clearTimeout(t1);
+        else
+          self.clearInterval(t1);
+        this._handle = null;
+      } else
+        throw H.wrapException(P.UnsupportedError$("Canceling a timer."));
+    },
+    $isTimer: 1
+  };
+  P._TimerImpl_internalCallback.prototype = {
+    call$0: function() {
+      var t1 = this.$this;
+      t1._handle = null;
+      t1._tick = 1;
+      this.callback.call$0();
+    },
+    $signature: 1
+  };
+  P._TimerImpl$periodic_closure.prototype = {
+    call$0: function() {
+      var duration, _this = this,
+        t1 = _this.$this,
+        tick = t1._tick + 1,
+        t2 = _this.milliseconds;
+      if (t2 > 0) {
+        duration = Date.now() - _this.start;
+        if (duration > (tick + 1) * t2)
+          tick = C.JSInt_methods.$tdiv(duration, t2);
+      }
+      t1._tick = tick;
+      _this.callback.call$1(t1);
+    },
+    $signature: 0
+  };
+  P._AsyncAwaitCompleter.prototype = {
+    complete$1: function(value) {
+      var t2, t3,
+        t1 = this.$ti;
+      t1._eval$1("1/")._check(value);
+      t2 = !this.isSync || t1._eval$1("Future<1>")._is(value);
+      t3 = this._future;
+      if (t2)
+        t3._asyncComplete$1(value);
+      else
+        t3._completeWithValue$1(t1._precomputed1._check(value));
+    },
+    completeError$2: function(e, st) {
+      var t1 = this._future;
+      if (this.isSync)
+        t1._completeError$2(e, st);
+      else
+        t1._asyncCompleteError$2(e, st);
+    },
+    $isCompleter: 1
+  };
+  P._awaitOnObject_closure.prototype = {
+    call$1: function(result) {
+      return this.bodyFunction.call$2(0, result);
+    },
+    $signature: 15
+  };
+  P._awaitOnObject_closure0.prototype = {
+    call$2: function(error, stackTrace) {
+      this.bodyFunction.call$2(1, new H.ExceptionAndStackTrace(error, type$.StackTrace._check(stackTrace)));
+    },
+    $signature: 5
+  };
+  P._wrapJsFunctionForAsync_closure.prototype = {
+    call$2: function(errorCode, result) {
+      this.$protected(H._checkIntNullable(errorCode), result);
+    },
+    $signature: 89
+  };
+  P._BroadcastStream.prototype = {
+    get$isBroadcast: function() {
+      return true;
+    }
+  };
+  P._BroadcastSubscription.prototype = {
+    _onPause$0: function() {
+    },
+    _onResume$0: function() {
+    },
+    set$_async$_next: function(_next) {
+      this._async$_next = this.$ti._check(_next);
+    },
+    set$_async$_previous: function(_previous) {
+      this._async$_previous = this.$ti._check(_previous);
+    }
+  };
+  P._BroadcastStreamController.prototype = {
+    get$_mayAddEvent: function() {
+      return this._state < 4;
+    },
+    _ensureDoneFuture$0: function() {
+      var t1 = this._doneFuture;
+      if (t1 != null)
+        return t1;
+      return this._doneFuture = new P._Future($.Zone__current, type$._Future_dynamic);
+    },
+    _removeListener$1: function(subscription) {
+      var previous, next, _this = this;
+      H._instanceType(_this)._eval$1("_BroadcastSubscription<1>")._check(subscription);
+      H.assertHelper(subscription._controller === _this);
+      H.assertHelper(subscription._async$_next !== subscription);
+      previous = subscription._async$_previous;
+      next = subscription._async$_next;
+      if (previous == null)
+        _this.set$_firstSubscription(next);
+      else
+        previous.set$_async$_next(next);
+      if (next == null)
+        _this.set$_lastSubscription(previous);
+      else
+        next.set$_async$_previous(previous);
+      subscription.set$_async$_previous(subscription);
+      subscription.set$_async$_next(subscription);
+    },
+    _subscribe$4: function(onData, onError, onDone, cancelOnError) {
+      var t2, t3, t4, subscription, oldLast, _this = this,
+        t1 = H._instanceType(_this);
+      t1._eval$1("~(1)")._check(onData);
+      type$.void_Function._check(onDone);
+      if ((_this._state & 4) !== 0) {
+        if (onDone == null)
+          onDone = P.async___nullDoneHandler$closure();
+        t1 = new P._DoneStreamSubscription($.Zone__current, onDone, t1._eval$1("_DoneStreamSubscription<1>"));
+        t1._schedule$0();
+        return t1;
+      }
+      t2 = $.Zone__current;
+      t3 = cancelOnError ? 1 : 0;
+      t4 = t1._eval$1("_BroadcastSubscription<1>");
+      subscription = new P._BroadcastSubscription(_this, t2, t3, t4);
+      subscription._BufferingStreamSubscription$4(onData, onError, onDone, cancelOnError, t1._precomputed1);
+      subscription.set$_async$_previous(subscription);
+      subscription.set$_async$_next(subscription);
+      t4._check(subscription);
+      H.assertHelper(subscription._async$_next === subscription);
+      subscription._eventState = _this._state & 1;
+      oldLast = _this._lastSubscription;
+      _this.set$_lastSubscription(subscription);
+      subscription.set$_async$_next(null);
+      subscription.set$_async$_previous(oldLast);
+      if (oldLast == null)
+        _this.set$_firstSubscription(subscription);
+      else
+        oldLast.set$_async$_next(subscription);
+      if (_this._firstSubscription == _this._lastSubscription)
+        P._runGuarded(_this.onListen);
+      return subscription;
+    },
+    _recordCancel$1: function(sub) {
+      var _this = this,
+        t1 = H._instanceType(_this);
+      sub = t1._eval$1("_BroadcastSubscription<1>")._check(t1._eval$1("StreamSubscription<1>")._check(sub));
+      if (sub._async$_next === sub)
+        return null;
+      t1 = (sub._eventState & 2) !== 0;
+      if (t1) {
+        H.assertHelper(t1);
+        sub._eventState |= 4;
+      } else {
+        _this._removeListener$1(sub);
+        if ((_this._state & 2) === 0 && _this._firstSubscription == null)
+          _this._callOnCancel$0();
+      }
+      return null;
+    },
+    _recordPause$1: function(subscription) {
+      H._instanceType(this)._eval$1("StreamSubscription<1>")._check(subscription);
+    },
+    _recordResume$1: function(subscription) {
+      H._instanceType(this)._eval$1("StreamSubscription<1>")._check(subscription);
+    },
+    _addEventError$0: function() {
+      var t1 = this._state;
+      if ((t1 & 4) !== 0)
+        return new P.StateError("Cannot add new events after calling close");
+      H.assertHelper((t1 & 8) !== 0);
+      return new P.StateError("Cannot add new events while doing an addStream");
+    },
+    add$1: function(_, data) {
+      var _this = this;
+      H._instanceType(_this)._precomputed1._check(data);
+      if (!_this.get$_mayAddEvent())
+        throw H.wrapException(_this._addEventError$0());
+      _this._sendData$1(data);
+    },
+    addError$2: function(error, stackTrace) {
+      var replacement;
+      type$.StackTrace._check(stackTrace);
+      if (error == null)
+        error = new P.NullThrownError();
+      if (!this.get$_mayAddEvent())
+        throw H.wrapException(this._addEventError$0());
+      replacement = $.Zone__current.errorCallback$2(error, stackTrace);
+      if (replacement != null) {
+        error = replacement.error;
+        if (error == null)
+          error = new P.NullThrownError();
+        stackTrace = replacement.stackTrace;
+      }
+      this._sendError$2(error, stackTrace);
+    },
+    addError$1: function(error) {
+      return this.addError$2(error, null);
+    },
+    close$0: function(_) {
+      var doneFuture, _this = this;
+      if ((_this._state & 4) !== 0) {
+        H.assertHelper(_this._doneFuture != null);
+        return _this._doneFuture;
+      }
+      if (!_this.get$_mayAddEvent())
+        throw H.wrapException(_this._addEventError$0());
+      _this._state |= 4;
+      doneFuture = _this._ensureDoneFuture$0();
+      _this._sendDone$0();
+      return doneFuture;
+    },
+    _async$_addError$2: function(error, stackTrace) {
+      this._sendError$2(error, type$.StackTrace._check(stackTrace));
+    },
+    _close$0: function() {
+      var addState, _this = this;
+      H.assertHelper((_this._state & 8) !== 0);
+      addState = _this._addStreamState;
+      _this.set$_addStreamState(null);
+      _this._state &= 4294967287;
+      addState.addStreamFuture._asyncComplete$1(null);
+    },
+    _forEachListener$1: function(action) {
+      var t1, subscription, id, next, _this = this;
+      H._instanceType(_this)._eval$1("~(_BufferingStreamSubscription<1>)")._check(action);
+      t1 = _this._state;
+      if ((t1 & 2) !== 0)
+        throw H.wrapException(P.StateError$("Cannot fire new event. Controller is already firing an event"));
+      subscription = _this._firstSubscription;
+      if (subscription == null)
+        return;
+      id = t1 & 1;
+      _this._state = t1 ^ 3;
+      for (; subscription != null;) {
+        t1 = subscription._eventState;
+        if ((t1 & 1) === id) {
+          subscription._eventState = t1 | 2;
+          action.call$1(subscription);
+          t1 = subscription._eventState ^= 1;
+          next = subscription._async$_next;
+          if ((t1 & 4) !== 0)
+            _this._removeListener$1(subscription);
+          subscription._eventState &= 4294967293;
+          subscription = next;
+        } else
+          subscription = subscription._async$_next;
+      }
+      _this._state &= 4294967293;
+      if (_this._firstSubscription == null)
+        _this._callOnCancel$0();
+    },
+    _callOnCancel$0: function() {
+      var _this = this;
+      H.assertHelper(_this._firstSubscription == null);
+      if ((_this._state & 4) !== 0 && _this._doneFuture._state === 0)
+        _this._doneFuture._asyncComplete$1(null);
+      P._runGuarded(_this.onCancel);
+    },
+    set$_firstSubscription: function(_firstSubscription) {
+      this._firstSubscription = H._instanceType(this)._eval$1("_BroadcastSubscription<1>")._check(_firstSubscription);
+    },
+    set$_lastSubscription: function(_lastSubscription) {
+      this._lastSubscription = H._instanceType(this)._eval$1("_BroadcastSubscription<1>")._check(_lastSubscription);
+    },
+    set$_addStreamState: function(_addStreamState) {
+      this._addStreamState = H._instanceType(this)._eval$1("_AddStreamState<1>")._check(_addStreamState);
+    },
+    $isEventSink: 1,
+    $isStreamConsumer: 1,
+    $isStreamSink: 1,
+    $isStreamController: 1,
+    $is_StreamControllerLifecycle: 1,
+    $is_EventDispatch: 1,
+    $isSink: 1
+  };
+  P._SyncBroadcastStreamController.prototype = {
+    get$_mayAddEvent: function() {
+      return P._BroadcastStreamController.prototype.get$_mayAddEvent.call(this) && (this._state & 2) === 0;
+    },
+    _addEventError$0: function() {
+      if ((this._state & 2) !== 0)
+        return new P.StateError("Cannot fire new event. Controller is already firing an event");
+      return this.super$_BroadcastStreamController$_addEventError();
+    },
+    _sendData$1: function(data) {
+      var t1, _this = this;
+      _this.$ti._precomputed1._check(data);
+      if (_this._firstSubscription == null)
+        return;
+      t1 = _this._firstSubscription;
+      if (t1 == _this._lastSubscription) {
+        _this._state |= 2;
+        t1._add$1(data);
+        _this._state &= 4294967293;
+        if (_this._firstSubscription == null)
+          _this._callOnCancel$0();
+        return;
+      }
+      _this._forEachListener$1(new P._SyncBroadcastStreamController__sendData_closure(_this, data));
+    },
+    _sendError$2: function(error, stackTrace) {
+      if (this._firstSubscription == null)
+        return;
+      this._forEachListener$1(new P._SyncBroadcastStreamController__sendError_closure(this, error, stackTrace));
+    },
+    _sendDone$0: function() {
+      var _this = this;
+      if (_this._firstSubscription != null)
+        _this._forEachListener$1(new P._SyncBroadcastStreamController__sendDone_closure(_this));
+      else {
+        H.assertHelper(_this._doneFuture != null);
+        H.assertHelper(_this._doneFuture._state === 0);
+        _this._doneFuture._asyncComplete$1(null);
+      }
+    }
+  };
+  P._SyncBroadcastStreamController__sendData_closure.prototype = {
+    call$1: function(subscription) {
+      this.$this.$ti._eval$1("_BufferingStreamSubscription<1>")._check(subscription)._add$1(this.data);
+    },
+    $signature: function() {
+      return this.$this.$ti._eval$1("Null(_BufferingStreamSubscription<1>)");
+    }
+  };
+  P._SyncBroadcastStreamController__sendError_closure.prototype = {
+    call$1: function(subscription) {
+      this.$this.$ti._eval$1("_BufferingStreamSubscription<1>")._check(subscription)._async$_addError$2(this.error, this.stackTrace);
+    },
+    $signature: function() {
+      return this.$this.$ti._eval$1("Null(_BufferingStreamSubscription<1>)");
+    }
+  };
+  P._SyncBroadcastStreamController__sendDone_closure.prototype = {
+    call$1: function(subscription) {
+      this.$this.$ti._eval$1("_BufferingStreamSubscription<1>")._check(subscription)._close$0();
+    },
+    $signature: function() {
+      return this.$this.$ti._eval$1("Null(_BufferingStreamSubscription<1>)");
+    }
+  };
+  P._AsyncBroadcastStreamController.prototype = {
+    _sendData$1: function(data) {
+      var subscription,
+        t1 = this.$ti;
+      t1._precomputed1._check(data);
+      for (subscription = this._firstSubscription, t1 = t1._eval$1("_DelayedData<1>"); subscription != null; subscription = subscription._async$_next)
+        subscription._addPending$1(new P._DelayedData(data, t1));
+    },
+    _sendError$2: function(error, stackTrace) {
+      var subscription;
+      for (subscription = this._firstSubscription; subscription != null; subscription = subscription._async$_next)
+        subscription._addPending$1(new P._DelayedError(error, stackTrace));
+    },
+    _sendDone$0: function() {
+      var _this = this,
+        subscription = _this._firstSubscription;
+      if (subscription != null)
+        for (; subscription != null; subscription = subscription._async$_next)
+          subscription._addPending$1(C.C__DelayedDone);
+      else {
+        H.assertHelper(_this._doneFuture != null);
+        H.assertHelper(_this._doneFuture._state === 0);
+        _this._doneFuture._asyncComplete$1(null);
+      }
+    }
+  };
+  P.Future.prototype = {};
+  P.Future_Future_closure.prototype = {
+    call$0: function() {
+      var e, s, exception;
+      try {
+        this.result._complete$1(this.computation.call$0());
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        s = H.getTraceFromException(exception);
+        P._completeWithErrorCallback(this.result, e, s);
+      }
+    },
+    $signature: 0
+  };
+  P.Future_Future$microtask_closure.prototype = {
+    call$0: function() {
+      var e, s, exception;
+      try {
+        this.result._complete$1(this.computation.call$0());
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        s = H.getTraceFromException(exception);
+        P._completeWithErrorCallback(this.result, e, s);
+      }
+    },
+    $signature: 0
+  };
+  P.Future_wait_handleError.prototype = {
+    call$2: function(theError, theStackTrace) {
+      var t1, t2, _this = this;
+      type$.StackTrace._check(theStackTrace);
+      t1 = _this._box_0;
+      t2 = --t1.remaining;
+      if (t1.values != null) {
+        t1.values = null;
+        if (t1.remaining === 0 || _this.eagerError)
+          _this.result._completeError$2(theError, theStackTrace);
+        else {
+          t1.error = theError;
+          t1.stackTrace = theStackTrace;
+        }
+      } else if (t2 === 0 && !_this.eagerError)
+        _this.result._completeError$2(t1.error, t1.stackTrace);
+    },
+    $signature: 5
+  };
+  P.Future_wait_closure.prototype = {
+    call$1: function(value) {
+      var t1, t2, _this = this;
+      _this.T._check(value);
+      t1 = _this._box_0;
+      --t1.remaining;
+      t2 = t1.values;
+      if (t2 != null) {
+        C.JSArray_methods.$indexSet(t2, _this.pos, value);
+        if (t1.remaining === 0)
+          _this.result._completeWithValue$1(t1.values);
+      } else if (t1.remaining === 0 && !_this.eagerError)
+        _this.result._completeError$2(t1.error, t1.stackTrace);
+    },
+    $signature: function() {
+      return this.T._eval$1("Null(0)");
+    }
+  };
+  P.Future_forEach_closure.prototype = {
+    call$0: function() {
+      var result,
+        t1 = this.iterator;
+      if (!t1.moveNext$0())
+        return false;
+      result = this.action.call$1(t1._current);
+      if (type$.Future_dynamic._is(result))
+        return result.then$1$1(P.async_Future__kTrue$closure(), type$.bool);
+      return true;
+    },
+    $signature: 81
+  };
+  P.Future_doWhile_closure.prototype = {
+    call$1: function(keepGoing) {
+      var result, error, stackTrace, t1, t2, exception, error0, stackTrace0, replacement, _this = this;
+      H._checkBoolNullable(keepGoing);
+      for (t1 = type$.Future_bool, t2 = _this.action; H.boolConversionCheck(keepGoing);) {
+        result = null;
+        try {
+          result = t2.call$0();
+        } catch (exception) {
+          error = H.unwrapException(exception);
+          stackTrace = H.getTraceFromException(exception);
+          error0 = error;
+          stackTrace0 = stackTrace;
+          replacement = $.Zone__current.errorCallback$2(error0, stackTrace0);
+          if (replacement != null) {
+            error = replacement.error;
+            if (error == null)
+              error = new P.NullThrownError();
+            stackTrace = replacement.stackTrace;
+          } else {
+            stackTrace = stackTrace0;
+            error = error0;
+          }
+          _this.doneSignal._asyncCompleteError$2(error, stackTrace);
+          return;
+        }
+        if (t1._is(result)) {
+          result.then$1$2$onError(_this._box_0.nextIteration, _this.doneSignal.get$_completeError(), type$.void);
+          return;
+        }
+        keepGoing = H._checkBoolNullable(result);
+      }
+      _this.doneSignal._complete$1(null);
+    },
+    $signature: 43
+  };
+  P.TimeoutException.prototype = {
+    toString$0: function(_) {
+      var t1 = this.duration,
+        result = (t1 != null ? "TimeoutException after " + t1.toString$0(0) : "TimeoutException") + ": " + this.message;
+      return result;
+    },
+    $isException: 1,
+    get$message: function(receiver) {
+      return this.message;
+    }
+  };
+  P.Completer.prototype = {};
+  P._Completer.prototype = {
+    completeError$2: function(error, stackTrace) {
+      var replacement;
+      if (error == null)
+        error = new P.NullThrownError();
+      if (this.future._state !== 0)
+        throw H.wrapException(P.StateError$("Future already completed"));
+      replacement = $.Zone__current.errorCallback$2(error, stackTrace);
+      if (replacement != null) {
+        error = replacement.error;
+        if (error == null)
+          error = new P.NullThrownError();
+        stackTrace = replacement.stackTrace;
+      }
+      this._completeError$2(error, stackTrace);
+    },
+    completeError$1: function(error) {
+      return this.completeError$2(error, null);
+    },
+    $isCompleter: 1
+  };
+  P._AsyncCompleter.prototype = {
+    complete$1: function(value) {
+      var t1;
+      this.$ti._eval$1("1/")._check(value);
+      t1 = this.future;
+      if (t1._state !== 0)
+        throw H.wrapException(P.StateError$("Future already completed"));
+      t1._asyncComplete$1(value);
+    },
+    complete$0: function() {
+      return this.complete$1(null);
+    },
+    _completeError$2: function(error, stackTrace) {
+      this.future._asyncCompleteError$2(error, stackTrace);
+    }
+  };
+  P._SyncCompleter.prototype = {
+    complete$1: function(value) {
+      var t1;
+      this.$ti._eval$1("1/")._check(value);
+      t1 = this.future;
+      if (t1._state !== 0)
+        throw H.wrapException(P.StateError$("Future already completed"));
+      t1._complete$1(value);
+    },
+    complete$0: function() {
+      return this.complete$1(null);
+    },
+    _completeError$2: function(error, stackTrace) {
+      this.future._completeError$2(error, stackTrace);
+    }
+  };
+  P._FutureListener.prototype = {
+    matchesErrorTest$1: function(asyncError) {
+      if ((this.state & 15) !== 6)
+        return true;
+      return this.result._zone.runUnary$2$2(type$.bool_Function_Object._check(this.callback), asyncError.error, type$.bool, type$.Object);
+    },
+    handleError$1: function(asyncError) {
+      var errorCallback, t2, t3, t4, _this = this,
+        t1 = (_this.state & 2) !== 0;
+      if (t1) {
+        H.assertHelper(t1);
+        t1 = _this.errorCallback != null;
+      } else
+        t1 = false;
+      H.assertHelper(t1);
+      errorCallback = _this.errorCallback;
+      t1 = type$.dynamic;
+      t2 = type$.Object;
+      t3 = _this.$ti._eval$1("2/");
+      t4 = _this.result._zone;
+      if (type$.dynamic_Function_Object_StackTrace._is(errorCallback))
+        return t3._check(t4.runBinary$3$3(errorCallback, asyncError.error, asyncError.stackTrace, t1, t2, type$.StackTrace));
+      else {
+        H.assertHelper(type$.dynamic_Function_Object._is(errorCallback));
+        return t3._check(t4.runUnary$2$2(errorCallback, asyncError.error, t1, t2));
+      }
+    }
+  };
+  P._Future.prototype = {
+    then$1$2$onError: function(f, onError, $R) {
+      var currentZone, result, t2,
+        t1 = this.$ti;
+      t1._bind$1($R)._eval$1("1/(2)")._check(f);
+      currentZone = $.Zone__current;
+      if (currentZone !== C.C__RootZone) {
+        f = currentZone.registerUnaryCallback$2$1(f, $R._eval$1("0/"), t1._precomputed1);
+        if (onError != null)
+          onError = P._registerErrorHandler(onError, currentZone);
+      }
+      result = new P._Future($.Zone__current, $R._eval$1("_Future<0>"));
+      t2 = onError == null ? 1 : 3;
+      this._addListener$1(new P._FutureListener(result, t2, f, onError, t1._eval$1("@<1>")._bind$1($R)._eval$1("_FutureListener<1,2>")));
+      return result;
+    },
+    then$1$1: function(f, $R) {
+      return this.then$1$2$onError(f, null, $R);
+    },
+    _thenAwait$1$2: function(f, onError, $E) {
+      var result,
+        t1 = this.$ti;
+      t1._bind$1($E)._eval$1("1/(2)")._check(f);
+      result = new P._Future($.Zone__current, $E._eval$1("_Future<0>"));
+      this._addListener$1(new P._FutureListener(result, (onError == null ? 1 : 3) | 16, f, onError, t1._eval$1("@<1>")._bind$1($E)._eval$1("_FutureListener<1,2>")));
+      return result;
+    },
+    catchError$1: function(onError) {
+      var t1, t2, result;
+      type$.bool_Function_dynamic._check(null);
+      t1 = this.$ti;
+      t2 = $.Zone__current;
+      result = new P._Future(t2, t1);
+      if (t2 !== C.C__RootZone)
+        onError = P._registerErrorHandler(onError, t2);
+      this._addListener$1(new P._FutureListener(result, 2, null, onError, t1._eval$1("@<1>")._bind$1(t1._precomputed1)._eval$1("_FutureListener<1,2>")));
+      return result;
+    },
+    whenComplete$1: function(action) {
+      var t1, t2, result;
+      type$.dynamic_Function._check(action);
+      t1 = this.$ti;
+      t2 = $.Zone__current;
+      result = new P._Future(t2, t1);
+      if (t2 !== C.C__RootZone)
+        action = t2.registerCallback$1$1(action, type$.dynamic);
+      this._addListener$1(new P._FutureListener(result, 8, action, null, t1._eval$1("@<1>")._bind$1(t1._precomputed1)._eval$1("_FutureListener<1,2>")));
+      return result;
+    },
+    _cloneResult$1: function(source) {
+      H.assertHelper(this._state < 4);
+      H.assertHelper(source._state >= 4);
+      this._state = source._state;
+      this._resultOrListeners = source._resultOrListeners;
+    },
+    _addListener$1: function(listener) {
+      var t1, source, _this = this;
+      H.assertHelper(listener._nextListener == null);
+      t1 = _this._state;
+      if (t1 <= 1) {
+        listener._nextListener = type$._FutureListener_dynamic_dynamic._check(_this._resultOrListeners);
+        _this._resultOrListeners = listener;
+      } else {
+        if (t1 === 2) {
+          source = type$._Future_dynamic._check(_this._resultOrListeners);
+          if (source._state < 4) {
+            source._addListener$1(listener);
+            return;
+          }
+          _this._cloneResult$1(source);
+        }
+        H.assertHelper(_this._state >= 4);
+        _this._zone.scheduleMicrotask$1(new P._Future__addListener_closure(_this, listener));
+      }
+    },
+    _prependListeners$1: function(listeners) {
+      var t1, existingListeners, cursor, cursor0, source, _this = this, _box_0 = {};
+      _box_0.listeners = listeners;
+      if (listeners == null)
+        return;
+      t1 = _this._state;
+      if (t1 <= 1) {
+        existingListeners = type$._FutureListener_dynamic_dynamic._check(_this._resultOrListeners);
+        cursor = _this._resultOrListeners = listeners;
+        if (existingListeners != null) {
+          for (; cursor0 = cursor._nextListener, cursor0 != null; cursor = cursor0)
+            ;
+          cursor._nextListener = existingListeners;
+        }
+      } else {
+        if (t1 === 2) {
+          source = type$._Future_dynamic._check(_this._resultOrListeners);
+          if (source._state < 4) {
+            source._prependListeners$1(listeners);
+            return;
+          }
+          _this._cloneResult$1(source);
+        }
+        H.assertHelper(_this._state >= 4);
+        _box_0.listeners = _this._reverseListeners$1(listeners);
+        _this._zone.scheduleMicrotask$1(new P._Future__prependListeners_closure(_box_0, _this));
+      }
+    },
+    _removeListeners$0: function() {
+      var current, _this = this;
+      H.assertHelper(_this._state < 4);
+      current = type$._FutureListener_dynamic_dynamic._check(_this._resultOrListeners);
+      _this._resultOrListeners = null;
+      return _this._reverseListeners$1(current);
+    },
+    _reverseListeners$1: function(listeners) {
+      var current, prev, next;
+      for (current = listeners, prev = null; current != null; prev = current, current = next) {
+        next = current._nextListener;
+        current._nextListener = prev;
+      }
+      return prev;
+    },
+    _complete$1: function(value) {
+      var listeners, _this = this,
+        t1 = _this.$ti;
+      t1._eval$1("1/")._check(value);
+      H.assertHelper(_this._state < 4);
+      if (t1._eval$1("Future<1>")._is(value))
+        if (t1._is(value))
+          P._Future__chainCoreFuture(value, _this);
+        else
+          P._Future__chainForeignFuture(value, _this);
+      else {
+        listeners = _this._removeListeners$0();
+        t1._precomputed1._check(value);
+        H.assertHelper(_this._state < 4);
+        _this._state = 4;
+        _this._resultOrListeners = value;
+        P._Future__propagateToListeners(_this, listeners);
+      }
+    },
+    _completeWithValue$1: function(value) {
+      var listeners, _this = this,
+        t1 = _this.$ti;
+      t1._precomputed1._check(value);
+      H.assertHelper(_this._state < 4);
+      H.assertHelper(!t1._eval$1("Future<1>")._is(value));
+      listeners = _this._removeListeners$0();
+      H.assertHelper(_this._state < 4);
+      _this._state = 4;
+      _this._resultOrListeners = value;
+      P._Future__propagateToListeners(_this, listeners);
+    },
+    _completeError$2: function(error, stackTrace) {
+      var listeners, _this = this;
+      type$.StackTrace._check(stackTrace);
+      H.assertHelper(_this._state < 4);
+      listeners = _this._removeListeners$0();
+      H.assertHelper(_this._state < 4);
+      _this._state = 8;
+      _this._resultOrListeners = new P.AsyncError(error, stackTrace);
+      P._Future__propagateToListeners(_this, listeners);
+    },
+    _completeError$1: function(error) {
+      return this._completeError$2(error, null);
+    },
+    _asyncComplete$1: function(value) {
+      var _this = this,
+        t1 = _this.$ti;
+      t1._eval$1("1/")._check(value);
+      H.assertHelper(_this._state < 4);
+      if (t1._eval$1("Future<1>")._is(value)) {
+        _this._chainFuture$1(value);
+        return;
+      }
+      H.assertHelper(_this._state === 0);
+      _this._state = 1;
+      _this._zone.scheduleMicrotask$1(new P._Future__asyncComplete_closure(_this, value));
+    },
+    _chainFuture$1: function(value) {
+      var _this = this,
+        t1 = _this.$ti;
+      t1._eval$1("Future<1>")._check(value);
+      if (t1._is(value)) {
+        if (value._state === 8) {
+          H.assertHelper(_this._state === 0);
+          _this._state = 1;
+          _this._zone.scheduleMicrotask$1(new P._Future__chainFuture_closure(_this, value));
+        } else
+          P._Future__chainCoreFuture(value, _this);
+        return;
+      }
+      P._Future__chainForeignFuture(value, _this);
+    },
+    _asyncCompleteError$2: function(error, stackTrace) {
+      var _this = this;
+      type$.StackTrace._check(stackTrace);
+      H.assertHelper(_this._state < 4);
+      H.assertHelper(_this._state === 0);
+      _this._state = 1;
+      _this._zone.scheduleMicrotask$1(new P._Future__asyncCompleteError_closure(_this, error, stackTrace));
+    },
+    $isFuture: 1
+  };
+  P._Future__addListener_closure.prototype = {
+    call$0: function() {
+      P._Future__propagateToListeners(this.$this, this.listener);
+    },
+    $signature: 0
+  };
+  P._Future__prependListeners_closure.prototype = {
+    call$0: function() {
+      P._Future__propagateToListeners(this.$this, this._box_0.listeners);
+    },
+    $signature: 0
+  };
+  P._Future__chainForeignFuture_closure.prototype = {
+    call$1: function(value) {
+      var t1 = this.target;
+      H.assertHelper(t1._state === 1);
+      H.assertHelper(t1._state === 1);
+      t1._state = 0;
+      t1._complete$1(value);
+    },
+    $signature: 3
+  };
+  P._Future__chainForeignFuture_closure0.prototype = {
+    call$2: function(error, stackTrace) {
+      var t1;
+      type$.StackTrace._check(stackTrace);
+      t1 = this.target;
+      H.assertHelper(t1._state === 1);
+      t1._completeError$2(error, stackTrace);
+    },
+    call$1: function(error) {
+      return this.call$2(error, null);
+    },
+    $signature: 80
+  };
+  P._Future__chainForeignFuture_closure1.prototype = {
+    call$0: function() {
+      this.target._completeError$2(this.e, this.s);
+    },
+    $signature: 0
+  };
+  P._Future__asyncComplete_closure.prototype = {
+    call$0: function() {
+      var t1 = this.$this;
+      t1._completeWithValue$1(t1.$ti._precomputed1._check(this.value));
+    },
+    $signature: 0
+  };
+  P._Future__chainFuture_closure.prototype = {
+    call$0: function() {
+      P._Future__chainCoreFuture(this.value, this.$this);
+    },
+    $signature: 0
+  };
+  P._Future__asyncCompleteError_closure.prototype = {
+    call$0: function() {
+      this.$this._completeError$2(this.error, this.stackTrace);
+    },
+    $signature: 0
+  };
+  P._Future__propagateToListeners_handleWhenCompleteCallback.prototype = {
+    call$0: function() {
+      var completeResult, e, s, t3, exception, originalSource, _this = this,
+        t1 = _this.listener,
+        t2 = t1.state;
+      H.assertHelper((t2 & 1) === 0);
+      t3 = (t2 & 2) === 0;
+      H.assertHelper(t3);
+      completeResult = null;
+      try {
+        H.assertHelper(t3);
+        H.assertHelper((t2 & 15) === 8);
+        completeResult = t1.result._zone.run$1$1(type$.dynamic_Function._check(t1.callback), type$.dynamic);
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        s = H.getTraceFromException(exception);
+        if (_this.hasError) {
+          t1 = _this._box_1.source;
+          H.assertHelper(t1._state === 8);
+          t1 = type$.AsyncError._check(t1._resultOrListeners).error;
+          t2 = e;
+          t2 = t1 == null ? t2 == null : t1 === t2;
+          t1 = t2;
+        } else
+          t1 = false;
+        t2 = _this._box_0;
+        if (t1) {
+          t1 = _this._box_1.source;
+          H.assertHelper(t1._state === 8);
+          t2.listenerValueOrError = type$.AsyncError._check(t1._resultOrListeners);
+        } else
+          t2.listenerValueOrError = new P.AsyncError(e, s);
+        t2.listenerHasError = true;
+        return;
+      }
+      if (type$.Future_dynamic._is(completeResult)) {
+        if (completeResult instanceof P._Future && completeResult._state >= 4) {
+          if (completeResult._state === 8) {
+            t1 = completeResult;
+            H.assertHelper(t1._state === 8);
+            t2 = _this._box_0;
+            t2.listenerValueOrError = type$.AsyncError._check(t1._resultOrListeners);
+            t2.listenerHasError = true;
+          }
+          return;
+        }
+        originalSource = _this._box_1.source;
+        t1 = _this._box_0;
+        t1.listenerValueOrError = completeResult.then$1$1(new P._Future__propagateToListeners_handleWhenCompleteCallback_closure(originalSource), type$.dynamic);
+        t1.listenerHasError = false;
+      }
+    },
+    $signature: 1
+  };
+  P._Future__propagateToListeners_handleWhenCompleteCallback_closure.prototype = {
+    call$1: function(_) {
+      return this.originalSource;
+    },
+    $signature: 75
+  };
+  P._Future__propagateToListeners_handleValueCallback.prototype = {
+    call$0: function() {
+      var e, s, t1, t2, t3, t4, exception, _this = this;
+      try {
+        t1 = _this.listener;
+        t2 = t1.$ti;
+        t3 = t2._precomputed1;
+        t4 = t3._check(_this.sourceResult);
+        H.assertHelper((t1.state & 1) !== 0);
+        _this._box_0.listenerValueOrError = t1.result._zone.runUnary$2$2(t2._eval$1("2/(1)")._check(t1.callback), t4, t2._eval$1("2/"), t3);
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        s = H.getTraceFromException(exception);
+        t1 = _this._box_0;
+        t1.listenerValueOrError = new P.AsyncError(e, s);
+        t1.listenerHasError = true;
+      }
+    },
+    $signature: 1
+  };
+  P._Future__propagateToListeners_handleError.prototype = {
+    call$0: function() {
+      var asyncError, e, s, t1, t2, exception, t3, t4, t5, _this = this;
+      try {
+        t1 = _this._box_1.source;
+        H.assertHelper(t1._state === 8);
+        asyncError = type$.AsyncError._check(t1._resultOrListeners);
+        t1 = _this.listener;
+        if (H.boolConversionCheck(t1.matchesErrorTest$1(asyncError))) {
+          H.assertHelper((t1.state & 2) !== 0);
+          t2 = t1.errorCallback != null;
+        } else
+          t2 = false;
+        if (t2) {
+          t2 = _this._box_0;
+          t2.listenerValueOrError = t1.handleError$1(asyncError);
+          t2.listenerHasError = false;
+        }
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        s = H.getTraceFromException(exception);
+        t1 = _this._box_1;
+        t2 = t1.source;
+        H.assertHelper(t2._state === 8);
+        t3 = type$.AsyncError;
+        t2 = t3._check(t2._resultOrListeners).error;
+        t4 = e;
+        t5 = _this._box_0;
+        if (t2 == null ? t4 == null : t2 === t4) {
+          t1 = t1.source;
+          H.assertHelper(t1._state === 8);
+          t5.listenerValueOrError = t3._check(t1._resultOrListeners);
+        } else
+          t5.listenerValueOrError = new P.AsyncError(e, s);
+        t5.listenerHasError = true;
+      }
+    },
+    $signature: 1
+  };
+  P._AsyncCallbackEntry.prototype = {};
+  P.Stream.prototype = {
+    get$isBroadcast: function() {
+      return false;
+    },
+    pipe$1: function(streamConsumer) {
+      H._instanceType(this)._eval$1("StreamConsumer<Stream.T>")._check(streamConsumer);
+      return streamConsumer.addStream$1(this).then$1$1(new P.Stream_pipe_closure(streamConsumer), type$.dynamic);
+    },
+    get$length: function(_) {
+      var t1 = {},
+        future = new P._Future($.Zone__current, type$._Future_int);
+      t1.count = 0;
+      this.listen$4$cancelOnError$onDone$onError(new P.Stream_length_closure(t1, this), true, new P.Stream_length_closure0(t1, future), future.get$_completeError());
+      return future;
+    },
+    get$first: function(_) {
+      var t1 = {},
+        future = new P._Future($.Zone__current, H._instanceType(this)._eval$1("_Future<Stream.T>"));
+      t1.subscription = null;
+      t1.subscription = this.listen$4$cancelOnError$onDone$onError(new P.Stream_first_closure(t1, this, future), true, new P.Stream_first_closure0(future), future.get$_completeError());
+      return future;
+    },
+    get$last: function(_) {
+      var t1 = {},
+        future = new P._Future($.Zone__current, H._instanceType(this)._eval$1("_Future<Stream.T>"));
+      t1.result = null;
+      t1.foundResult = false;
+      this.listen$4$cancelOnError$onDone$onError(new P.Stream_last_closure(t1, this), true, new P.Stream_last_closure0(t1, future), future.get$_completeError());
+      return future;
+    },
+    firstWhere$1: function(_, test) {
+      var future, _this = this, t1 = {},
+        t2 = H._instanceType(_this);
+      t2._eval$1("bool(Stream.T)")._check(test);
+      t2._eval$1("Stream.T()")._check(null);
+      future = new P._Future($.Zone__current, t2._eval$1("_Future<Stream.T>"));
+      t1.subscription = null;
+      t1.subscription = _this.listen$4$cancelOnError$onDone$onError(new P.Stream_firstWhere_closure(t1, _this, test, future), true, new P.Stream_firstWhere_closure0(_this, null, future), future.get$_completeError());
+      return future;
+    }
+  };
+  P.Stream_Stream$fromFuture_closure.prototype = {
+    call$1: function(value) {
+      var t1 = this.controller;
+      t1._add$1(this.T._check(value));
+      t1._closeUnchecked$0();
+    },
+    $signature: function() {
+      return this.T._eval$1("Null(0)");
+    }
+  };
+  P.Stream_Stream$fromFuture_closure0.prototype = {
+    call$2: function(error, stackTrace) {
+      var t1 = this.controller;
+      t1._async$_addError$2(error, type$.StackTrace._check(stackTrace));
+      t1._closeUnchecked$0();
+    },
+    $signature: 6
+  };
+  P.Stream_Stream$fromIterable_closure.prototype = {
+    call$0: function() {
+      var t1 = this.elements;
+      return new P._IterablePendingEvents(new J.ArrayIterator(t1, 0, H._arrayInstanceType(t1)._eval$1("ArrayIterator<1>")), this.T._eval$1("_IterablePendingEvents<0>"));
+    },
+    $signature: function() {
+      return this.T._eval$1("_IterablePendingEvents<0>()");
+    }
+  };
+  P.Stream_pipe_closure.prototype = {
+    call$1: function(_) {
+      return this.streamConsumer.close$0(0);
+    },
+    $signature: 73
+  };
+  P.Stream_length_closure.prototype = {
+    call$1: function(_) {
+      H._instanceType(this.$this)._eval$1("Stream.T")._check(_);
+      ++this._box_0.count;
+    },
+    $signature: function() {
+      return H._instanceType(this.$this)._eval$1("Null(Stream.T)");
+    }
+  };
+  P.Stream_length_closure0.prototype = {
+    call$0: function() {
+      this.future._complete$1(this._box_0.count);
+    },
+    $signature: 0
+  };
+  P.Stream_first_closure.prototype = {
+    call$1: function(value) {
+      H._instanceType(this.$this)._eval$1("Stream.T")._check(value);
+      P._cancelAndValue(this._box_0.subscription, this.future, value);
+    },
+    $signature: function() {
+      return H._instanceType(this.$this)._eval$1("Null(Stream.T)");
+    }
+  };
+  P.Stream_first_closure0.prototype = {
+    call$0: function() {
+      var e, s, t1, exception;
+      try {
+        t1 = H.IterableElementError_noElement();
+        throw H.wrapException(t1);
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        s = H.getTraceFromException(exception);
+        P._completeWithErrorCallback(this.future, e, s);
+      }
+    },
+    $signature: 0
+  };
+  P.Stream_last_closure.prototype = {
+    call$1: function(value) {
+      var t1;
+      H._instanceType(this.$this)._eval$1("Stream.T")._check(value);
+      t1 = this._box_0;
+      t1.foundResult = true;
+      t1.result = value;
+    },
+    $signature: function() {
+      return H._instanceType(this.$this)._eval$1("Null(Stream.T)");
+    }
+  };
+  P.Stream_last_closure0.prototype = {
+    call$0: function() {
+      var e, s, exception,
+        t1 = this._box_0;
+      if (t1.foundResult) {
+        this.future._complete$1(t1.result);
+        return;
+      }
+      try {
+        t1 = H.IterableElementError_noElement();
+        throw H.wrapException(t1);
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        s = H.getTraceFromException(exception);
+        P._completeWithErrorCallback(this.future, e, s);
+      }
+    },
+    $signature: 0
+  };
+  P.Stream_firstWhere_closure.prototype = {
+    call$1: function(value) {
+      var t1, t2, _this = this;
+      H._instanceType(_this.$this)._eval$1("Stream.T")._check(value);
+      t1 = _this._box_0;
+      t2 = _this.future;
+      P._runUserCode(new P.Stream_firstWhere__closure(_this.test, value), new P.Stream_firstWhere__closure0(t1, t2, value), P._cancelAndErrorClosure(t1.subscription, t2), type$.bool);
+    },
+    $signature: function() {
+      return H._instanceType(this.$this)._eval$1("Null(Stream.T)");
+    }
+  };
+  P.Stream_firstWhere__closure.prototype = {
+    call$0: function() {
+      return this.test.call$1(this.value);
+    },
+    $signature: 49
+  };
+  P.Stream_firstWhere__closure0.prototype = {
+    call$1: function(isMatch) {
+      if (H.boolConversionCheck(H._checkBoolNullable(isMatch)))
+        P._cancelAndValue(this._box_0.subscription, this.future, this.value);
+    },
+    $signature: 43
+  };
+  P.Stream_firstWhere_closure0.prototype = {
+    call$0: function() {
+      var e, s, t1, exception;
+      try {
+        t1 = H.IterableElementError_noElement();
+        throw H.wrapException(t1);
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        s = H.getTraceFromException(exception);
+        P._completeWithErrorCallback(this.future, e, s);
+      }
+    },
+    $signature: 0
+  };
+  P.StreamSubscription.prototype = {};
+  P.StreamTransformerBase.prototype = {$isStreamTransformer: 1};
+  P._StreamController.prototype = {
+    get$_pendingEvents: function() {
+      var t1, _this = this;
+      H.assertHelper((_this._state & 3) === 0);
+      if ((_this._state & 8) === 0)
+        return H._instanceType(_this)._eval$1("_PendingEvents<1>")._check(_this._varData);
+      t1 = H._instanceType(_this);
+      return t1._eval$1("_PendingEvents<1>")._check(t1._eval$1("_StreamControllerAddStreamState<1>")._check(_this._varData).varData);
+    },
+    _ensurePendingEvents$0: function() {
+      var t1, state, t2, _this = this;
+      H.assertHelper((_this._state & 3) === 0);
+      if ((_this._state & 8) === 0) {
+        t1 = _this._varData;
+        if (t1 == null)
+          t1 = _this._varData = new P._StreamImplEvents(H._instanceType(_this)._eval$1("_StreamImplEvents<1>"));
+        return H._instanceType(_this)._eval$1("_StreamImplEvents<1>")._check(t1);
+      }
+      t1 = H._instanceType(_this);
+      state = t1._eval$1("_StreamControllerAddStreamState<1>")._check(_this._varData);
+      t2 = state.varData;
+      if (t2 == null)
+        t2 = state.varData = new P._StreamImplEvents(t1._eval$1("_StreamImplEvents<1>"));
+      return t1._eval$1("_StreamImplEvents<1>")._check(t2);
+    },
+    get$_async$_subscription: function() {
+      var t1, _this = this;
+      H.assertHelper((_this._state & 1) !== 0);
+      if ((_this._state & 8) !== 0) {
+        t1 = H._instanceType(_this);
+        return t1._eval$1("_ControllerSubscription<1>")._check(t1._eval$1("_StreamControllerAddStreamState<1>")._check(_this._varData).varData);
+      }
+      return H._instanceType(_this)._eval$1("_ControllerSubscription<1>")._check(_this._varData);
+    },
+    _badEventState$0: function() {
+      var t1 = this._state;
+      if ((t1 & 4) !== 0)
+        return new P.StateError("Cannot add event after closing");
+      H.assertHelper((t1 & 8) !== 0);
+      return new P.StateError("Cannot add event while adding a stream");
+    },
+    addStream$2$cancelOnError: function(source, cancelOnError) {
+      var t2, t3, t4, t5, _this = this,
+        t1 = H._instanceType(_this);
+      t1._eval$1("Stream<1>")._check(source);
+      t2 = _this._state;
+      if (t2 >= 4)
+        throw H.wrapException(_this._badEventState$0());
+      if ((t2 & 2) !== 0) {
+        t1 = new P._Future($.Zone__current, type$._Future_dynamic);
+        t1._asyncComplete$1(null);
+        return t1;
+      }
+      t2 = _this._varData;
+      t3 = cancelOnError === true;
+      t4 = new P._Future($.Zone__current, type$._Future_dynamic);
+      t5 = t3 ? P._AddStreamState_makeErrorHandler(_this) : _this.get$_async$_addError();
+      t5 = source.listen$4$cancelOnError$onDone$onError(_this.get$_add(), t3, _this.get$_close(), t5);
+      t3 = _this._state;
+      if ((t3 & 1) !== 0 ? (_this.get$_async$_subscription()._state & 4) !== 0 : (t3 & 2) === 0)
+        t5.pause$0();
+      _this._varData = new P._StreamControllerAddStreamState(t2, t4, t5, t1._eval$1("_StreamControllerAddStreamState<1>"));
+      _this._state |= 8;
+      return t4;
+    },
+    _ensureDoneFuture$0: function() {
+      var t1 = this._doneFuture;
+      if (t1 == null)
+        t1 = this._doneFuture = (this._state & 2) !== 0 ? $.$get$Future__nullFuture() : new P._Future($.Zone__current, type$._Future_dynamic);
+      return t1;
+    },
+    add$1: function(_, value) {
+      var _this = this;
+      H._instanceType(_this)._precomputed1._check(value);
+      if (_this._state >= 4)
+        throw H.wrapException(_this._badEventState$0());
+      _this._add$1(value);
+    },
+    addError$2: function(error, stackTrace) {
+      var replacement;
+      type$.StackTrace._check(stackTrace);
+      if (this._state >= 4)
+        throw H.wrapException(this._badEventState$0());
+      if (error == null)
+        error = new P.NullThrownError();
+      replacement = $.Zone__current.errorCallback$2(error, stackTrace);
+      if (replacement != null) {
+        error = replacement.error;
+        if (error == null)
+          error = new P.NullThrownError();
+        stackTrace = replacement.stackTrace;
+      }
+      this._async$_addError$2(error, stackTrace);
+    },
+    addError$1: function(error) {
+      return this.addError$2(error, null);
+    },
+    close$0: function(_) {
+      var _this = this,
+        t1 = _this._state;
+      if ((t1 & 4) !== 0)
+        return _this._ensureDoneFuture$0();
+      if (t1 >= 4)
+        throw H.wrapException(_this._badEventState$0());
+      _this._closeUnchecked$0();
+      return _this._ensureDoneFuture$0();
+    },
+    _closeUnchecked$0: function() {
+      var t1 = this._state |= 4;
+      if ((t1 & 1) !== 0)
+        this._sendDone$0();
+      else if ((t1 & 3) === 0)
+        this._ensurePendingEvents$0().add$1(0, C.C__DelayedDone);
+    },
+    _add$1: function(value) {
+      var t2, _this = this,
+        t1 = H._instanceType(_this);
+      t1._precomputed1._check(value);
+      t2 = _this._state;
+      if ((t2 & 1) !== 0)
+        _this._sendData$1(value);
+      else if ((t2 & 3) === 0)
+        _this._ensurePendingEvents$0().add$1(0, new P._DelayedData(value, t1._eval$1("_DelayedData<1>")));
+    },
+    _async$_addError$2: function(error, stackTrace) {
+      var t1;
+      type$.StackTrace._check(stackTrace);
+      t1 = this._state;
+      if ((t1 & 1) !== 0)
+        this._sendError$2(error, stackTrace);
+      else if ((t1 & 3) === 0)
+        this._ensurePendingEvents$0().add$1(0, new P._DelayedError(error, stackTrace));
+    },
+    _close$0: function() {
+      var addState, _this = this;
+      H.assertHelper((_this._state & 8) !== 0);
+      addState = H._instanceType(_this)._eval$1("_StreamControllerAddStreamState<1>")._check(_this._varData);
+      _this._varData = addState.varData;
+      _this._state &= 4294967287;
+      addState.addStreamFuture._asyncComplete$1(null);
+    },
+    _subscribe$4: function(onData, onError, onDone, cancelOnError) {
+      var t2, t3, subscription, pendingEvents, addState, _this = this,
+        t1 = H._instanceType(_this);
+      t1._eval$1("~(1)")._check(onData);
+      type$.void_Function._check(onDone);
+      if ((_this._state & 3) !== 0)
+        throw H.wrapException(P.StateError$("Stream has already been listened to."));
+      t2 = $.Zone__current;
+      t3 = cancelOnError ? 1 : 0;
+      subscription = new P._ControllerSubscription(_this, t2, t3, t1._eval$1("_ControllerSubscription<1>"));
+      subscription._BufferingStreamSubscription$4(onData, onError, onDone, cancelOnError, t1._precomputed1);
+      pendingEvents = _this.get$_pendingEvents();
+      t3 = _this._state |= 1;
+      if ((t3 & 8) !== 0) {
+        addState = t1._eval$1("_StreamControllerAddStreamState<1>")._check(_this._varData);
+        addState.varData = subscription;
+        addState.addSubscription.resume$0();
+      } else
+        _this._varData = subscription;
+      subscription._setPendingEvents$1(pendingEvents);
+      subscription._guardCallback$1(new P._StreamController__subscribe_closure(_this));
+      return subscription;
+    },
+    _recordCancel$1: function(subscription) {
+      var result, e, s, exception, result0, _this = this,
+        t1 = H._instanceType(_this);
+      t1._eval$1("StreamSubscription<1>")._check(subscription);
+      result = null;
+      if ((_this._state & 8) !== 0)
+        result = t1._eval$1("_StreamControllerAddStreamState<1>")._check(_this._varData).cancel$0();
+      _this._varData = null;
+      _this._state = _this._state & 4294967286 | 2;
+      t1 = _this.onCancel;
+      if (t1 != null)
+        if (result == null)
+          try {
+            result = type$.Future_dynamic._check(t1.call$0());
+          } catch (exception) {
+            e = H.unwrapException(exception);
+            s = H.getTraceFromException(exception);
+            result0 = new P._Future($.Zone__current, type$._Future_dynamic);
+            result0._asyncCompleteError$2(e, s);
+            result = result0;
+          }
+        else
+          result = result.whenComplete$1(t1);
+      t1 = new P._StreamController__recordCancel_complete(_this);
+      if (result != null)
+        result = result.whenComplete$1(t1);
+      else
+        t1.call$0();
+      return result;
+    },
+    _recordPause$1: function(subscription) {
+      var _this = this,
+        t1 = H._instanceType(_this);
+      t1._eval$1("StreamSubscription<1>")._check(subscription);
+      if ((_this._state & 8) !== 0)
+        t1._eval$1("_StreamControllerAddStreamState<1>")._check(_this._varData).addSubscription.pause$0();
+      P._runGuarded(_this.onPause);
+    },
+    _recordResume$1: function(subscription) {
+      var _this = this,
+        t1 = H._instanceType(_this);
+      t1._eval$1("StreamSubscription<1>")._check(subscription);
+      if ((_this._state & 8) !== 0)
+        t1._eval$1("_StreamControllerAddStreamState<1>")._check(_this._varData).addSubscription.resume$0();
+      P._runGuarded(_this.onResume);
+    },
+    $isEventSink: 1,
+    $isStreamConsumer: 1,
+    $isStreamSink: 1,
+    $isStreamController: 1,
+    $is_StreamControllerLifecycle: 1,
+    $is_EventDispatch: 1,
+    $isSink: 1
+  };
+  P._StreamController__subscribe_closure.prototype = {
+    call$0: function() {
+      P._runGuarded(this.$this.onListen);
+    },
+    $signature: 0
+  };
+  P._StreamController__recordCancel_complete.prototype = {
+    call$0: function() {
+      var t1 = this.$this._doneFuture;
+      if (t1 != null && t1._state === 0)
+        t1._asyncComplete$1(null);
+    },
+    $signature: 1
+  };
+  P._SyncStreamControllerDispatch.prototype = {
+    _sendData$1: function(data) {
+      this.$ti._precomputed1._check(data);
+      this.get$_async$_subscription()._add$1(data);
+    },
+    _sendError$2: function(error, stackTrace) {
+      this.get$_async$_subscription()._async$_addError$2(error, stackTrace);
+    },
+    _sendDone$0: function() {
+      this.get$_async$_subscription()._close$0();
+    }
+  };
+  P._AsyncStreamControllerDispatch.prototype = {
+    _sendData$1: function(data) {
+      var t1 = this.$ti;
+      t1._precomputed1._check(data);
+      this.get$_async$_subscription()._addPending$1(new P._DelayedData(data, t1._eval$1("_DelayedData<1>")));
+    },
+    _sendError$2: function(error, stackTrace) {
+      this.get$_async$_subscription()._addPending$1(new P._DelayedError(error, stackTrace));
+    },
+    _sendDone$0: function() {
+      this.get$_async$_subscription()._addPending$1(C.C__DelayedDone);
+    }
+  };
+  P._AsyncStreamController.prototype = {};
+  P._SyncStreamController.prototype = {};
+  P._ControllerStream.prototype = {
+    _createSubscription$4: function(onData, onError, onDone, cancelOnError) {
+      return this._controller._subscribe$4(H._instanceType(this)._eval$1("~(1)")._check(onData), onError, type$.void_Function._check(onDone), cancelOnError);
+    },
+    get$hashCode: function(_) {
+      return (H.Primitives_objectHashCode(this._controller) ^ 892482866) >>> 0;
+    },
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      if (this === other)
+        return true;
+      return other instanceof P._ControllerStream && other._controller === this._controller;
+    }
+  };
+  P._ControllerSubscription.prototype = {
+    _onCancel$0: function() {
+      return this._controller._recordCancel$1(this);
+    },
+    _onPause$0: function() {
+      this._controller._recordPause$1(this);
+    },
+    _onResume$0: function() {
+      this._controller._recordResume$1(this);
+    }
+  };
+  P._StreamSinkWrapper.prototype = {
+    add$1: function(_, data) {
+      this._async$_target.add$1(0, this.$ti._precomputed1._check(data));
+    },
+    $isEventSink: 1,
+    $isStreamConsumer: 1,
+    $isStreamSink: 1,
+    $isSink: 1
+  };
+  P._AddStreamState.prototype = {
+    cancel$0: function() {
+      var cancel = this.addSubscription.cancel$0();
+      if (cancel == null) {
+        this.addStreamFuture._asyncComplete$1(null);
+        return null;
+      }
+      return cancel.whenComplete$1(new P._AddStreamState_cancel_closure(this));
+    }
+  };
+  P._AddStreamState_makeErrorHandler_closure.prototype = {
+    call$2: function(e, s) {
+      var t1 = this.controller;
+      t1._async$_addError$2(e, type$.StackTrace._check(s));
+      t1._close$0();
+    },
+    $signature: 5
+  };
+  P._AddStreamState_cancel_closure.prototype = {
+    call$0: function() {
+      this.$this.addStreamFuture._asyncComplete$1(null);
+    },
+    $signature: 0
+  };
+  P._StreamControllerAddStreamState.prototype = {};
+  P._BufferingStreamSubscription.prototype = {
+    _BufferingStreamSubscription$4: function(onData, onError, onDone, cancelOnError, $T) {
+      this.onData$1(onData);
+      this.onError$1(0, onError);
+      this.onDone$1(onDone);
+    },
+    _setPendingEvents$1: function(pendingEvents) {
+      var _this = this;
+      H._instanceType(_this)._eval$1("_PendingEvents<_BufferingStreamSubscription.T>")._check(pendingEvents);
+      H.assertHelper(_this._pending == null);
+      if (pendingEvents == null)
+        return;
+      _this.set$_pending(pendingEvents);
+      if (!pendingEvents.get$isEmpty(pendingEvents)) {
+        _this._state = (_this._state | 64) >>> 0;
+        _this._pending.schedule$1(_this);
+      }
+    },
+    onData$1: function(handleData) {
+      var t1 = H._instanceType(this);
+      t1._eval$1("~(_BufferingStreamSubscription.T)")._check(handleData);
+      if (handleData == null)
+        handleData = P.async___nullDataHandler$closure();
+      this.set$_onData(this._zone.registerUnaryCallback$2$1(handleData, type$.dynamic, t1._eval$1("_BufferingStreamSubscription.T")));
+    },
+    onError$1: function(_, handleError) {
+      var _this = this;
+      if (handleError == null)
+        handleError = P.async___nullErrorHandler$closure();
+      if (type$.void_Function_Object_StackTrace._is(handleError))
+        _this._onError = _this._zone.registerBinaryCallback$3$1(handleError, type$.dynamic, type$.Object, type$.StackTrace);
+      else if (type$.void_Function_Object._is(handleError))
+        _this._onError = _this._zone.registerUnaryCallback$2$1(handleError, type$.dynamic, type$.Object);
+      else
+        throw H.wrapException(P.ArgumentError$("handleError callback must take either an Object (the error), or both an Object (the error) and a StackTrace."));
+    },
+    onDone$1: function(handleDone) {
+      type$.void_Function._check(handleDone);
+      if (handleDone == null)
+        handleDone = P.async___nullDoneHandler$closure();
+      this.set$_onDone(this._zone.registerCallback$1$1(handleDone, type$.void));
+    },
+    pause$1: function(resumeSignal) {
+      var t2, t3, _this = this,
+        t1 = _this._state;
+      if ((t1 & 8) !== 0)
+        return;
+      t2 = (t1 + 128 | 4) >>> 0;
+      _this._state = t2;
+      if (t1 < 128 && _this._pending != null) {
+        t3 = _this._pending;
+        if (t3._state === 1)
+          t3._state = 3;
+      }
+      if ((t1 & 4) === 0 && (t2 & 32) === 0)
+        _this._guardCallback$1(_this.get$_onPause());
+    },
+    pause$0: function() {
+      return this.pause$1(null);
+    },
+    resume$0: function() {
+      var _this = this,
+        t1 = _this._state;
+      if ((t1 & 8) !== 0)
+        return;
+      if (t1 >= 128) {
+        t1 = _this._state -= 128;
+        if (t1 < 128) {
+          if ((t1 & 64) !== 0) {
+            t1 = _this._pending;
+            t1 = !t1.get$isEmpty(t1);
+          } else
+            t1 = false;
+          if (t1)
+            _this._pending.schedule$1(_this);
+          else {
+            H.assertHelper(_this.get$_mayResumeInput());
+            t1 = (_this._state & 4294967291) >>> 0;
+            _this._state = t1;
+            if ((t1 & 32) === 0)
+              _this._guardCallback$1(_this.get$_onResume());
+          }
+        }
+      }
+    },
+    cancel$0: function() {
+      var _this = this,
+        t1 = (_this._state & 4294967279) >>> 0;
+      _this._state = t1;
+      if ((t1 & 8) === 0)
+        _this._cancel$0();
+      t1 = _this._cancelFuture;
+      return t1 == null ? $.$get$Future__nullFuture() : t1;
+    },
+    get$_mayResumeInput: function() {
+      if (this._state < 128) {
+        var t1 = this._pending;
+        t1 = t1 == null || t1.get$isEmpty(t1);
+      } else
+        t1 = false;
+      return t1;
+    },
+    get$isPaused: function() {
+      return this._state >= 128;
+    },
+    _cancel$0: function() {
+      var t2, _this = this,
+        t1 = _this._state = (_this._state | 8) >>> 0;
+      if ((t1 & 64) !== 0) {
+        t2 = _this._pending;
+        if (t2._state === 1)
+          t2._state = 3;
+      }
+      if ((t1 & 32) === 0)
+        _this.set$_pending(null);
+      _this._cancelFuture = _this._onCancel$0();
+    },
+    _add$1: function(data) {
+      var t2, _this = this,
+        t1 = H._instanceType(_this);
+      t1._eval$1("_BufferingStreamSubscription.T")._check(data);
+      H.assertHelper((_this._state & 2) === 0);
+      t2 = _this._state;
+      if ((t2 & 8) !== 0)
+        return;
+      if (t2 < 32)
+        _this._sendData$1(data);
+      else
+        _this._addPending$1(new P._DelayedData(data, t1._eval$1("_DelayedData<_BufferingStreamSubscription.T>")));
+    },
+    _async$_addError$2: function(error, stackTrace) {
+      var t1 = this._state;
+      if ((t1 & 8) !== 0)
+        return;
+      if (t1 < 32)
+        this._sendError$2(error, stackTrace);
+      else
+        this._addPending$1(new P._DelayedError(error, stackTrace));
+    },
+    _close$0: function() {
+      var t1, _this = this;
+      H.assertHelper((_this._state & 2) === 0);
+      t1 = _this._state;
+      if ((t1 & 8) !== 0)
+        return;
+      t1 = (t1 | 2) >>> 0;
+      _this._state = t1;
+      if (t1 < 32)
+        _this._sendDone$0();
+      else
+        _this._addPending$1(C.C__DelayedDone);
+    },
+    _onPause$0: function() {
+      H.assertHelper((this._state & 4) !== 0);
+    },
+    _onResume$0: function() {
+      H.assertHelper((this._state & 4) === 0);
+    },
+    _onCancel$0: function() {
+      H.assertHelper((this._state & 8) !== 0);
+      return null;
+    },
+    _addPending$1: function($event) {
+      var _this = this,
+        t1 = H._instanceType(_this)._eval$1("_StreamImplEvents<_BufferingStreamSubscription.T>"),
+        pending = t1._check(_this._pending);
+      if (pending == null) {
+        pending = new P._StreamImplEvents(t1);
+        _this.set$_pending(pending);
+      }
+      pending.add$1(0, $event);
+      t1 = _this._state;
+      if ((t1 & 64) === 0) {
+        t1 = (t1 | 64) >>> 0;
+        _this._state = t1;
+        if (t1 < 128)
+          _this._pending.schedule$1(_this);
+      }
+    },
+    _sendData$1: function(data) {
+      var t2, _this = this,
+        t1 = H._instanceType(_this)._eval$1("_BufferingStreamSubscription.T");
+      t1._check(data);
+      H.assertHelper((_this._state & 8) === 0);
+      H.assertHelper(_this._state < 128);
+      H.assertHelper((_this._state & 32) === 0);
+      t2 = _this._state;
+      _this._state = (t2 | 32) >>> 0;
+      _this._zone.runUnaryGuarded$1$2(_this._onData, data, t1);
+      _this._state = (_this._state & 4294967263) >>> 0;
+      _this._checkState$1((t2 & 4) !== 0);
+    },
+    _sendError$2: function(error, stackTrace) {
+      var t1, t2, _this = this;
+      type$.StackTrace._check(stackTrace);
+      H.assertHelper((_this._state & 8) === 0);
+      H.assertHelper(_this._state < 128);
+      H.assertHelper((_this._state & 32) === 0);
+      t1 = _this._state;
+      t2 = new P._BufferingStreamSubscription__sendError_sendError(_this, error, stackTrace);
+      if ((t1 & 1) !== 0) {
+        _this._state = (t1 | 16) >>> 0;
+        _this._cancel$0();
+        t1 = _this._cancelFuture;
+        if (t1 != null && t1 !== $.$get$Future__nullFuture())
+          t1.whenComplete$1(t2);
+        else
+          t2.call$0();
+      } else {
+        t2.call$0();
+        _this._checkState$1((t1 & 4) !== 0);
+      }
+    },
+    _sendDone$0: function() {
+      var t1, t2, _this = this;
+      H.assertHelper((_this._state & 8) === 0);
+      H.assertHelper(_this._state < 128);
+      H.assertHelper((_this._state & 32) === 0);
+      t1 = new P._BufferingStreamSubscription__sendDone_sendDone(_this);
+      _this._cancel$0();
+      _this._state = (_this._state | 16) >>> 0;
+      t2 = _this._cancelFuture;
+      if (t2 != null && t2 !== $.$get$Future__nullFuture())
+        t2.whenComplete$1(t1);
+      else
+        t1.call$0();
+    },
+    _guardCallback$1: function(callback) {
+      var t1, _this = this;
+      type$.void_Function._check(callback);
+      H.assertHelper((_this._state & 32) === 0);
+      t1 = _this._state;
+      _this._state = (t1 | 32) >>> 0;
+      callback.call$0();
+      _this._state = (_this._state & 4294967263) >>> 0;
+      _this._checkState$1((t1 & 4) !== 0);
+    },
+    _checkState$1: function(wasInputPaused) {
+      var t1, isInputPaused, _this = this;
+      H.assertHelper((_this._state & 32) === 0);
+      if ((_this._state & 64) !== 0) {
+        t1 = _this._pending;
+        t1 = t1.get$isEmpty(t1);
+      } else
+        t1 = false;
+      if (t1) {
+        t1 = (_this._state & 4294967231) >>> 0;
+        _this._state = t1;
+        if ((t1 & 4) !== 0 && _this.get$_mayResumeInput())
+          _this._state = (_this._state & 4294967291) >>> 0;
+      }
+      for (; true; wasInputPaused = isInputPaused) {
+        t1 = _this._state;
+        if ((t1 & 8) !== 0) {
+          _this.set$_pending(null);
+          return;
+        }
+        isInputPaused = (t1 & 4) !== 0;
+        if (wasInputPaused === isInputPaused)
+          break;
+        _this._state = (t1 ^ 32) >>> 0;
+        if (isInputPaused)
+          _this._onPause$0();
+        else
+          _this._onResume$0();
+        _this._state = (_this._state & 4294967263) >>> 0;
+      }
+      t1 = _this._state;
+      if ((t1 & 64) !== 0 && t1 < 128)
+        _this._pending.schedule$1(_this);
+    },
+    set$_onData: function(_onData) {
+      this._onData = H._instanceType(this)._eval$1("~(_BufferingStreamSubscription.T)")._check(_onData);
+    },
+    set$_onDone: function(_onDone) {
+      this._onDone = type$.void_Function._check(_onDone);
+    },
+    set$_pending: function(_pending) {
+      this._pending = H._instanceType(this)._eval$1("_PendingEvents<_BufferingStreamSubscription.T>")._check(_pending);
+    },
+    $isStreamSubscription: 1,
+    $is_EventDispatch: 1
+  };
+  P._BufferingStreamSubscription__sendError_sendError.prototype = {
+    call$0: function() {
+      var onError, t3, t4, t5,
+        t1 = this.$this,
+        t2 = t1._state;
+      if ((t2 & 8) !== 0 && (t2 & 16) === 0)
+        return;
+      t1._state = (t2 | 32) >>> 0;
+      onError = t1._onError;
+      t2 = this.error;
+      t3 = type$.Object;
+      t4 = t1._zone;
+      if (type$.void_Function_Object_StackTrace._is(onError))
+        t4.runBinaryGuarded$2$3(onError, t2, this.stackTrace, t3, type$.StackTrace);
+      else {
+        t5 = type$.void_Function_Object;
+        H.assertHelper(t5._is(onError));
+        t4.runUnaryGuarded$1$2(t5._check(t1._onError), t2, t3);
+      }
+      t1._state = (t1._state & 4294967263) >>> 0;
+    },
+    $signature: 1
+  };
+  P._BufferingStreamSubscription__sendDone_sendDone.prototype = {
+    call$0: function() {
+      var t1 = this.$this,
+        t2 = t1._state;
+      if ((t2 & 16) === 0)
+        return;
+      t1._state = (t2 | 42) >>> 0;
+      t1._zone.runGuarded$1(t1._onDone);
+      t1._state = (t1._state & 4294967263) >>> 0;
+    },
+    $signature: 1
+  };
+  P._StreamImpl.prototype = {
+    listen$4$cancelOnError$onDone$onError: function(onData, cancelOnError, onDone, onError) {
+      return this._createSubscription$4(H._instanceType(this)._eval$1("~(1)")._check(onData), onError, type$.void_Function._check(onDone), true === H._checkBoolNullable(cancelOnError));
+    },
+    listen$2$onDone: function(onData, onDone) {
+      return this.listen$4$cancelOnError$onDone$onError(onData, null, onDone, null);
+    },
+    listen$3$onDone$onError: function(onData, onDone, onError) {
+      return this.listen$4$cancelOnError$onDone$onError(onData, null, onDone, onError);
+    },
+    listen$1: function(onData) {
+      return this.listen$4$cancelOnError$onDone$onError(onData, null, null, null);
+    },
+    _createSubscription$4: function(onData, onError, onDone, cancelOnError) {
+      var t1 = H._instanceType(this);
+      return P._BufferingStreamSubscription$(t1._eval$1("~(1)")._check(onData), onError, type$.void_Function._check(onDone), cancelOnError, t1._precomputed1);
+    }
+  };
+  P._GeneratedStreamImpl.prototype = {
+    _createSubscription$4: function(onData, onError, onDone, cancelOnError) {
+      var _this = this,
+        t1 = _this.$ti;
+      t1._eval$1("~(1)")._check(onData);
+      type$.void_Function._check(onDone);
+      if (_this._isUsed)
+        throw H.wrapException(P.StateError$("Stream has already been listened to."));
+      _this._isUsed = true;
+      t1 = P._BufferingStreamSubscription$(onData, onError, onDone, cancelOnError, t1._precomputed1);
+      t1._setPendingEvents$1(_this._pending.call$0());
+      return t1;
+    }
+  };
+  P._IterablePendingEvents.prototype = {
+    get$isEmpty: function(_) {
+      return this._async$_iterator == null;
+    },
+    handleNext$1: function(dispatch) {
+      var hasMore, e, s, t1, exception, _this = this;
+      _this.$ti._eval$1("_EventDispatch<1>")._check(dispatch);
+      t1 = _this._async$_iterator;
+      if (t1 == null)
+        throw H.wrapException(P.StateError$("No events pending."));
+      hasMore = null;
+      try {
+        hasMore = t1.moveNext$0();
+        if (H.boolConversionCheck(hasMore))
+          dispatch._sendData$1(_this._async$_iterator.get$current());
+        else {
+          _this.set$_async$_iterator(null);
+          dispatch._sendDone$0();
+        }
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        s = H.getTraceFromException(exception);
+        if (hasMore == null) {
+          _this.set$_async$_iterator(C.C_EmptyIterator);
+          dispatch._sendError$2(e, s);
+        } else
+          dispatch._sendError$2(e, s);
+      }
+    },
+    set$_async$_iterator: function(_iterator) {
+      this._async$_iterator = this.$ti._eval$1("Iterator<1>")._check(_iterator);
+    }
+  };
+  P._DelayedEvent.prototype = {
+    set$next: function(next) {
+      this.next = type$._DelayedEvent_dynamic._check(next);
+    },
+    get$next: function() {
+      return this.next;
+    }
+  };
+  P._DelayedData.prototype = {
+    perform$1: function(dispatch) {
+      this.$ti._eval$1("_EventDispatch<1>")._check(dispatch)._sendData$1(this.value);
+    }
+  };
+  P._DelayedError.prototype = {
+    perform$1: function(dispatch) {
+      dispatch._sendError$2(this.error, this.stackTrace);
+    }
+  };
+  P._DelayedDone.prototype = {
+    perform$1: function(dispatch) {
+      dispatch._sendDone$0();
+    },
+    get$next: function() {
+      return null;
+    },
+    set$next: function(_) {
+      throw H.wrapException(P.StateError$("No events after a done."));
+    },
+    $is_DelayedEvent: 1
+  };
+  P._PendingEvents.prototype = {
+    schedule$1: function(dispatch) {
+      var t1, _this = this;
+      H._instanceType(_this)._eval$1("_EventDispatch<1>")._check(dispatch);
+      if (_this._state === 1)
+        return;
+      H.assertHelper(!_this.get$isEmpty(_this));
+      t1 = _this._state;
+      if (t1 >= 1) {
+        H.assertHelper(t1 === 3);
+        _this._state = 1;
+        return;
+      }
+      P.scheduleMicrotask(new P._PendingEvents_schedule_closure(_this, dispatch));
+      _this._state = 1;
+    }
+  };
+  P._PendingEvents_schedule_closure.prototype = {
+    call$0: function() {
+      var t1 = this.$this,
+        oldState = t1._state;
+      t1._state = 0;
+      if (oldState === 3)
+        return;
+      t1.handleNext$1(this.dispatch);
+    },
+    $signature: 0
+  };
+  P._StreamImplEvents.prototype = {
+    get$isEmpty: function(_) {
+      return this.lastPendingEvent == null;
+    },
+    add$1: function(_, $event) {
+      var _this = this,
+        t1 = _this.lastPendingEvent;
+      if (t1 == null)
+        _this.firstPendingEvent = _this.lastPendingEvent = $event;
+      else {
+        t1.set$next($event);
+        _this.lastPendingEvent = $event;
+      }
+    },
+    handleNext$1: function(dispatch) {
+      var $event, t1, _this = this;
+      _this.$ti._eval$1("_EventDispatch<1>")._check(dispatch);
+      H.assertHelper(_this._state !== 1);
+      $event = _this.firstPendingEvent;
+      t1 = $event.get$next();
+      _this.firstPendingEvent = t1;
+      if (t1 == null)
+        _this.lastPendingEvent = null;
+      $event.perform$1(dispatch);
+    }
+  };
+  P._DoneStreamSubscription.prototype = {
+    get$isPaused: function() {
+      return this._state >= 4;
+    },
+    _schedule$0: function() {
+      var _this = this;
+      if ((_this._state & 2) !== 0)
+        return;
+      _this._zone.scheduleMicrotask$1(_this.get$_sendDone());
+      _this._state = (_this._state | 2) >>> 0;
+    },
+    onData$1: function(handleData) {
+      this.$ti._eval$1("~(1)")._check(handleData);
+    },
+    onError$1: function(_, handleError) {
+    },
+    onDone$1: function(handleDone) {
+      this.set$_onDone(type$.void_Function._check(handleDone));
+    },
+    pause$1: function(resumeSignal) {
+      this._state += 4;
+    },
+    pause$0: function() {
+      return this.pause$1(null);
+    },
+    resume$0: function() {
+      var t1 = this._state;
+      if (t1 >= 4) {
+        t1 = this._state = t1 - 4;
+        if (t1 < 4 && (t1 & 1) === 0)
+          this._schedule$0();
+      }
+    },
+    cancel$0: function() {
+      return $.$get$Future__nullFuture();
+    },
+    _sendDone$0: function() {
+      var _this = this,
+        t1 = _this._state = (_this._state & 4294967293) >>> 0;
+      if (t1 >= 4)
+        return;
+      _this._state = (t1 | 1) >>> 0;
+      t1 = _this._onDone;
+      if (t1 != null)
+        _this._zone.runGuarded$1(t1);
+    },
+    set$_onDone: function(_onDone) {
+      this._onDone = type$.void_Function._check(_onDone);
+    },
+    $isStreamSubscription: 1
+  };
+  P._StreamIterator.prototype = {};
+  P._EmptyStream.prototype = {
+    get$isBroadcast: function() {
+      return true;
+    },
+    listen$4$cancelOnError$onDone$onError: function(onData, cancelOnError, onDone, onError) {
+      var t1 = this.$ti;
+      t1._eval$1("~(1)")._check(onData);
+      type$.void_Function._check(onDone);
+      H._checkBoolNullable(cancelOnError);
+      t1 = new P._DoneStreamSubscription($.Zone__current, onDone, t1._eval$1("_DoneStreamSubscription<1>"));
+      t1._schedule$0();
+      return t1;
+    },
+    listen$3$onDone$onError: function(onData, onDone, onError) {
+      return this.listen$4$cancelOnError$onDone$onError(onData, null, onDone, onError);
+    },
+    listen$1: function(onData) {
+      return this.listen$4$cancelOnError$onDone$onError(onData, null, null, null);
+    }
+  };
+  P._cancelAndError_closure.prototype = {
+    call$0: function() {
+      return this.future._completeError$2(this.error, this.stackTrace);
+    },
+    $signature: 1
+  };
+  P._cancelAndErrorClosure_closure.prototype = {
+    call$2: function(error, stackTrace) {
+      P._cancelAndError(this.subscription, this.future, error, type$.StackTrace._check(stackTrace));
+    },
+    $signature: 5
+  };
+  P._cancelAndValue_closure.prototype = {
+    call$0: function() {
+      return this.future._complete$1(this.value);
+    },
+    $signature: 1
+  };
+  P.Timer.prototype = {};
+  P.AsyncError.prototype = {
+    toString$0: function(_) {
+      return H.S(this.error);
+    },
+    $isError: 1
+  };
+  P._ZoneFunction.prototype = {};
+  P.ZoneSpecification.prototype = {};
+  P._ZoneSpecification.prototype = {$isZoneSpecification: 1};
+  P.ZoneDelegate.prototype = {};
+  P.Zone.prototype = {};
+  P._ZoneDelegate.prototype = {
+    handleUncaughtError$3: function(zone, error, stackTrace) {
+      var implementation, implZone;
+      type$.StackTrace._check(stackTrace);
+      implementation = this._delegationTarget.get$_handleUncaughtError();
+      implZone = implementation.zone;
+      return implementation.$function.call$5(implZone, P._parentDelegate(implZone), zone, error, stackTrace);
+    },
+    registerCallback$1$2: function(zone, f, $R) {
+      var implementation, implZone;
+      $R._eval$1("0()")._check(f);
+      implementation = this._delegationTarget.get$_registerCallback();
+      implZone = implementation.zone;
+      return type$.A_Function_Function_A_4_Zone_and_ZoneDelegate_and_Zone_and_A_Function._check(implementation.$function).call$1$4(implZone, P._parentDelegate(implZone), zone, f, $R);
+    },
+    registerUnaryCallback$2$2: function(zone, f, $R, $T) {
+      var implementation, implZone;
+      $R._eval$1("@<0>")._bind$1($T)._eval$1("1(2)")._check(f);
+      implementation = this._delegationTarget.get$_registerUnaryCallback();
+      implZone = implementation.zone;
+      return type$.A_Function_B_Function_A_and_B_4_Zone_and_ZoneDelegate_and_Zone_and_A_Function_B._check(implementation.$function).call$2$4(implZone, P._parentDelegate(implZone), zone, f, $R, $T);
+    },
+    registerBinaryCallback$3$2: function(zone, f, $R, T1, T2) {
+      var implementation, implZone;
+      $R._eval$1("@<0>")._bind$1(T1)._bind$1(T2)._eval$1("1(2,3)")._check(f);
+      implementation = this._delegationTarget.get$_registerBinaryCallback();
+      implZone = implementation.zone;
+      return type$.A_Function_2_B_and_C_Function_A_and_B_and_C_4_Zone_and_ZoneDelegate_and_Zone_and_A_Function_2_B_and_C._check(implementation.$function).call$3$4(implZone, P._parentDelegate(implZone), zone, f, $R, T1, T2);
+    },
+    errorCallback$3: function(zone, error, stackTrace) {
+      var implementation = this._delegationTarget.get$_errorCallback(),
+        implZone = implementation.zone;
+      if (implZone === C.C__RootZone)
+        return null;
+      return implementation.$function.call$5(implZone, P._parentDelegate(implZone), zone, error, stackTrace);
+    },
+    $isZoneDelegate: 1
+  };
+  P._Zone.prototype = {$isZone: 1};
+  P._CustomZone.prototype = {
+    get$_delegate: function() {
+      var t1 = this._delegateCache;
+      if (t1 != null)
+        return t1;
+      return this._delegateCache = new P._ZoneDelegate(this);
+    },
+    get$errorZone: function() {
+      return this._handleUncaughtError.zone;
+    },
+    runGuarded$1: function(f) {
+      var e, s, exception;
+      type$.void_Function._check(f);
+      try {
+        this.run$1$1(f, type$.void);
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        s = H.getTraceFromException(exception);
+        this.handleUncaughtError$2(e, s);
+      }
+    },
+    runUnaryGuarded$1$2: function(f, arg, $T) {
+      var e, s, exception;
+      $T._eval$1("~(0)")._check(f);
+      $T._check(arg);
+      try {
+        this.runUnary$2$2(f, arg, type$.void, $T);
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        s = H.getTraceFromException(exception);
+        this.handleUncaughtError$2(e, s);
+      }
+    },
+    runBinaryGuarded$2$3: function(f, arg1, arg2, T1, T2) {
+      var e, s, exception;
+      T1._eval$1("@<0>")._bind$1(T2)._eval$1("~(1,2)")._check(f);
+      T1._check(arg1);
+      T2._check(arg2);
+      try {
+        this.runBinary$3$3(f, arg1, arg2, type$.void, T1, T2);
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        s = H.getTraceFromException(exception);
+        this.handleUncaughtError$2(e, s);
+      }
+    },
+    bindCallback$1$1: function(f, $R) {
+      return new P._CustomZone_bindCallback_closure(this, this.registerCallback$1$1($R._eval$1("0()")._check(f), $R), $R);
+    },
+    bindUnaryCallback$2$1: function(f, $R, $T) {
+      return new P._CustomZone_bindUnaryCallback_closure(this, this.registerUnaryCallback$2$1($R._eval$1("@<0>")._bind$1($T)._eval$1("1(2)")._check(f), $R, $T), $T, $R);
+    },
+    bindCallbackGuarded$1: function(f) {
+      return new P._CustomZone_bindCallbackGuarded_closure(this, this.registerCallback$1$1(type$.void_Function._check(f), type$.void));
+    },
+    bindUnaryCallbackGuarded$1$1: function(f, $T) {
+      return new P._CustomZone_bindUnaryCallbackGuarded_closure(this, this.registerUnaryCallback$2$1($T._eval$1("~(0)")._check(f), type$.void, $T), $T);
+    },
+    $index: function(_, key) {
+      var value,
+        t1 = this._async$_map,
+        result = t1.$index(0, key);
+      if (result != null || t1.containsKey$1(key))
+        return result;
+      value = this.parent.$index(0, key);
+      if (value != null)
+        t1.$indexSet(0, key, value);
+      return value;
+    },
+    handleUncaughtError$2: function(error, stackTrace) {
+      var implementation, t1, parentDelegate;
+      type$.StackTrace._check(stackTrace);
+      implementation = this._handleUncaughtError;
+      H.assertHelper(implementation != null);
+      t1 = implementation.zone;
+      parentDelegate = P._parentDelegate(t1);
+      return implementation.$function.call$5(t1, parentDelegate, this, error, stackTrace);
+    },
+    fork$2$specification$zoneValues: function(specification, zoneValues) {
+      var t1, parentDelegate,
+        implementation = this._fork;
+      H.assertHelper(implementation != null);
+      t1 = implementation.zone;
+      parentDelegate = P._parentDelegate(t1);
+      return implementation.$function.call$5(t1, parentDelegate, this, specification, zoneValues);
+    },
+    run$1$1: function(f, $R) {
+      var implementation, t1, parentDelegate;
+      $R._eval$1("0()")._check(f);
+      implementation = this._run;
+      H.assertHelper(implementation != null);
+      t1 = implementation.zone;
+      parentDelegate = P._parentDelegate(t1);
+      return type$.A_Function_A_4_Zone_and_ZoneDelegate_and_Zone_and_A_Function._check(implementation.$function).call$1$4(t1, parentDelegate, this, f, $R);
+    },
+    runUnary$2$2: function(f, arg, $R, $T) {
+      var implementation, t1, parentDelegate;
+      $R._eval$1("@<0>")._bind$1($T)._eval$1("1(2)")._check(f);
+      $T._check(arg);
+      implementation = this._runUnary;
+      H.assertHelper(implementation != null);
+      t1 = implementation.zone;
+      parentDelegate = P._parentDelegate(t1);
+      return type$.A_Function_A_and_B_5_Zone_and_ZoneDelegate_and_Zone_and_A_Function_B_and_B._check(implementation.$function).call$2$5(t1, parentDelegate, this, f, arg, $R, $T);
+    },
+    runBinary$3$3: function(f, arg1, arg2, $R, T1, T2) {
+      var implementation, t1, parentDelegate;
+      $R._eval$1("@<0>")._bind$1(T1)._bind$1(T2)._eval$1("1(2,3)")._check(f);
+      T1._check(arg1);
+      T2._check(arg2);
+      implementation = this._runBinary;
+      H.assertHelper(implementation != null);
+      t1 = implementation.zone;
+      parentDelegate = P._parentDelegate(t1);
+      return type$.A_Function_A_and_B_and_C_6_Zone_and_ZoneDelegate_and_Zone_and_A_Function_2_B_and_C_and_B_and_C._check(implementation.$function).call$3$6(t1, parentDelegate, this, f, arg1, arg2, $R, T1, T2);
+    },
+    registerCallback$1$1: function(callback, $R) {
+      var implementation, t1, parentDelegate;
+      $R._eval$1("0()")._check(callback);
+      implementation = this._registerCallback;
+      H.assertHelper(implementation != null);
+      t1 = implementation.zone;
+      parentDelegate = P._parentDelegate(t1);
+      return type$.A_Function_Function_A_4_Zone_and_ZoneDelegate_and_Zone_and_A_Function._check(implementation.$function).call$1$4(t1, parentDelegate, this, callback, $R);
+    },
+    registerUnaryCallback$2$1: function(callback, $R, $T) {
+      var implementation, t1, parentDelegate;
+      $R._eval$1("@<0>")._bind$1($T)._eval$1("1(2)")._check(callback);
+      implementation = this._registerUnaryCallback;
+      H.assertHelper(implementation != null);
+      t1 = implementation.zone;
+      parentDelegate = P._parentDelegate(t1);
+      return type$.A_Function_B_Function_A_and_B_4_Zone_and_ZoneDelegate_and_Zone_and_A_Function_B._check(implementation.$function).call$2$4(t1, parentDelegate, this, callback, $R, $T);
+    },
+    registerBinaryCallback$3$1: function(callback, $R, T1, T2) {
+      var implementation, t1, parentDelegate;
+      $R._eval$1("@<0>")._bind$1(T1)._bind$1(T2)._eval$1("1(2,3)")._check(callback);
+      implementation = this._registerBinaryCallback;
+      H.assertHelper(implementation != null);
+      t1 = implementation.zone;
+      parentDelegate = P._parentDelegate(t1);
+      return type$.A_Function_2_B_and_C_Function_A_and_B_and_C_4_Zone_and_ZoneDelegate_and_Zone_and_A_Function_2_B_and_C._check(implementation.$function).call$3$4(t1, parentDelegate, this, callback, $R, T1, T2);
+    },
+    errorCallback$2: function(error, stackTrace) {
+      var implementation, implementationZone, parentDelegate;
+      type$.StackTrace._check(stackTrace);
+      implementation = this._errorCallback;
+      H.assertHelper(implementation != null);
+      implementationZone = implementation.zone;
+      if (implementationZone === C.C__RootZone)
+        return null;
+      parentDelegate = P._parentDelegate(implementationZone);
+      return implementation.$function.call$5(implementationZone, parentDelegate, this, error, stackTrace);
+    },
+    scheduleMicrotask$1: function(f) {
+      var implementation, t1, parentDelegate;
+      type$.void_Function._check(f);
+      implementation = this._scheduleMicrotask;
+      H.assertHelper(implementation != null);
+      t1 = implementation.zone;
+      parentDelegate = P._parentDelegate(t1);
+      return implementation.$function.call$4(t1, parentDelegate, this, f);
+    },
+    createTimer$2: function(duration, f) {
+      var implementation, t1, parentDelegate;
+      type$.void_Function._check(f);
+      implementation = this._createTimer;
+      H.assertHelper(implementation != null);
+      t1 = implementation.zone;
+      parentDelegate = P._parentDelegate(t1);
+      return implementation.$function.call$5(t1, parentDelegate, this, duration, f);
+    },
+    print$1: function(_, line) {
+      var t1, parentDelegate,
+        implementation = this._print;
+      H.assertHelper(implementation != null);
+      t1 = implementation.zone;
+      parentDelegate = P._parentDelegate(t1);
+      return implementation.$function.call$4(t1, parentDelegate, this, line);
+    },
+    set$_run: function(_run) {
+      this._run = type$._ZoneFunction_Function._check(_run);
+    },
+    set$_runUnary: function(_runUnary) {
+      this._runUnary = type$._ZoneFunction_Function._check(_runUnary);
+    },
+    set$_runBinary: function(_runBinary) {
+      this._runBinary = type$._ZoneFunction_Function._check(_runBinary);
+    },
+    set$_registerCallback: function(_registerCallback) {
+      this._registerCallback = type$._ZoneFunction_Function._check(_registerCallback);
+    },
+    set$_registerUnaryCallback: function(_registerUnaryCallback) {
+      this._registerUnaryCallback = type$._ZoneFunction_Function._check(_registerUnaryCallback);
+    },
+    set$_registerBinaryCallback: function(_registerBinaryCallback) {
+      this._registerBinaryCallback = type$._ZoneFunction_Function._check(_registerBinaryCallback);
+    },
+    set$_errorCallback: function(_errorCallback) {
+      this._errorCallback = type$._ZoneFunction_of_AsyncError_Function_Zone_ZoneDelegate_Zone_Object_StackTrace._check(_errorCallback);
+    },
+    set$_scheduleMicrotask: function(_scheduleMicrotask) {
+      this._scheduleMicrotask = type$._ZoneFunction_of_void_Function_4_Zone_and_ZoneDelegate_and_Zone_and_void_Function._check(_scheduleMicrotask);
+    },
+    set$_createTimer: function(_createTimer) {
+      this._createTimer = type$._ZoneFunction_of_Timer_Function_5_Zone_and_ZoneDelegate_and_Zone_and_Duration_and_void_Function._check(_createTimer);
+    },
+    set$_createPeriodicTimer: function(_createPeriodicTimer) {
+      this._createPeriodicTimer = type$._ZoneFunction_of_Timer_Function_5_Zone_and_ZoneDelegate_and_Zone_and_Duration_and_void_Function_Timer._check(_createPeriodicTimer);
+    },
+    set$_print: function(_print) {
+      this._print = type$._ZoneFunction_of_void_Function_Zone_ZoneDelegate_Zone_String._check(_print);
+    },
+    set$_fork: function(_fork) {
+      this._fork = type$._ZoneFunction_of_Zone_Function_5_Zone_and_ZoneDelegate_and_Zone_and_ZoneSpecification_and_Map_dynamic_dynamic._check(_fork);
+    },
+    set$_handleUncaughtError: function(_handleUncaughtError) {
+      this._handleUncaughtError = type$._ZoneFunction_of_void_Function_Zone_ZoneDelegate_Zone_Object_StackTrace._check(_handleUncaughtError);
+    },
+    get$_run: function() {
+      return this._run;
+    },
+    get$_runUnary: function() {
+      return this._runUnary;
+    },
+    get$_runBinary: function() {
+      return this._runBinary;
+    },
+    get$_registerCallback: function() {
+      return this._registerCallback;
+    },
+    get$_registerUnaryCallback: function() {
+      return this._registerUnaryCallback;
+    },
+    get$_registerBinaryCallback: function() {
+      return this._registerBinaryCallback;
+    },
+    get$_errorCallback: function() {
+      return this._errorCallback;
+    },
+    get$_scheduleMicrotask: function() {
+      return this._scheduleMicrotask;
+    },
+    get$_createTimer: function() {
+      return this._createTimer;
+    },
+    get$_createPeriodicTimer: function() {
+      return this._createPeriodicTimer;
+    },
+    get$_print: function() {
+      return this._print;
+    },
+    get$_fork: function() {
+      return this._fork;
+    },
+    get$_handleUncaughtError: function() {
+      return this._handleUncaughtError;
+    },
+    get$parent: function(receiver) {
+      return this.parent;
+    },
+    get$_async$_map: function() {
+      return this._async$_map;
+    }
+  };
+  P._CustomZone_bindCallback_closure.prototype = {
+    call$0: function() {
+      return this.$this.run$1$1(this.registered, this.R);
+    },
+    $signature: function() {
+      return this.R._eval$1("0()");
+    }
+  };
+  P._CustomZone_bindUnaryCallback_closure.prototype = {
+    call$1: function(arg) {
+      var _this = this,
+        t1 = _this.T;
+      return _this.$this.runUnary$2$2(_this.registered, t1._check(arg), _this.R, t1);
+    },
+    $signature: function() {
+      return this.R._eval$1("@<0>")._bind$1(this.T)._eval$1("1(2)");
+    }
+  };
+  P._CustomZone_bindCallbackGuarded_closure.prototype = {
+    call$0: function() {
+      return this.$this.runGuarded$1(this.registered);
+    },
+    $signature: 1
+  };
+  P._CustomZone_bindUnaryCallbackGuarded_closure.prototype = {
+    call$1: function(arg) {
+      var t1 = this.T;
+      return this.$this.runUnaryGuarded$1$2(this.registered, t1._check(arg), t1);
+    },
+    $signature: function() {
+      return this.T._eval$1("~(0)");
+    }
+  };
+  P._rootHandleUncaughtError_closure.prototype = {
+    call$0: function() {
+      var error,
+        t1 = this._box_0,
+        t2 = t1.error;
+      t1 = t2 == null ? t1.error = new P.NullThrownError() : t2;
+      t2 = this.stackTrace;
+      if (t2 == null)
+        throw H.wrapException(t1);
+      error = H.wrapException(t1);
+      error.stack = t2.toString$0(0);
+      throw error;
+    },
+    $signature: 0
+  };
+  P._RootZone.prototype = {
+    get$_run: function() {
+      return C._ZoneFunction__RootZone__rootRun;
+    },
+    get$_runUnary: function() {
+      return C._ZoneFunction__RootZone__rootRunUnary;
+    },
+    get$_runBinary: function() {
+      return C._ZoneFunction__RootZone__rootRunBinary;
+    },
+    get$_registerCallback: function() {
+      return C._ZoneFunction__RootZone__rootRegisterCallback;
+    },
+    get$_registerUnaryCallback: function() {
+      return C._ZoneFunction_Eeh;
+    },
+    get$_registerBinaryCallback: function() {
+      return C._ZoneFunction_7G2;
+    },
+    get$_errorCallback: function() {
+      return C._ZoneFunction__RootZone__rootErrorCallback;
+    },
+    get$_scheduleMicrotask: function() {
+      return C._ZoneFunction__RootZone__rootScheduleMicrotask;
+    },
+    get$_createTimer: function() {
+      return C._ZoneFunction__RootZone__rootCreateTimer;
+    },
+    get$_createPeriodicTimer: function() {
+      return C._ZoneFunction_3bB;
+    },
+    get$_print: function() {
+      return C._ZoneFunction__RootZone__rootPrint;
+    },
+    get$_fork: function() {
+      return C._ZoneFunction__RootZone__rootFork;
+    },
+    get$_handleUncaughtError: function() {
+      return C._ZoneFunction_NMc;
+    },
+    get$parent: function(_) {
+      return null;
+    },
+    get$_async$_map: function() {
+      return $.$get$_RootZone__rootMap();
+    },
+    get$_delegate: function() {
+      var t1 = $._RootZone__rootDelegate;
+      if (t1 != null)
+        return t1;
+      return $._RootZone__rootDelegate = new P._ZoneDelegate(this);
+    },
+    get$errorZone: function() {
+      return this;
+    },
+    runGuarded$1: function(f) {
+      var e, s, exception, _null = null;
+      type$.void_Function._check(f);
+      try {
+        if (C.C__RootZone === $.Zone__current) {
+          f.call$0();
+          return;
+        }
+        P._rootRun(_null, _null, this, f, type$.void);
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        s = H.getTraceFromException(exception);
+        P._rootHandleUncaughtError(_null, _null, this, e, type$.StackTrace._check(s));
+      }
+    },
+    runUnaryGuarded$1$2: function(f, arg, $T) {
+      var e, s, exception, _null = null;
+      $T._eval$1("~(0)")._check(f);
+      $T._check(arg);
+      try {
+        if (C.C__RootZone === $.Zone__current) {
+          f.call$1(arg);
+          return;
+        }
+        P._rootRunUnary(_null, _null, this, f, arg, type$.void, $T);
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        s = H.getTraceFromException(exception);
+        P._rootHandleUncaughtError(_null, _null, this, e, type$.StackTrace._check(s));
+      }
+    },
+    runBinaryGuarded$2$3: function(f, arg1, arg2, T1, T2) {
+      var e, s, exception, _null = null;
+      T1._eval$1("@<0>")._bind$1(T2)._eval$1("~(1,2)")._check(f);
+      T1._check(arg1);
+      T2._check(arg2);
+      try {
+        if (C.C__RootZone === $.Zone__current) {
+          f.call$2(arg1, arg2);
+          return;
+        }
+        P._rootRunBinary(_null, _null, this, f, arg1, arg2, type$.void, T1, T2);
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        s = H.getTraceFromException(exception);
+        P._rootHandleUncaughtError(_null, _null, this, e, type$.StackTrace._check(s));
+      }
+    },
+    bindCallback$1$1: function(f, $R) {
+      return new P._RootZone_bindCallback_closure(this, $R._eval$1("0()")._check(f), $R);
+    },
+    bindCallbackGuarded$1: function(f) {
+      return new P._RootZone_bindCallbackGuarded_closure(this, type$.void_Function._check(f));
+    },
+    bindUnaryCallbackGuarded$1$1: function(f, $T) {
+      return new P._RootZone_bindUnaryCallbackGuarded_closure(this, $T._eval$1("~(0)")._check(f), $T);
+    },
+    $index: function(_, key) {
+      return null;
+    },
+    handleUncaughtError$2: function(error, stackTrace) {
+      P._rootHandleUncaughtError(null, null, this, error, type$.StackTrace._check(stackTrace));
+    },
+    fork$2$specification$zoneValues: function(specification, zoneValues) {
+      return P._rootFork(null, null, this, specification, zoneValues);
+    },
+    run$1$1: function(f, $R) {
+      $R._eval$1("0()")._check(f);
+      if ($.Zone__current === C.C__RootZone)
+        return f.call$0();
+      return P._rootRun(null, null, this, f, $R);
+    },
+    runUnary$2$2: function(f, arg, $R, $T) {
+      $R._eval$1("@<0>")._bind$1($T)._eval$1("1(2)")._check(f);
+      $T._check(arg);
+      if ($.Zone__current === C.C__RootZone)
+        return f.call$1(arg);
+      return P._rootRunUnary(null, null, this, f, arg, $R, $T);
+    },
+    runBinary$3$3: function(f, arg1, arg2, $R, T1, T2) {
+      $R._eval$1("@<0>")._bind$1(T1)._bind$1(T2)._eval$1("1(2,3)")._check(f);
+      T1._check(arg1);
+      T2._check(arg2);
+      if ($.Zone__current === C.C__RootZone)
+        return f.call$2(arg1, arg2);
+      return P._rootRunBinary(null, null, this, f, arg1, arg2, $R, T1, T2);
+    },
+    registerCallback$1$1: function(f, $R) {
+      return $R._eval$1("0()")._check(f);
+    },
+    registerUnaryCallback$2$1: function(f, $R, $T) {
+      return $R._eval$1("@<0>")._bind$1($T)._eval$1("1(2)")._check(f);
+    },
+    registerBinaryCallback$3$1: function(f, $R, T1, T2) {
+      return $R._eval$1("@<0>")._bind$1(T1)._bind$1(T2)._eval$1("1(2,3)")._check(f);
+    },
+    errorCallback$2: function(error, stackTrace) {
+      type$.StackTrace._check(stackTrace);
+      return null;
+    },
+    scheduleMicrotask$1: function(f) {
+      P._rootScheduleMicrotask(null, null, this, type$.void_Function._check(f));
+    },
+    createTimer$2: function(duration, f) {
+      return P.Timer__createTimer(duration, type$.void_Function._check(f));
+    },
+    print$1: function(_, line) {
+      H.printString(line);
+    }
+  };
+  P._RootZone_bindCallback_closure.prototype = {
+    call$0: function() {
+      return this.$this.run$1$1(this.f, this.R);
+    },
+    $signature: function() {
+      return this.R._eval$1("0()");
+    }
+  };
+  P._RootZone_bindCallbackGuarded_closure.prototype = {
+    call$0: function() {
+      return this.$this.runGuarded$1(this.f);
+    },
+    $signature: 1
+  };
+  P._RootZone_bindUnaryCallbackGuarded_closure.prototype = {
+    call$1: function(arg) {
+      var t1 = this.T;
+      return this.$this.runUnaryGuarded$1$2(this.f, t1._check(arg), t1);
+    },
+    $signature: function() {
+      return this.T._eval$1("~(0)");
+    }
+  };
+  P.runZoned_closure.prototype = {
+    call$5: function($self, $parent, zone, error, stackTrace) {
+      var e, s, t2, t3, t4, exception,
+        t1 = type$.StackTrace;
+      t1._check(stackTrace);
+      try {
+        t2 = this._box_0;
+        t3 = type$.void;
+        t4 = type$.Object;
+        if (t2.binaryOnError != null)
+          $self.get$parent($self).runBinary$3$3(t2.binaryOnError, error, stackTrace, t3, t4, t1);
+        else {
+          H.assertHelper(t2.unaryOnError != null);
+          $self.get$parent($self).runUnary$2$2(t2.unaryOnError, error, t3, t4);
+        }
+      } catch (exception) {
+        e = H.unwrapException(exception);
+        s = H.getTraceFromException(exception);
+        t1 = e;
+        if (t1 == null ? error == null : t1 === error)
+          $parent.handleUncaughtError$3(zone, error, stackTrace);
+        else
+          $parent.handleUncaughtError$3(zone, e, s);
+      }
+    },
+    $signature: 28
+  };
+  P._HashMap.prototype = {
+    get$length: function(_) {
+      return this._collection$_length;
+    },
+    get$isEmpty: function(_) {
+      return this._collection$_length === 0;
+    },
+    get$keys: function() {
+      return new P._HashMapKeyIterable(this, H._instanceType(this)._eval$1("_HashMapKeyIterable<1>"));
+    },
+    containsKey$1: function(key) {
+      var strings, nums;
+      if (typeof key == "string" && key !== "__proto__") {
+        strings = this._strings;
+        return strings == null ? false : strings[key] != null;
+      } else if (typeof key == "number" && (key & 1073741823) === key) {
+        nums = this._nums;
+        return nums == null ? false : nums[key] != null;
+      } else
+        return this._containsKey$1(key);
+    },
+    _containsKey$1: function(key) {
+      var rest = this._collection$_rest;
+      if (rest == null)
+        return false;
+      return this._findBucketIndex$2(this._getBucket$2(rest, key), key) >= 0;
+    },
+    $index: function(_, key) {
+      var strings, t1, nums;
+      if (typeof key == "string" && key !== "__proto__") {
+        strings = this._strings;
+        t1 = strings == null ? null : P._HashMap__getTableEntry(strings, key);
+        return t1;
+      } else if (typeof key == "number" && (key & 1073741823) === key) {
+        nums = this._nums;
+        t1 = nums == null ? null : P._HashMap__getTableEntry(nums, key);
+        return t1;
+      } else
+        return this._get$1(key);
+    },
+    _get$1: function(key) {
+      var bucket, index,
+        rest = this._collection$_rest;
+      if (rest == null)
+        return null;
+      bucket = this._getBucket$2(rest, key);
+      index = this._findBucketIndex$2(bucket, key);
+      return index < 0 ? null : bucket[index + 1];
+    },
+    $indexSet: function(_, key, value) {
+      var strings, nums, _this = this,
+        t1 = H._instanceType(_this);
+      t1._precomputed1._check(key);
+      t1._rest[1]._check(value);
+      if (typeof key == "string" && key !== "__proto__") {
+        strings = _this._strings;
+        _this._addHashTableEntry$3(strings == null ? _this._strings = P._HashMap__newHashTable() : strings, key, value);
+      } else if (typeof key == "number" && (key & 1073741823) === key) {
+        nums = _this._nums;
+        _this._addHashTableEntry$3(nums == null ? _this._nums = P._HashMap__newHashTable() : nums, key, value);
+      } else
+        _this._set$2(key, value);
+    },
+    _set$2: function(key, value) {
+      var rest, hash, bucket, index, _this = this,
+        t1 = H._instanceType(_this);
+      t1._precomputed1._check(key);
+      t1._rest[1]._check(value);
+      rest = _this._collection$_rest;
+      if (rest == null)
+        rest = _this._collection$_rest = P._HashMap__newHashTable();
+      hash = _this._computeHashCode$1(key);
+      bucket = rest[hash];
+      if (bucket == null) {
+        P._HashMap__setTableEntry(rest, hash, [key, value]);
+        ++_this._collection$_length;
+        _this._keys = null;
+      } else {
+        index = _this._findBucketIndex$2(bucket, key);
+        if (index >= 0)
+          bucket[index + 1] = value;
+        else {
+          bucket.push(key, value);
+          ++_this._collection$_length;
+          _this._keys = null;
+        }
+      }
+    },
+    remove$1: function(_, key) {
+      var t1 = this._remove$1(key);
+      return t1;
+    },
+    _remove$1: function(key) {
+      var hash, bucket, index, result, _this = this,
+        rest = _this._collection$_rest;
+      if (rest == null)
+        return null;
+      hash = _this._computeHashCode$1(key);
+      bucket = rest[hash];
+      index = _this._findBucketIndex$2(bucket, key);
+      if (index < 0)
+        return null;
+      --_this._collection$_length;
+      _this._keys = null;
+      result = bucket.splice(index, 2)[1];
+      if (0 === bucket.length)
+        delete rest[hash];
+      return result;
+    },
+    forEach$1: function(_, action) {
+      var keys, $length, i, key, _this = this,
+        t1 = H._instanceType(_this);
+      t1._eval$1("~(1,2)")._check(action);
+      keys = _this._computeKeys$0();
+      for ($length = keys.length, t1 = t1._precomputed1, i = 0; i < $length; ++i) {
+        key = keys[i];
+        action.call$2(t1._check(key), _this.$index(0, key));
+        if (keys !== _this._keys)
+          throw H.wrapException(P.ConcurrentModificationError$(_this));
+      }
+    },
+    _computeKeys$0: function() {
+      var result, strings, names, entries, index, i, nums, rest, bucket, $length, i0, _this = this,
+        t1 = _this._keys;
+      if (t1 != null)
+        return t1;
+      result = new Array(_this._collection$_length);
+      result.fixed$length = Array;
+      strings = _this._strings;
+      if (strings != null) {
+        names = Object.getOwnPropertyNames(strings);
+        entries = names.length;
+        for (index = 0, i = 0; i < entries; ++i) {
+          result[index] = names[i];
+          ++index;
+        }
+      } else
+        index = 0;
+      nums = _this._nums;
+      if (nums != null) {
+        names = Object.getOwnPropertyNames(nums);
+        entries = names.length;
+        for (i = 0; i < entries; ++i) {
+          result[index] = +names[i];
+          ++index;
+        }
+      }
+      rest = _this._collection$_rest;
+      if (rest != null) {
+        names = Object.getOwnPropertyNames(rest);
+        entries = names.length;
+        for (i = 0; i < entries; ++i) {
+          bucket = rest[names[i]];
+          $length = bucket.length;
+          for (i0 = 0; i0 < $length; i0 += 2) {
+            result[index] = bucket[i0];
+            ++index;
+          }
+        }
+      }
+      H.assertHelper(index === _this._collection$_length);
+      return _this._keys = result;
+    },
+    _addHashTableEntry$3: function(table, key, value) {
+      var t1 = H._instanceType(this);
+      t1._precomputed1._check(key);
+      t1._rest[1]._check(value);
+      if (table[key] == null) {
+        ++this._collection$_length;
+        this._keys = null;
+      }
+      P._HashMap__setTableEntry(table, key, value);
+    },
+    _computeHashCode$1: function(key) {
+      return J.get$hashCode$(key) & 1073741823;
+    },
+    _getBucket$2: function(table, key) {
+      return table[this._computeHashCode$1(key)];
+    },
+    _findBucketIndex$2: function(bucket, key) {
+      var $length, i;
+      if (bucket == null)
+        return -1;
+      $length = bucket.length;
+      for (i = 0; i < $length; i += 2)
+        if (J.$eq$(bucket[i], key))
+          return i;
+      return -1;
+    }
+  };
+  P._IdentityHashMap.prototype = {
+    _computeHashCode$1: function(key) {
+      return H.objectHashCode(key) & 1073741823;
+    },
+    _findBucketIndex$2: function(bucket, key) {
+      var $length, i, t1;
+      if (bucket == null)
+        return -1;
+      $length = bucket.length;
+      for (i = 0; i < $length; i += 2) {
+        t1 = bucket[i];
+        if (t1 == null ? key == null : t1 === key)
+          return i;
+      }
+      return -1;
+    }
+  };
+  P._HashMapKeyIterable.prototype = {
+    get$length: function(_) {
+      return this._map._collection$_length;
+    },
+    get$isEmpty: function(_) {
+      return this._map._collection$_length === 0;
+    },
+    get$iterator: function(_) {
+      var t1 = this._map;
+      return new P._HashMapKeyIterator(t1, t1._computeKeys$0(), this.$ti._eval$1("_HashMapKeyIterator<1>"));
+    },
+    contains$1: function(_, element) {
+      return this._map.containsKey$1(element);
+    }
+  };
+  P._HashMapKeyIterator.prototype = {
+    get$current: function() {
+      return this._collection$_current;
+    },
+    moveNext$0: function() {
+      var _this = this,
+        keys = _this._keys,
+        offset = _this._offset,
+        t1 = _this._map;
+      if (keys !== t1._keys)
+        throw H.wrapException(P.ConcurrentModificationError$(t1));
+      else if (offset >= keys.length) {
+        _this.set$_collection$_current(null);
+        return false;
+      } else {
+        _this.set$_collection$_current(keys[offset]);
+        _this._offset = offset + 1;
+        return true;
+      }
+    },
+    set$_collection$_current: function(_current) {
+      this._collection$_current = this.$ti._precomputed1._check(_current);
+    },
+    $isIterator: 1
+  };
+  P._LinkedHashSet.prototype = {
+    _newSet$0: function() {
+      return new P._LinkedHashSet(H._instanceType(this)._eval$1("_LinkedHashSet<1>"));
+    },
+    get$iterator: function(_) {
+      var _this = this,
+        t1 = new P._LinkedHashSetIterator(_this, _this._collection$_modifications, H._instanceType(_this)._eval$1("_LinkedHashSetIterator<1>"));
+      t1._collection$_cell = _this._collection$_first;
+      return t1;
+    },
+    get$length: function(_) {
+      return this._collection$_length;
+    },
+    get$isEmpty: function(_) {
+      return this._collection$_length === 0;
+    },
+    contains$1: function(_, object) {
+      var strings, nums;
+      if (typeof object == "string" && object !== "__proto__") {
+        strings = this._strings;
+        if (strings == null)
+          return false;
+        return type$._LinkedHashSetCell._check(strings[object]) != null;
+      } else if (typeof object == "number" && (object & 1073741823) === object) {
+        nums = this._nums;
+        if (nums == null)
+          return false;
+        return type$._LinkedHashSetCell._check(nums[object]) != null;
+      } else
+        return this._contains$1(object);
+    },
+    _contains$1: function(object) {
+      var rest = this._collection$_rest;
+      if (rest == null)
+        return false;
+      return this._findBucketIndex$2(rest[this._computeHashCode$1(object)], object) >= 0;
+    },
+    get$first: function(_) {
+      var t1 = this._collection$_first;
+      if (t1 == null)
+        throw H.wrapException(P.StateError$("No elements"));
+      return H._instanceType(this)._precomputed1._check(t1._element);
+    },
+    get$last: function(_) {
+      var t1 = this._collection$_last;
+      if (t1 == null)
+        throw H.wrapException(P.StateError$("No elements"));
+      return H._instanceType(this)._precomputed1._check(t1._element);
+    },
+    add$1: function(_, element) {
+      var strings, nums, _this = this;
+      H._instanceType(_this)._precomputed1._check(element);
+      if (typeof element == "string" && element !== "__proto__") {
+        strings = _this._strings;
+        return _this._addHashTableEntry$2(strings == null ? _this._strings = P._LinkedHashSet__newHashTable() : strings, element);
+      } else if (typeof element == "number" && (element & 1073741823) === element) {
+        nums = _this._nums;
+        return _this._addHashTableEntry$2(nums == null ? _this._nums = P._LinkedHashSet__newHashTable() : nums, element);
+      } else
+        return _this._collection$_add$1(element);
+    },
+    _collection$_add$1: function(element) {
+      var rest, hash, bucket, t1, _this = this;
+      H._instanceType(_this)._precomputed1._check(element);
+      rest = _this._collection$_rest;
+      if (rest == null)
+        rest = _this._collection$_rest = P._LinkedHashSet__newHashTable();
+      hash = _this._computeHashCode$1(element);
+      bucket = rest[hash];
+      if (bucket == null) {
+        t1 = [_this._collection$_newLinkedCell$1(element)];
+        H.assertHelper(t1 != null);
+        rest[hash] = t1;
+      } else {
+        if (_this._findBucketIndex$2(bucket, element) >= 0)
+          return false;
+        bucket.push(_this._collection$_newLinkedCell$1(element));
+      }
+      return true;
+    },
+    remove$1: function(_, object) {
+      var _this = this;
+      if (typeof object == "string" && object !== "__proto__")
+        return _this._removeHashTableEntry$2(_this._strings, object);
+      else if (typeof object == "number" && (object & 1073741823) === object)
+        return _this._removeHashTableEntry$2(_this._nums, object);
+      else
+        return _this._remove$1(object);
+    },
+    _remove$1: function(object) {
+      var hash, bucket, index, cell, _this = this,
+        rest = _this._collection$_rest;
+      if (rest == null)
+        return false;
+      hash = _this._computeHashCode$1(object);
+      bucket = rest[hash];
+      index = _this._findBucketIndex$2(bucket, object);
+      if (index < 0)
+        return false;
+      cell = bucket.splice(index, 1)[0];
+      if (0 === bucket.length)
+        delete rest[hash];
+      _this._unlinkCell$1(cell);
+      return true;
+    },
+    _addHashTableEntry$2: function(table, element) {
+      H._instanceType(this)._precomputed1._check(element);
+      if (type$._LinkedHashSetCell._check(table[element]) != null)
+        return false;
+      table[element] = this._collection$_newLinkedCell$1(element);
+      return true;
+    },
+    _removeHashTableEntry$2: function(table, element) {
+      var cell;
+      if (table == null)
+        return false;
+      cell = type$._LinkedHashSetCell._check(table[element]);
+      if (cell == null)
+        return false;
+      this._unlinkCell$1(cell);
+      delete table[element];
+      return true;
+    },
+    _collection$_modified$0: function() {
+      this._collection$_modifications = 1073741823 & this._collection$_modifications + 1;
+    },
+    _collection$_newLinkedCell$1: function(element) {
+      var last, _this = this,
+        cell = new P._LinkedHashSetCell(H._instanceType(_this)._precomputed1._check(element));
+      if (_this._collection$_first == null)
+        _this._collection$_first = _this._collection$_last = cell;
+      else {
+        last = _this._collection$_last;
+        cell._collection$_previous = last;
+        _this._collection$_last = last._collection$_next = cell;
+      }
+      ++_this._collection$_length;
+      _this._collection$_modified$0();
+      return cell;
+    },
+    _unlinkCell$1: function(cell) {
+      var _this = this,
+        previous = cell._collection$_previous,
+        next = cell._collection$_next;
+      if (previous == null) {
+        H.assertHelper(cell == _this._collection$_first);
+        _this._collection$_first = next;
+      } else
+        previous._collection$_next = next;
+      if (next == null) {
+        H.assertHelper(cell == _this._collection$_last);
+        _this._collection$_last = previous;
+      } else
+        next._collection$_previous = previous;
+      --_this._collection$_length;
+      _this._collection$_modified$0();
+    },
+    _computeHashCode$1: function(element) {
+      return J.get$hashCode$(element) & 1073741823;
+    },
+    _findBucketIndex$2: function(bucket, element) {
+      var $length, i;
+      if (bucket == null)
+        return -1;
+      $length = bucket.length;
+      for (i = 0; i < $length; ++i)
+        if (J.$eq$(bucket[i]._element, element))
+          return i;
+      return -1;
+    },
+    $isLinkedHashSet: 1
+  };
+  P._LinkedHashSetCell.prototype = {};
+  P._LinkedHashSetIterator.prototype = {
+    get$current: function() {
+      return this._collection$_current;
+    },
+    moveNext$0: function() {
+      var _this = this,
+        t1 = _this._set;
+      if (_this._collection$_modifications !== t1._collection$_modifications)
+        throw H.wrapException(P.ConcurrentModificationError$(t1));
+      else {
+        t1 = _this._collection$_cell;
+        if (t1 == null) {
+          _this.set$_collection$_current(null);
+          return false;
+        } else {
+          _this.set$_collection$_current(_this.$ti._precomputed1._check(t1._element));
+          _this._collection$_cell = _this._collection$_cell._collection$_next;
+          return true;
+        }
+      }
+    },
+    set$_collection$_current: function(_current) {
+      this._collection$_current = this.$ti._precomputed1._check(_current);
+    },
+    $isIterator: 1
+  };
+  P.UnmodifiableListView.prototype = {
+    get$length: function(_) {
+      var t1 = this._collection$_source;
+      return t1.get$length(t1);
+    },
+    $index: function(_, index) {
+      return this._collection$_source.$index(0, H._checkIntNullable(index));
+    }
+  };
+  P.HashMap_HashMap$from_closure.prototype = {
+    call$2: function(k, v) {
+      this.result.$indexSet(0, this.K._check(k), this.V._check(v));
+    },
+    $signature: 6
+  };
+  P.IterableBase.prototype = {};
+  P.LinkedHashMap_LinkedHashMap$from_closure.prototype = {
+    call$2: function(k, v) {
+      this.result.$indexSet(0, this.K._check(k), this.V._check(v));
+    },
+    $signature: 6
+  };
+  P.ListBase.prototype = {$isEfficientLengthIterable: 1, $isIterable: 1, $isList: 1};
+  P.ListMixin.prototype = {
+    get$iterator: function(receiver) {
+      return new H.ListIterator(receiver, this.get$length(receiver), H.instanceType(receiver)._eval$1("ListIterator<ListMixin.E>"));
+    },
+    elementAt$1: function(receiver, index) {
+      return this.$index(receiver, index);
+    },
+    get$isEmpty: function(receiver) {
+      return this.get$length(receiver) === 0;
+    },
+    get$first: function(receiver) {
+      if (this.get$length(receiver) === 0)
+        throw H.wrapException(H.IterableElementError_noElement());
+      return this.$index(receiver, 0);
+    },
+    get$last: function(receiver) {
+      if (this.get$length(receiver) === 0)
+        throw H.wrapException(H.IterableElementError_noElement());
+      return this.$index(receiver, this.get$length(receiver) - 1);
+    },
+    map$1$1: function(receiver, f, $T) {
+      var t1 = H.instanceType(receiver);
+      return new H.MappedListIterable(receiver, t1._bind$1($T)._eval$1("1(ListMixin.E)")._check(f), t1._eval$1("@<ListMixin.E>")._bind$1($T)._eval$1("MappedListIterable<1,2>"));
+    },
+    toList$1$growable: function(receiver, growable) {
+      var i,
+        result = H.setRuntimeTypeInfo([], H.instanceType(receiver)._eval$1("JSArray<ListMixin.E>"));
+      C.JSArray_methods.set$length(result, this.get$length(receiver));
+      for (i = 0; i < this.get$length(receiver); ++i)
+        C.JSArray_methods.$indexSet(result, i, this.$index(receiver, i));
+      return result;
+    },
+    toList$0: function($receiver) {
+      return this.toList$1$growable($receiver, true);
+    },
+    toSet$0: function(receiver) {
+      var i,
+        result = P.LinkedHashSet_LinkedHashSet(H.instanceType(receiver)._eval$1("ListMixin.E"));
+      for (i = 0; i < this.get$length(receiver); ++i)
+        result.add$1(0, this.$index(receiver, i));
+      return result;
+    },
+    remove$1: function(receiver, element) {
+      var i;
+      for (i = 0; i < this.get$length(receiver); ++i)
+        if (J.$eq$(this.$index(receiver, i), element)) {
+          this._closeGap$2(receiver, i, i + 1);
+          return true;
+        }
+      return false;
+    },
+    _closeGap$2: function(receiver, start, end) {
+      var size, i, _this = this,
+        $length = _this.get$length(receiver);
+      H.assertHelper(start < end);
+      H.assertHelper(end <= $length);
+      size = end - start;
+      for (i = end; i < $length; ++i)
+        _this.$indexSet(receiver, i - size, _this.$index(receiver, i));
+      _this.set$length(receiver, $length - size);
+    },
+    fillRange$3: function(receiver, start, end, fill) {
+      var i;
+      H.instanceType(receiver)._eval$1("ListMixin.E")._check(fill);
+      P.RangeError_checkValidRange(start, end, this.get$length(receiver));
+      for (i = start; i < end; ++i)
+        this.$indexSet(receiver, i, fill);
+    },
+    toString$0: function(receiver) {
+      return P.IterableBase_iterableToFullString(receiver, "[", "]");
+    }
+  };
+  P.MapBase.prototype = {};
+  P.MapBase_mapToString_closure.prototype = {
+    call$2: function(k, v) {
+      var t2,
+        t1 = this._box_0;
+      if (!t1.first)
+        this.result._contents += ", ";
+      t1.first = false;
+      t1 = this.result;
+      t2 = t1._contents += H.S(k);
+      t1._contents = t2 + ": ";
+      t1._contents += H.S(v);
+    },
+    $signature: 6
+  };
+  P.MapMixin.prototype = {
+    cast$2$0: function(_, RK, RV) {
+      var t1 = H._instanceType(this);
+      return P.Map_castFrom(this, t1._eval$1("MapMixin.K"), t1._eval$1("MapMixin.V"), RK, RV);
+    },
+    forEach$1: function(_, action) {
+      var t1, key;
+      H._instanceType(this)._eval$1("~(MapMixin.K,MapMixin.V)")._check(action);
+      for (t1 = this.get$keys(), t1 = t1.get$iterator(t1); t1.moveNext$0();) {
+        key = t1.get$current();
+        action.call$2(key, this.$index(0, key));
+      }
+    },
+    map$2$1: function(_, transform, K2, V2) {
+      var result, t1, key, entry;
+      H._instanceType(this)._bind$1(K2)._bind$1(V2)._eval$1("MapEntry<1,2>(MapMixin.K,MapMixin.V)")._check(transform);
+      result = P.LinkedHashMap_LinkedHashMap$_empty(K2, V2);
+      for (t1 = this.get$keys(), t1 = t1.get$iterator(t1); t1.moveNext$0();) {
+        key = t1.get$current();
+        entry = transform.call$2(key, this.$index(0, key));
+        result.$indexSet(0, entry.key, entry.value);
+      }
+      return result;
+    },
+    containsKey$1: function(key) {
+      return this.get$keys().contains$1(0, key);
+    },
+    get$length: function(_) {
+      var t1 = this.get$keys();
+      return t1.get$length(t1);
+    },
+    get$isEmpty: function(_) {
+      var t1 = this.get$keys();
+      return t1.get$isEmpty(t1);
+    },
+    toString$0: function(_) {
+      return P.MapBase_mapToString(this);
+    },
+    $isMap: 1
+  };
+  P._UnmodifiableMapMixin.prototype = {
+    remove$1: function(_, key) {
+      throw H.wrapException(P.UnsupportedError$("Cannot modify unmodifiable map"));
+    }
+  };
+  P.MapView.prototype = {
+    cast$2$0: function(_, RK, RV) {
+      return this._map.cast$2$0(0, RK, RV);
+    },
+    $index: function(_, key) {
+      return this._map.$index(0, key);
+    },
+    containsKey$1: function(key) {
+      return this._map.containsKey$1(key);
+    },
+    forEach$1: function(_, action) {
+      this._map.forEach$1(0, H._instanceType(this)._eval$1("~(1,2)")._check(action));
+    },
+    get$isEmpty: function(_) {
+      var t1 = this._map;
+      return t1.get$isEmpty(t1);
+    },
+    get$length: function(_) {
+      var t1 = this._map;
+      return t1.get$length(t1);
+    },
+    get$keys: function() {
+      return this._map.get$keys();
+    },
+    remove$1: function(_, key) {
+      return this._map.remove$1(0, key);
+    },
+    toString$0: function(_) {
+      return this._map.toString$0(0);
+    },
+    map$2$1: function(_, transform, K2, V2) {
+      return this._map.map$2$1(0, H._instanceType(this)._bind$1(K2)._bind$1(V2)._eval$1("MapEntry<1,2>(3,4)")._check(transform), K2, V2);
+    },
+    $isMap: 1
+  };
+  P.UnmodifiableMapView.prototype = {
+    cast$2$0: function(_, RK, RV) {
+      return new P.UnmodifiableMapView(this._map.cast$2$0(0, RK, RV), RK._eval$1("@<0>")._bind$1(RV)._eval$1("UnmodifiableMapView<1,2>"));
+    }
+  };
+  P.ListQueue.prototype = {
+    get$iterator: function(_) {
+      var _this = this;
+      return new P._ListQueueIterator(_this, _this._tail, _this._modificationCount, _this._head, _this.$ti._eval$1("_ListQueueIterator<1>"));
+    },
+    get$isEmpty: function(_) {
+      return this._head === this._tail;
+    },
+    get$length: function(_) {
+      return (this._tail - this._head & this._table.length - 1) >>> 0;
+    },
+    get$first: function(_) {
+      var t2,
+        t1 = this._head;
+      if (t1 === this._tail)
+        throw H.wrapException(H.IterableElementError_noElement());
+      t2 = this._table;
+      if (t1 >= t2.length)
+        return H.ioore(t2, t1);
+      return t2[t1];
+    },
+    get$last: function(_) {
+      var t3,
+        t1 = this._head,
+        t2 = this._tail;
+      if (t1 === t2)
+        throw H.wrapException(H.IterableElementError_noElement());
+      t1 = this._table;
+      t3 = t1.length;
+      t2 = (t2 - 1 & t3 - 1) >>> 0;
+      if (t2 < 0 || t2 >= t3)
+        return H.ioore(t1, t2);
+      return t1[t2];
+    },
+    elementAt$1: function(_, index) {
+      var t1, t2, t3, _this = this,
+        $length = _this.get$length(_this);
+      if (0 > index || index >= $length)
+        H.throwExpression(P.IndexError$(index, _this, "index", null, $length));
+      t1 = _this._table;
+      t2 = t1.length;
+      t3 = (_this._head + index & t2 - 1) >>> 0;
+      if (t3 < 0 || t3 >= t2)
+        return H.ioore(t1, t3);
+      return t1[t3];
+    },
+    clear$0: function(_) {
+      var _this = this,
+        i = _this._head;
+      if (i !== _this._tail) {
+        for (; i !== _this._tail; i = (i + 1 & _this._table.length - 1) >>> 0)
+          C.JSArray_methods.$indexSet(_this._table, i, null);
+        _this._head = _this._tail = 0;
+        ++_this._modificationCount;
+      }
+    },
+    toString$0: function(_) {
+      return P.IterableBase_iterableToFullString(this, "{", "}");
+    },
+    removeFirst$0: function() {
+      var t2, result, _this = this,
+        t1 = _this._head;
+      if (t1 === _this._tail)
+        throw H.wrapException(H.IterableElementError_noElement());
+      ++_this._modificationCount;
+      t2 = _this._table;
+      if (t1 >= t2.length)
+        return H.ioore(t2, t1);
+      result = t2[t1];
+      C.JSArray_methods.$indexSet(t2, t1, null);
+      _this._head = (_this._head + 1 & _this._table.length - 1) >>> 0;
+      return result;
+    },
+    _collection$_add$1: function(element) {
+      var t2, t3, newTable, split, _this = this,
+        t1 = _this.$ti;
+      t1._precomputed1._check(element);
+      C.JSArray_methods.$indexSet(_this._table, _this._tail, element);
+      t2 = _this._tail;
+      t3 = _this._table.length;
+      t2 = (t2 + 1 & t3 - 1) >>> 0;
+      _this._tail = t2;
+      if (_this._head === t2) {
+        t2 = new Array(t3 * 2);
+        t2.fixed$length = Array;
+        newTable = H.setRuntimeTypeInfo(t2, t1._eval$1("JSArray<1>"));
+        t1 = _this._table;
+        t2 = _this._head;
+        split = t1.length - t2;
+        C.JSArray_methods.setRange$4(newTable, 0, split, t1, t2);
+        C.JSArray_methods.setRange$4(newTable, split, split + _this._head, _this._table, 0);
+        _this._head = 0;
+        _this._tail = _this._table.length;
+        _this.set$_table(newTable);
+      }
+      ++_this._modificationCount;
+    },
+    set$_table: function(_table) {
+      this._table = this.$ti._eval$1("List<1>")._check(_table);
+    },
+    $isQueue: 1
+  };
+  P._ListQueueIterator.prototype = {
+    get$current: function() {
+      return this._collection$_current;
+    },
+    moveNext$0: function() {
+      var t2, t3, _this = this,
+        t1 = _this._queue;
+      if (_this._modificationCount !== t1._modificationCount)
+        H.throwExpression(P.ConcurrentModificationError$(t1));
+      t2 = _this._position;
+      if (t2 === _this._end) {
+        _this.set$_collection$_current(null);
+        return false;
+      }
+      t3 = t1._table;
+      if (t2 >= t3.length)
+        return H.ioore(t3, t2);
+      _this.set$_collection$_current(t3[t2]);
+      _this._position = (_this._position + 1 & t1._table.length - 1) >>> 0;
+      return true;
+    },
+    set$_collection$_current: function(_current) {
+      this._collection$_current = this.$ti._precomputed1._check(_current);
+    },
+    $isIterator: 1
+  };
+  P.SetMixin.prototype = {
+    get$isEmpty: function(_) {
+      return this.get$length(this) === 0;
+    },
+    map$1$1: function(_, f, $T) {
+      var t1 = H._instanceType(this);
+      return new H.EfficientLengthMappedIterable(this, t1._bind$1($T)._eval$1("1(2)")._check(f), t1._eval$1("@<1>")._bind$1($T)._eval$1("EfficientLengthMappedIterable<1,2>"));
+    },
+    toString$0: function(_) {
+      return P.IterableBase_iterableToFullString(this, "{", "}");
+    },
+    every$1: function(_, f) {
+      var t1;
+      H._instanceType(this)._eval$1("bool(1)")._check(f);
+      for (t1 = this.get$iterator(this); t1.moveNext$0();)
+        if (!H.boolConversionCheck(f.call$1(t1.get$current())))
+          return false;
+      return true;
+    },
+    get$first: function(_) {
+      var it = this.get$iterator(this);
+      if (!it.moveNext$0())
+        throw H.wrapException(H.IterableElementError_noElement());
+      return it.get$current();
+    },
+    get$last: function(_) {
+      var result,
+        it = this.get$iterator(this);
+      if (!it.moveNext$0())
+        throw H.wrapException(H.IterableElementError_noElement());
+      do
+        result = it.get$current();
+      while (it.moveNext$0());
+      return result;
+    },
+    $isEfficientLengthIterable: 1,
+    $isIterable: 1,
+    $isSet: 1
+  };
+  P.SetBase.prototype = {$isEfficientLengthIterable: 1, $isIterable: 1, $isSet: 1};
+  P._SetBase.prototype = {
+    toSet$0: function(_) {
+      var t1 = this._newSet$0();
+      t1.addAll$1(0, this);
+      return t1;
+    },
+    get$isEmpty: function(_) {
+      return this._collection$_length === 0;
+    },
+    addAll$1: function(_, elements) {
+      var t1;
+      H._instanceType(this)._eval$1("Iterable<1>")._check(elements);
+      for (t1 = elements.get$iterator(elements); t1.moveNext$0();)
+        this.add$1(0, t1.get$current());
+    },
+    union$1: function(other) {
+      var t1;
+      H._instanceType(this)._eval$1("Set<1>")._check(other);
+      t1 = this.toSet$0(0);
+      t1.addAll$1(0, other);
+      return t1;
+    },
+    toList$1$growable: function(_, growable) {
+      var i, i0, _this = this,
+        t1 = H._instanceType(_this),
+        result = H.setRuntimeTypeInfo([], t1._eval$1("JSArray<1>"));
+      C.JSArray_methods.set$length(result, _this._collection$_length);
+      for (t1 = P._LinkedHashSetIterator$(_this, _this._collection$_modifications, t1._precomputed1), i = 0; t1.moveNext$0(); i = i0) {
+        i0 = i + 1;
+        C.JSArray_methods.$indexSet(result, i, t1._collection$_current);
+      }
+      return result;
+    },
+    toList$0: function($receiver) {
+      return this.toList$1$growable($receiver, true);
+    },
+    map$1$1: function(_, f, $T) {
+      var t1 = H._instanceType(this);
+      return new H.EfficientLengthMappedIterable(this, t1._bind$1($T)._eval$1("1(2)")._check(f), t1._eval$1("@<1>")._bind$1($T)._eval$1("EfficientLengthMappedIterable<1,2>"));
+    },
+    toString$0: function(_) {
+      return P.IterableBase_iterableToFullString(this, "{", "}");
+    },
+    where$1: function(_, f) {
+      var t1 = H._instanceType(this);
+      return new H.WhereIterable(this, t1._eval$1("bool(1)")._check(f), t1._eval$1("WhereIterable<1>"));
+    },
+    fold$1$2: function(_, initialValue, combine, $T) {
+      var t1, value;
+      $T._check(initialValue);
+      t1 = H._instanceType(this);
+      t1._bind$1($T)._eval$1("1(1,2)")._check(combine);
+      for (t1 = P._LinkedHashSetIterator$(this, this._collection$_modifications, t1._precomputed1), value = initialValue; t1.moveNext$0();)
+        value = combine.call$2(value, t1._collection$_current);
+      return value;
+    },
+    every$1: function(_, f) {
+      var t1 = H._instanceType(this);
+      t1._eval$1("bool(1)")._check(f);
+      for (t1 = P._LinkedHashSetIterator$(this, this._collection$_modifications, t1._precomputed1); t1.moveNext$0();)
+        if (!H.boolConversionCheck(f.call$1(t1._collection$_current)))
+          return false;
+      return true;
+    },
+    any$1: function(_, test) {
+      var t1 = H._instanceType(this);
+      t1._eval$1("bool(1)")._check(test);
+      for (t1 = P._LinkedHashSetIterator$(this, this._collection$_modifications, t1._precomputed1); t1.moveNext$0();)
+        if (H.boolConversionCheck(test.call$1(t1._collection$_current)))
+          return true;
+      return false;
+    },
+    get$first: function(_) {
+      var it = P._LinkedHashSetIterator$(this, this._collection$_modifications, H._instanceType(this)._precomputed1);
+      if (!it.moveNext$0())
+        throw H.wrapException(H.IterableElementError_noElement());
+      return it._collection$_current;
+    },
+    get$last: function(_) {
+      var result,
+        it = P._LinkedHashSetIterator$(this, this._collection$_modifications, H._instanceType(this)._precomputed1);
+      if (!it.moveNext$0())
+        throw H.wrapException(H.IterableElementError_noElement());
+      do
+        result = it._collection$_current;
+      while (it.moveNext$0());
+      return result;
+    },
+    $isEfficientLengthIterable: 1,
+    $isIterable: 1,
+    $isSet: 1
+  };
+  P._ListBase_Object_ListMixin.prototype = {};
+  P._SetBase_Object_SetMixin.prototype = {};
+  P._UnmodifiableMapView_MapView__UnmodifiableMapMixin.prototype = {};
+  P._JsonMap.prototype = {
+    $index: function(_, key) {
+      var result,
+        t1 = this._processed;
+      if (t1 == null)
+        return this.get$_upgradedMap().$index(0, key);
+      else if (typeof key != "string")
+        return null;
+      else {
+        result = t1[key];
+        return typeof result == "undefined" ? this._process$1(key) : result;
+      }
+    },
+    get$length: function(_) {
+      var t1;
+      if (this._processed == null) {
+        t1 = this.get$_upgradedMap();
+        t1 = t1.get$length(t1);
+      } else
+        t1 = this._convert$_computeKeys$0().length;
+      return t1;
+    },
+    get$isEmpty: function(_) {
+      return this.get$length(this) === 0;
+    },
+    get$keys: function() {
+      if (this._processed == null)
+        return this.get$_upgradedMap().get$keys();
+      return new P._JsonMapKeyIterable(this);
+    },
+    containsKey$1: function(key) {
+      if (this._processed == null)
+        return this.get$_upgradedMap().containsKey$1(key);
+      if (typeof key != "string")
+        return false;
+      return Object.prototype.hasOwnProperty.call(this._original, key);
+    },
+    remove$1: function(_, key) {
+      if (this._processed != null && !this.containsKey$1(key))
+        return null;
+      return this._upgrade$0().remove$1(0, key);
+    },
+    forEach$1: function(_, f) {
+      var keys, i, key, value, _this = this;
+      type$.void_Function_String_dynamic._check(f);
+      if (_this._processed == null)
+        return _this.get$_upgradedMap().forEach$1(0, f);
+      keys = _this._convert$_computeKeys$0();
+      for (i = 0; i < keys.length; ++i) {
+        key = keys[i];
+        value = _this._processed[key];
+        if (typeof value == "undefined") {
+          value = P._convertJsonToDartLazy(_this._original[key]);
+          _this._processed[key] = value;
+        }
+        f.call$2(key, value);
+        if (keys !== _this._data)
+          throw H.wrapException(P.ConcurrentModificationError$(_this));
+      }
+    },
+    get$_upgradedMap: function() {
+      H.assertHelper(this._processed == null);
+      return this._data;
+    },
+    _convert$_computeKeys$0: function() {
+      var keys, _this = this;
+      H.assertHelper(_this._processed != null);
+      keys = type$.List_dynamic._check(_this._data);
+      if (keys == null)
+        keys = _this._data = H.setRuntimeTypeInfo(Object.keys(_this._original), type$.JSArray_String);
+      return keys;
+    },
+    _upgrade$0: function() {
+      var result, keys, i, t1, key, _this = this;
+      if (_this._processed == null)
+        return _this.get$_upgradedMap();
+      result = P.LinkedHashMap_LinkedHashMap$_empty(type$.String, type$.dynamic);
+      keys = _this._convert$_computeKeys$0();
+      for (i = 0; t1 = keys.length, i < t1; ++i) {
+        key = keys[i];
+        result.$indexSet(0, key, _this.$index(0, key));
+      }
+      if (t1 === 0)
+        C.JSArray_methods.add$1(keys, null);
+      else
+        C.JSArray_methods.set$length(keys, 0);
+      _this._original = _this._processed = null;
+      return _this._data = result;
+    },
+    _process$1: function(key) {
+      var result;
+      if (!Object.prototype.hasOwnProperty.call(this._original, key))
+        return null;
+      result = P._convertJsonToDartLazy(this._original[key]);
+      return this._processed[key] = result;
+    }
+  };
+  P._JsonMapKeyIterable.prototype = {
+    get$length: function(_) {
+      var t1 = this._parent;
+      return t1.get$length(t1);
+    },
+    elementAt$1: function(_, index) {
+      var t1 = this._parent;
+      if (t1._processed == null)
+        t1 = t1.get$keys().elementAt$1(0, index);
+      else {
+        t1 = t1._convert$_computeKeys$0();
+        if (index < 0 || index >= t1.length)
+          return H.ioore(t1, index);
+        t1 = t1[index];
+      }
+      return t1;
+    },
+    get$iterator: function(_) {
+      var t1 = this._parent;
+      if (t1._processed == null) {
+        t1 = t1.get$keys();
+        t1 = t1.get$iterator(t1);
+      } else {
+        t1 = t1._convert$_computeKeys$0();
+        t1 = new J.ArrayIterator(t1, t1.length, H._arrayInstanceType(t1)._eval$1("ArrayIterator<1>"));
+      }
+      return t1;
+    },
+    contains$1: function(_, key) {
+      return this._parent.containsKey$1(key);
+    }
+  };
+  P.AsciiCodec.prototype = {
+    encode$1: function(source) {
+      return C.AsciiEncoder_127.convert$1(source);
+    }
+  };
+  P._UnicodeSubsetEncoder.prototype = {
+    convert$1: function(string) {
+      var $length, result, t1, t2, t3, i, codeUnit;
+      H._checkStringNullable(string);
+      $length = P.RangeError_checkValidRange(0, null, string.length) - 0;
+      result = new Uint8Array($length);
+      for (t1 = result.length, t2 = ~this._subsetMask, t3 = J.getInterceptor$s(string), i = 0; i < $length; ++i) {
+        codeUnit = t3._codeUnitAt$1(string, i);
+        if ((codeUnit & t2) !== 0)
+          throw H.wrapException(P.ArgumentError$value(string, "string", "Contains invalid characters."));
+        if (i >= t1)
+          return H.ioore(result, i);
+        result[i] = codeUnit;
+      }
+      return result;
+    }
+  };
+  P.AsciiEncoder.prototype = {};
+  P.Base64Codec.prototype = {
+    normalize$3: function(source, start, end) {
+      var inverseAlphabet, i, sliceStart, buffer, firstPadding, firstPaddingSourceIndex, paddingCount, i0, char, i1, digit1, digit2, char0, value, t2, endLength, $length,
+        _s31_ = "Invalid base64 encoding length ",
+        t1 = source.length;
+      end = P.RangeError_checkValidRange(start, end, t1);
+      inverseAlphabet = $.$get$_Base64Decoder__inverseAlphabet();
+      for (i = start, sliceStart = i, buffer = null, firstPadding = -1, firstPaddingSourceIndex = -1, paddingCount = 0; i < end; i = i0) {
+        i0 = i + 1;
+        char = C.JSString_methods._codeUnitAt$1(source, i);
+        if (char === 37) {
+          i1 = i0 + 2;
+          if (i1 <= end) {
+            H.assertHelper(i1 <= t1);
+            digit1 = H.hexDigitValue(C.JSString_methods._codeUnitAt$1(source, i0));
+            digit2 = H.hexDigitValue(C.JSString_methods._codeUnitAt$1(source, i0 + 1));
+            char0 = digit1 * 16 + digit2 - (digit2 & 256);
+            if (char0 === 37)
+              char0 = -1;
+            i0 = i1;
+          } else
+            char0 = -1;
+        } else
+          char0 = char;
+        if (0 <= char0 && char0 <= 127) {
+          if (char0 < 0 || char0 >= inverseAlphabet.length)
+            return H.ioore(inverseAlphabet, char0);
+          value = inverseAlphabet[char0];
+          if (value >= 0) {
+            char0 = C.JSString_methods.codeUnitAt$1("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/", value);
+            if (char0 === char)
+              continue;
+            char = char0;
+          } else {
+            if (value === -1) {
+              if (firstPadding < 0) {
+                t2 = buffer == null ? null : buffer._contents.length;
+                if (t2 == null)
+                  t2 = 0;
+                firstPadding = t2 + (i - sliceStart);
+                firstPaddingSourceIndex = i;
+              }
+              ++paddingCount;
+              if (char === 61)
+                continue;
+            }
+            char = char0;
+          }
+          if (value !== -2) {
+            if (buffer == null)
+              buffer = new P.StringBuffer("");
+            t2 = buffer._contents += C.JSString_methods.substring$2(source, sliceStart, i);
+            buffer._contents = t2 + H.Primitives_stringFromCharCode(char);
+            sliceStart = i0;
+            continue;
+          }
+        }
+        throw H.wrapException(P.FormatException$("Invalid base64 data", source, i));
+      }
+      if (buffer != null) {
+        t1 = buffer._contents += C.JSString_methods.substring$2(source, sliceStart, end);
+        t2 = t1.length;
+        if (firstPadding >= 0)
+          P.Base64Codec__checkPadding(source, firstPaddingSourceIndex, end, firstPadding, paddingCount, t2);
+        else {
+          endLength = C.JSInt_methods.$mod(t2 - 1, 4) + 1;
+          if (endLength === 1)
+            throw H.wrapException(P.FormatException$(_s31_, source, end));
+          for (; endLength < 4;) {
+            t1 += "=";
+            buffer._contents = t1;
+            ++endLength;
+          }
+        }
+        t1 = buffer._contents;
+        return C.JSString_methods.replaceRange$3(source, start, end, t1.charCodeAt(0) == 0 ? t1 : t1);
+      }
+      $length = end - start;
+      if (firstPadding >= 0)
+        P.Base64Codec__checkPadding(source, firstPaddingSourceIndex, end, firstPadding, paddingCount, $length);
+      else {
+        endLength = C.JSInt_methods.$mod($length, 4);
+        if (endLength === 1)
+          throw H.wrapException(P.FormatException$(_s31_, source, end));
+        if (endLength > 1)
+          source = C.JSString_methods.replaceRange$3(source, end, end, endLength === 2 ? "==" : "=");
+      }
+      return source;
+    }
+  };
+  P.Base64Encoder.prototype = {};
+  P.Codec.prototype = {};
+  P._FusedCodec.prototype = {};
+  P.Converter.prototype = {};
+  P.Encoding.prototype = {};
+  P.JsonCodec.prototype = {
+    decode$2$reviver: function(source, reviver) {
+      var t1;
+      type$.dynamic_Function_Object_Object._check(reviver);
+      t1 = P._parseJson(source, this.get$decoder()._reviver);
+      return t1;
+    },
+    get$decoder: function() {
+      return C.JsonDecoder_null;
+    }
+  };
+  P.JsonDecoder.prototype = {};
+  P.Utf8Codec.prototype = {
+    get$encoder: function() {
+      return C.C_Utf8Encoder;
+    }
+  };
+  P.Utf8Encoder.prototype = {
+    convert$1: function(string) {
+      var end, $length, t1, encoder, endPosition, t2, lastCodeUnit;
+      H._checkStringNullable(string);
+      end = P.RangeError_checkValidRange(0, null, string.length);
+      $length = end - 0;
+      if ($length === 0)
+        return new Uint8Array(0);
+      t1 = new Uint8Array($length * 3);
+      encoder = new P._Utf8Encoder(t1);
+      endPosition = encoder._fillBuffer$3(string, 0, end);
+      t2 = end - 1;
+      H.assertHelper(endPosition >= t2);
+      if (endPosition !== end) {
+        lastCodeUnit = J.codeUnitAt$1$s(string, t2);
+        H.assertHelper((lastCodeUnit & 64512) === 55296);
+        H.assertHelper(!encoder._writeSurrogate$2(lastCodeUnit, 0));
+      }
+      return C.NativeUint8List_methods.sublist$2(t1, 0, encoder._bufferIndex);
+    }
+  };
+  P._Utf8Encoder.prototype = {
+    _writeSurrogate$2: function(leadingSurrogate, nextCodeUnit) {
+      var rune, t3, t4, _this = this,
+        t1 = _this._buffer,
+        t2 = t1.length;
+      if ((nextCodeUnit & 64512) === 56320) {
+        rune = 65536 + ((leadingSurrogate & 1023) << 10) | nextCodeUnit & 1023;
+        H.assertHelper(rune > 65535);
+        H.assertHelper(rune <= 1114111);
+        t3 = _this._bufferIndex;
+        t4 = _this._bufferIndex = t3 + 1;
+        if (t3 >= t2)
+          return H.ioore(t1, t3);
+        t1[t3] = 240 | rune >>> 18;
+        t3 = _this._bufferIndex = t4 + 1;
+        if (t4 >= t2)
+          return H.ioore(t1, t4);
+        t1[t4] = 128 | rune >>> 12 & 63;
+        t4 = _this._bufferIndex = t3 + 1;
+        if (t3 >= t2)
+          return H.ioore(t1, t3);
+        t1[t3] = 128 | rune >>> 6 & 63;
+        _this._bufferIndex = t4 + 1;
+        if (t4 >= t2)
+          return H.ioore(t1, t4);
+        t1[t4] = 128 | rune & 63;
+        return true;
+      } else {
+        t3 = _this._bufferIndex;
+        t4 = _this._bufferIndex = t3 + 1;
+        if (t3 >= t2)
+          return H.ioore(t1, t3);
+        t1[t3] = 224 | leadingSurrogate >>> 12;
+        t3 = _this._bufferIndex = t4 + 1;
+        if (t4 >= t2)
+          return H.ioore(t1, t4);
+        t1[t4] = 128 | leadingSurrogate >>> 6 & 63;
+        _this._bufferIndex = t3 + 1;
+        if (t3 >= t2)
+          return H.ioore(t1, t3);
+        t1[t3] = 128 | leadingSurrogate & 63;
+        return false;
+      }
+    },
+    _fillBuffer$3: function(str, start, end) {
+      var t1, t2, t3, stringIndex, codeUnit, t4, stringIndex0, t5, _this = this;
+      if (start !== end && (J.codeUnitAt$1$s(str, end - 1) & 64512) === 55296)
+        --end;
+      for (t1 = _this._buffer, t2 = t1.length, t3 = J.getInterceptor$s(str), stringIndex = start; stringIndex < end; ++stringIndex) {
+        codeUnit = t3._codeUnitAt$1(str, stringIndex);
+        if (codeUnit <= 127) {
+          t4 = _this._bufferIndex;
+          if (t4 >= t2)
+            break;
+          _this._bufferIndex = t4 + 1;
+          t1[t4] = codeUnit;
+        } else if ((codeUnit & 64512) === 55296) {
+          if (_this._bufferIndex + 3 >= t2)
+            break;
+          stringIndex0 = stringIndex + 1;
+          if (_this._writeSurrogate$2(codeUnit, C.JSString_methods._codeUnitAt$1(str, stringIndex0)))
+            stringIndex = stringIndex0;
+        } else if (codeUnit <= 2047) {
+          t4 = _this._bufferIndex;
+          t5 = t4 + 1;
+          if (t5 >= t2)
+            break;
+          _this._bufferIndex = t5;
+          if (t4 >= t2)
+            return H.ioore(t1, t4);
+          t1[t4] = 192 | codeUnit >>> 6;
+          _this._bufferIndex = t5 + 1;
+          t1[t5] = 128 | codeUnit & 63;
+        } else {
+          H.assertHelper(codeUnit <= 65535);
+          t4 = _this._bufferIndex;
+          if (t4 + 2 >= t2)
+            break;
+          t5 = _this._bufferIndex = t4 + 1;
+          if (t4 >= t2)
+            return H.ioore(t1, t4);
+          t1[t4] = 224 | codeUnit >>> 12;
+          t4 = _this._bufferIndex = t5 + 1;
+          if (t5 >= t2)
+            return H.ioore(t1, t5);
+          t1[t5] = 128 | codeUnit >>> 6 & 63;
+          _this._bufferIndex = t4 + 1;
+          if (t4 >= t2)
+            return H.ioore(t1, t4);
+          t1[t4] = 128 | codeUnit & 63;
+        }
+      }
+      return stringIndex;
+    }
+  };
+  P.Utf8Decoder.prototype = {
+    convert$1: function(codeUnits) {
+      var result, end, oneBytes, firstPart, buffer, start, isFirstCharacter, decoder, t1;
+      type$.List_int._check(codeUnits);
+      result = P.Utf8Decoder__convertIntercepted(false, codeUnits, 0, null);
+      if (result != null)
+        return result;
+      end = P.RangeError_checkValidRange(0, null, J.get$length$asx(codeUnits));
+      oneBytes = P._scanOneByteCharacters(codeUnits, 0, end);
+      if (oneBytes > 0) {
+        firstPart = P.String_String$fromCharCodes(codeUnits, 0, oneBytes);
+        if (oneBytes === end)
+          return firstPart;
+        buffer = new P.StringBuffer(firstPart);
+        start = oneBytes;
+        isFirstCharacter = false;
+      } else {
+        start = 0;
+        buffer = null;
+        isFirstCharacter = true;
+      }
+      if (buffer == null)
+        buffer = new P.StringBuffer("");
+      decoder = new P._Utf8Decoder(false, buffer);
+      decoder._isFirstCharacter = isFirstCharacter;
+      decoder.convert$3(codeUnits, start, end);
+      decoder.flush$2(codeUnits, end);
+      t1 = buffer._contents;
+      return t1.charCodeAt(0) == 0 ? t1 : t1;
+    }
+  };
+  P._Utf8Decoder.prototype = {
+    flush$2: function(source, offset) {
+      var t1;
+      type$.List_int._check(source);
+      if (this._expectedUnits > 0) {
+        t1 = P.FormatException$("Unfinished UTF-8 octet sequence", source, offset);
+        throw H.wrapException(t1);
+      }
+    },
+    convert$3: function(codeUnits, startIndex, endIndex) {
+      var value, expectedUnits, extraUnits, t1, t2, i, unit, t3, oneBytes, i0, i1, t4, _this = this,
+        _s21_ = "Bad UTF-8 encoding 0x";
+      type$.List_int._check(codeUnits);
+      value = _this._convert$_value;
+      expectedUnits = _this._expectedUnits;
+      extraUnits = _this._extraUnits;
+      _this._extraUnits = _this._expectedUnits = _this._convert$_value = 0;
+      $label0$0:
+        for (t1 = J.getInterceptor$asx(codeUnits), t2 = _this._stringSink, i = startIndex; true; i = i1) {
+          $label1$1:
+            if (expectedUnits > 0) {
+              do {
+                if (i === endIndex)
+                  break $label0$0;
+                unit = t1.$index(codeUnits, i);
+                if (typeof unit !== "number")
+                  return unit.$and();
+                if ((unit & 192) !== 128) {
+                  t3 = P.FormatException$(_s21_ + C.JSInt_methods.toRadixString$1(unit, 16), codeUnits, i);
+                  throw H.wrapException(t3);
+                } else {
+                  value = (value << 6 | unit & 63) >>> 0;
+                  --expectedUnits;
+                  ++i;
+                }
+              } while (expectedUnits > 0);
+              t3 = extraUnits - 1;
+              if (t3 < 0 || t3 >= 4)
+                return H.ioore(C.List_127_2047_65535_1114111, t3);
+              if (value <= C.List_127_2047_65535_1114111[t3]) {
+                t3 = P.FormatException$("Overlong encoding of 0x" + C.JSInt_methods.toRadixString$1(value, 16), codeUnits, i - extraUnits - 1);
+                throw H.wrapException(t3);
+              }
+              if (value > 1114111) {
+                t3 = P.FormatException$("Character outside valid Unicode range: 0x" + C.JSInt_methods.toRadixString$1(value, 16), codeUnits, i - extraUnits - 1);
+                throw H.wrapException(t3);
+              }
+              if (!_this._isFirstCharacter || value !== 65279)
+                t2._contents += H.Primitives_stringFromCharCode(value);
+              _this._isFirstCharacter = false;
+            }
+          for (t3 = i < endIndex; t3;) {
+            oneBytes = P._scanOneByteCharacters(codeUnits, i, endIndex);
+            if (oneBytes > 0) {
+              _this._isFirstCharacter = false;
+              i0 = i + oneBytes;
+              H.assertHelper(i0 <= endIndex);
+              t2._contents += P.String_String$fromCharCodes(codeUnits, i, i0);
+              if (i0 === endIndex)
+                break;
+            } else
+              i0 = i;
+            i1 = i0 + 1;
+            unit = t1.$index(codeUnits, i0);
+            if (typeof unit !== "number")
+              return unit.$lt();
+            if (unit < 0) {
+              t4 = P.FormatException$("Negative UTF-8 code unit: -0x" + C.JSInt_methods.toRadixString$1(-unit, 16), codeUnits, i1 - 1);
+              throw H.wrapException(t4);
+            } else {
+              H.assertHelper(unit > 127);
+              if ((unit & 224) === 192) {
+                value = unit & 31;
+                expectedUnits = 1;
+                extraUnits = 1;
+                continue $label0$0;
+              }
+              if ((unit & 240) === 224) {
+                value = unit & 15;
+                expectedUnits = 2;
+                extraUnits = 2;
+                continue $label0$0;
+              }
+              if ((unit & 248) === 240 && unit < 245) {
+                value = unit & 7;
+                expectedUnits = 3;
+                extraUnits = 3;
+                continue $label0$0;
+              }
+              t4 = P.FormatException$(_s21_ + C.JSInt_methods.toRadixString$1(unit, 16), codeUnits, i1 - 1);
+              throw H.wrapException(t4);
+            }
+          }
+          break $label0$0;
+        }
+      if (expectedUnits > 0) {
+        _this._convert$_value = value;
+        _this._expectedUnits = expectedUnits;
+        _this._extraUnits = extraUnits;
+      }
+    }
+  };
+  P.bool.prototype = {};
+  P.DateTime.prototype = {
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      return other instanceof P.DateTime && this._value === other._value && true;
+    },
+    get$hashCode: function(_) {
+      var t1 = this._value;
+      return (t1 ^ C.JSInt_methods._shrOtherPositive$1(t1, 30)) & 1073741823;
+    },
+    toString$0: function(_) {
+      var _this = this,
+        y = P.DateTime__fourDigits(H.Primitives_getYear(_this)),
+        m = P.DateTime__twoDigits(H.Primitives_getMonth(_this)),
+        d = P.DateTime__twoDigits(H.Primitives_getDay(_this)),
+        h = P.DateTime__twoDigits(H.Primitives_getHours(_this)),
+        min = P.DateTime__twoDigits(H.Primitives_getMinutes(_this)),
+        sec = P.DateTime__twoDigits(H.Primitives_getSeconds(_this)),
+        ms = P.DateTime__threeDigits(H.Primitives_getMilliseconds(_this)),
+        t1 = y + "-" + m + "-" + d + " " + h + ":" + min + ":" + sec + "." + ms + "Z";
+      return t1;
+    }
+  };
+  P.double.prototype = {};
+  P.Duration.prototype = {
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      return other instanceof P.Duration && this._duration === other._duration;
+    },
+    get$hashCode: function(_) {
+      return C.JSInt_methods.get$hashCode(this._duration);
+    },
+    toString$0: function(_) {
+      var twoDigitMinutes, twoDigitSeconds, sixDigitUs,
+        t1 = new P.Duration_toString_twoDigits(),
+        t2 = this._duration;
+      if (t2 < 0)
+        return "-" + new P.Duration(0 - t2).toString$0(0);
+      twoDigitMinutes = t1.call$1(C.JSInt_methods._tdivFast$1(t2, 60000000) % 60);
+      twoDigitSeconds = t1.call$1(C.JSInt_methods._tdivFast$1(t2, 1000000) % 60);
+      sixDigitUs = new P.Duration_toString_sixDigits().call$1(t2 % 1000000);
+      return "" + C.JSInt_methods._tdivFast$1(t2, 3600000000) + ":" + H.S(twoDigitMinutes) + ":" + H.S(twoDigitSeconds) + "." + H.S(sixDigitUs);
+    }
+  };
+  P.Duration_toString_sixDigits.prototype = {
+    call$1: function(n) {
+      if (n >= 100000)
+        return "" + n;
+      if (n >= 10000)
+        return "0" + n;
+      if (n >= 1000)
+        return "00" + n;
+      if (n >= 100)
+        return "000" + n;
+      if (n >= 10)
+        return "0000" + n;
+      return "00000" + n;
+    },
+    $signature: 25
+  };
+  P.Duration_toString_twoDigits.prototype = {
+    call$1: function(n) {
+      if (n >= 10)
+        return "" + n;
+      return "0" + n;
+    },
+    $signature: 25
+  };
+  P.Error.prototype = {};
+  P.AssertionError.prototype = {
+    toString$0: function(_) {
+      var t1 = this.message;
+      if (t1 != null)
+        return "Assertion failed: " + P.Error_safeToString(t1);
+      return "Assertion failed";
+    },
+    get$message: function(receiver) {
+      return this.message;
+    }
+  };
+  P.NullThrownError.prototype = {
+    toString$0: function(_) {
+      return "Throw of null.";
+    }
+  };
+  P.ArgumentError.prototype = {
+    get$_errorName: function() {
+      return "Invalid argument" + (!this._hasValue ? "(s)" : "");
+    },
+    get$_errorExplanation: function() {
+      return "";
+    },
+    toString$0: function(_) {
+      var message, prefix, explanation, errorValue, _this = this,
+        t1 = _this.name,
+        nameString = t1 != null ? " (" + t1 + ")" : "";
+      t1 = _this.message;
+      message = t1 == null ? "" : ": " + H.S(t1);
+      prefix = _this.get$_errorName() + nameString + message;
+      if (!_this._hasValue)
+        return prefix;
+      explanation = _this.get$_errorExplanation();
+      errorValue = P.Error_safeToString(_this.invalidValue);
+      return prefix + explanation + ": " + errorValue;
+    },
+    get$message: function(receiver) {
+      return this.message;
+    }
+  };
+  P.RangeError.prototype = {
+    get$_errorName: function() {
+      return "RangeError";
+    },
+    get$_errorExplanation: function() {
+      var t1, explanation, t2, _this = this;
+      H.assertHelper(_this._hasValue);
+      t1 = _this.start;
+      if (t1 == null) {
+        t1 = _this.end;
+        explanation = t1 != null ? ": Not less than or equal to " + H.S(t1) : "";
+      } else {
+        t2 = _this.end;
+        if (t2 == null)
+          explanation = ": Not greater than or equal to " + H.S(t1);
+        else if (t2 > t1)
+          explanation = ": Not in range " + H.S(t1) + ".." + H.S(t2) + ", inclusive";
+        else
+          explanation = t2 < t1 ? ": Valid value range is empty" : ": Only valid value is " + H.S(t1);
+      }
+      return explanation;
+    }
+  };
+  P.IndexError.prototype = {
+    get$_errorName: function() {
+      return "RangeError";
+    },
+    get$_errorExplanation: function() {
+      var invalidValue, t1;
+      H.assertHelper(this._hasValue);
+      invalidValue = H._checkIntNullable(this.invalidValue);
+      if (typeof invalidValue !== "number")
+        return invalidValue.$lt();
+      if (invalidValue < 0)
+        return ": index must not be negative";
+      t1 = this.length;
+      if (t1 === 0)
+        return ": no indices are valid";
+      return ": index should be less than " + H.S(t1);
+    },
+    get$length: function(receiver) {
+      return this.length;
+    }
+  };
+  P.UnsupportedError.prototype = {
+    toString$0: function(_) {
+      return "Unsupported operation: " + this.message;
+    },
+    get$message: function(receiver) {
+      return this.message;
+    }
+  };
+  P.UnimplementedError.prototype = {
+    toString$0: function(_) {
+      var t1 = this.message;
+      return t1 != null ? "UnimplementedError: " + t1 : "UnimplementedError";
+    },
+    get$message: function(receiver) {
+      return this.message;
+    }
+  };
+  P.StateError.prototype = {
+    toString$0: function(_) {
+      return "Bad state: " + this.message;
+    },
+    get$message: function(receiver) {
+      return this.message;
+    }
+  };
+  P.ConcurrentModificationError.prototype = {
+    toString$0: function(_) {
+      var t1 = this.modifiedObject;
+      if (t1 == null)
+        return "Concurrent modification during iteration.";
+      return "Concurrent modification during iteration: " + P.Error_safeToString(t1) + ".";
+    }
+  };
+  P.OutOfMemoryError.prototype = {
+    toString$0: function(_) {
+      return "Out of Memory";
+    },
+    $isError: 1
+  };
+  P.StackOverflowError.prototype = {
+    toString$0: function(_) {
+      return "Stack Overflow";
+    },
+    $isError: 1
+  };
+  P.CyclicInitializationError.prototype = {
+    toString$0: function(_) {
+      var t1 = this.variableName;
+      return t1 == null ? "Reading static variable during its initialization" : "Reading static variable '" + t1 + "' during its initialization";
+    }
+  };
+  P._Exception.prototype = {
+    toString$0: function(_) {
+      return "Exception: " + this.message;
+    },
+    $isException: 1,
+    get$message: function(receiver) {
+      return this.message;
+    }
+  };
+  P.FormatException.prototype = {
+    toString$0: function(_) {
+      var source, lineNum, lineStart, previousCharWasCR, i, char, lineEnd, end, start, prefix, postfix, slice,
+        t1 = this.message,
+        report = t1 != null && "" !== t1 ? "FormatException: " + H.S(t1) : "FormatException",
+        offset = this.offset,
+        objectSource = this.source;
+      if (typeof objectSource == "string") {
+        if (offset != null)
+          t1 = offset < 0 || offset > objectSource.length;
+        else
+          t1 = false;
+        if (t1)
+          offset = null;
+        if (offset == null) {
+          source = objectSource.length > 78 ? C.JSString_methods.substring$2(objectSource, 0, 75) + "..." : objectSource;
+          return report + "\n" + source;
+        }
+        for (lineNum = 1, lineStart = 0, previousCharWasCR = false, i = 0; i < offset; ++i) {
+          char = C.JSString_methods._codeUnitAt$1(objectSource, i);
+          if (char === 10) {
+            if (lineStart !== i || !previousCharWasCR)
+              ++lineNum;
+            lineStart = i + 1;
+            previousCharWasCR = false;
+          } else if (char === 13) {
+            ++lineNum;
+            lineStart = i + 1;
+            previousCharWasCR = true;
+          }
+        }
+        report = lineNum > 1 ? report + (" (at line " + lineNum + ", character " + (offset - lineStart + 1) + ")\n") : report + (" (at character " + (offset + 1) + ")\n");
+        lineEnd = objectSource.length;
+        for (i = offset; i < lineEnd; ++i) {
+          char = C.JSString_methods.codeUnitAt$1(objectSource, i);
+          if (char === 10 || char === 13) {
+            lineEnd = i;
+            break;
+          }
+        }
+        if (lineEnd - lineStart > 78)
+          if (offset - lineStart < 75) {
+            end = lineStart + 75;
+            start = lineStart;
+            prefix = "";
+            postfix = "...";
+          } else {
+            if (lineEnd - offset < 75) {
+              start = lineEnd - 75;
+              end = lineEnd;
+              postfix = "";
+            } else {
+              start = offset - 36;
+              end = offset + 36;
+              postfix = "...";
+            }
+            prefix = "...";
+          }
+        else {
+          end = lineEnd;
+          start = lineStart;
+          prefix = "";
+          postfix = "";
+        }
+        slice = C.JSString_methods.substring$2(objectSource, start, end);
+        return report + prefix + slice + postfix + "\n" + C.JSString_methods.$mul(" ", offset - start + prefix.length) + "^\n";
+      } else
+        return offset != null ? report + (" (at offset " + H.S(offset) + ")") : report;
+    },
+    $isException: 1,
+    get$message: function(receiver) {
+      return this.message;
+    }
+  };
+  P.Expando.prototype = {
+    $index: function(_, object) {
+      var t2, values,
+        t1 = this._jsWeakMapOrKey;
+      if (typeof t1 != "string") {
+        if (object != null)
+          t2 = typeof object == "number" || typeof object == "string";
+        else
+          t2 = true;
+        if (t2)
+          H.throwExpression(P.ArgumentError$value(object, "Expandos are not allowed on strings, numbers, booleans or null", null));
+        return t1.get(object);
+      }
+      values = H.Primitives_getProperty(object, "expando$values");
+      t1 = values == null ? null : H.Primitives_getProperty(values, t1);
+      return this.$ti._precomputed1._check(t1);
+    },
+    $indexSet: function(_, object, value) {
+      var t1, values,
+        _s14_ = "expando$values";
+      this.$ti._precomputed1._check(value);
+      t1 = this._jsWeakMapOrKey;
+      if (typeof t1 != "string")
+        t1.set(object, value);
+      else {
+        values = H.Primitives_getProperty(object, _s14_);
+        if (values == null) {
+          values = new P.Object();
+          H.Primitives_setProperty(object, _s14_, values);
+        }
+        H.Primitives_setProperty(values, t1, value);
+      }
+    },
+    toString$0: function(_) {
+      return "Expando:" + this.name;
+    }
+  };
+  P.Function.prototype = {};
+  P.int.prototype = {};
+  P.Iterable.prototype = {
+    map$1$1: function(_, f, $T) {
+      var t1 = H._instanceType(this);
+      return H.MappedIterable_MappedIterable(this, t1._bind$1($T)._eval$1("1(Iterable.E)")._check(f), t1._eval$1("Iterable.E"), $T);
+    },
+    where$1: function(_, test) {
+      var t1 = H._instanceType(this);
+      return new H.WhereIterable(this, t1._eval$1("bool(Iterable.E)")._check(test), t1._eval$1("WhereIterable<Iterable.E>"));
+    },
+    contains$1: function(_, element) {
+      var t1;
+      for (t1 = this.get$iterator(this); t1.moveNext$0();)
+        if (J.$eq$(t1.get$current(), element))
+          return true;
+      return false;
+    },
+    join$1: function(_, separator) {
+      var t1,
+        iterator = this.get$iterator(this);
+      if (!iterator.moveNext$0())
+        return "";
+      if (separator === "") {
+        t1 = "";
+        do
+          t1 += H.S(iterator.get$current());
+        while (iterator.moveNext$0());
+      } else {
+        t1 = H.S(iterator.get$current());
+        for (; iterator.moveNext$0();)
+          t1 = t1 + separator + H.S(iterator.get$current());
+      }
+      return t1.charCodeAt(0) == 0 ? t1 : t1;
+    },
+    join$0: function($receiver) {
+      return this.join$1($receiver, "");
+    },
+    toList$1$growable: function(_, growable) {
+      return P.List_List$from(this, true, H._instanceType(this)._eval$1("Iterable.E"));
+    },
+    toList$0: function($receiver) {
+      return this.toList$1$growable($receiver, true);
+    },
+    toSet$0: function(_) {
+      return P.LinkedHashSet_LinkedHashSet$from(this, H._instanceType(this)._eval$1("Iterable.E"));
+    },
+    get$length: function(_) {
+      var it, count;
+      H.assertHelper(!type$.EfficientLengthIterable_dynamic._is(this));
+      it = this.get$iterator(this);
+      for (count = 0; it.moveNext$0();)
+        ++count;
+      return count;
+    },
+    get$isEmpty: function(_) {
+      return !this.get$iterator(this).moveNext$0();
+    },
+    skipWhile$1: function(_, test) {
+      var t1 = H._instanceType(this);
+      return new H.SkipWhileIterable(this, t1._eval$1("bool(Iterable.E)")._check(test), t1._eval$1("SkipWhileIterable<Iterable.E>"));
+    },
+    get$first: function(_) {
+      var it = this.get$iterator(this);
+      if (!it.moveNext$0())
+        throw H.wrapException(H.IterableElementError_noElement());
+      return it.get$current();
+    },
+    get$last: function(_) {
+      var result,
+        it = this.get$iterator(this);
+      if (!it.moveNext$0())
+        throw H.wrapException(H.IterableElementError_noElement());
+      do
+        result = it.get$current();
+      while (it.moveNext$0());
+      return result;
+    },
+    elementAt$1: function(_, index) {
+      var t1, elementIndex, element;
+      P.RangeError_checkNotNegative(index, "index");
+      for (t1 = this.get$iterator(this), elementIndex = 0; t1.moveNext$0();) {
+        element = t1.get$current();
+        if (index === elementIndex)
+          return element;
+        ++elementIndex;
+      }
+      throw H.wrapException(P.IndexError$(index, this, "index", null, elementIndex));
+    },
+    toString$0: function(_) {
+      return P.IterableBase_iterableToShortString(this, "(", ")");
+    }
+  };
+  P.Iterator.prototype = {};
+  P.List.prototype = {$isEfficientLengthIterable: 1, $isIterable: 1};
+  P.Map.prototype = {};
+  P.MapEntry.prototype = {
+    toString$0: function(_) {
+      return "MapEntry(" + H.S(this.key) + ": " + H.S(this.value) + ")";
+    }
+  };
+  P.Null.prototype = {
+    get$hashCode: function(_) {
+      return P.Object.prototype.get$hashCode.call(this, this);
+    },
+    toString$0: function(_) {
+      return "null";
+    }
+  };
+  P.num.prototype = {};
+  P.Object.prototype = {constructor: P.Object, $isObject: 1,
+    $eq: function(_, other) {
+      return this === other;
+    },
+    get$hashCode: function(_) {
+      return H.Primitives_objectHashCode(this);
+    },
+    toString$0: function(_) {
+      return "Instance of '" + H.S(H.Primitives_objectTypeName(this)) + "'";
+    },
+    get$runtimeType: function(_) {
+      return H.getRuntimeType(this);
+    },
+    toString: function() {
+      return this.toString$0(this);
+    }
+  };
+  P.Pattern.prototype = {};
+  P.Match.prototype = {};
+  P.RegExpMatch.prototype = {$isMatch: 1};
+  P.Set.prototype = {};
+  P.StackTrace.prototype = {};
+  P._StringStackTrace.prototype = {
+    toString$0: function(_) {
+      return this._stackTrace;
+    },
+    $isStackTrace: 1
+  };
+  P.Stopwatch.prototype = {
+    get$elapsedMicroseconds: function() {
+      var t2, ticks,
+        t1 = this._stop;
+      if (t1 == null)
+        t1 = H._checkIntNullable($.Primitives_timerTicks.call$0());
+      t2 = this._core$_start;
+      if (typeof t1 !== "number")
+        return t1.$sub();
+      ticks = t1 - t2;
+      t1 = $.Stopwatch__frequency;
+      if (t1 === 1000000)
+        return ticks;
+      H.assertHelper(t1 === 1000);
+      return ticks * 1000;
+    }
+  };
+  P.String.prototype = {$isPattern: 1};
+  P.Runes.prototype = {
+    get$iterator: function(_) {
+      return new P.RuneIterator(this.string);
+    },
+    get$last: function(_) {
+      var code, previousCode,
+        t1 = this.string,
+        t2 = t1.length;
+      if (t2 === 0)
+        throw H.wrapException(P.StateError$("No elements."));
+      code = C.JSString_methods.codeUnitAt$1(t1, t2 - 1);
+      if ((code & 64512) === 56320 && t2 > 1) {
+        previousCode = C.JSString_methods.codeUnitAt$1(t1, t2 - 2);
+        if ((previousCode & 64512) === 55296)
+          return P._combineSurrogatePair(previousCode, code);
+      }
+      return code;
+    }
+  };
+  P.RuneIterator.prototype = {
+    get$current: function() {
+      return this._currentCodePoint;
+    },
+    moveNext$0: function() {
+      var codeUnit, nextPosition, nextCodeUnit, _this = this,
+        t1 = _this._core$_position = _this._nextPosition,
+        t2 = _this.string,
+        t3 = t2.length;
+      if (t1 === t3) {
+        _this._currentCodePoint = null;
+        return false;
+      }
+      codeUnit = C.JSString_methods._codeUnitAt$1(t2, t1);
+      nextPosition = t1 + 1;
+      if ((codeUnit & 64512) === 55296 && nextPosition < t3) {
+        nextCodeUnit = C.JSString_methods._codeUnitAt$1(t2, nextPosition);
+        if ((nextCodeUnit & 64512) === 56320) {
+          _this._nextPosition = nextPosition + 1;
+          _this._currentCodePoint = P._combineSurrogatePair(codeUnit, nextCodeUnit);
+          return true;
+        }
+      }
+      _this._nextPosition = nextPosition;
+      _this._currentCodePoint = codeUnit;
+      return true;
+    },
+    $isIterator: 1
+  };
+  P.StringBuffer.prototype = {
+    get$length: function(_) {
+      return this._contents.length;
+    },
+    toString$0: function(_) {
+      var t1 = this._contents;
+      return t1.charCodeAt(0) == 0 ? t1 : t1;
+    },
+    $isStringSink: 1
+  };
+  P.Uri.prototype = {};
+  P.Uri__parseIPv4Address_error.prototype = {
+    call$2: function(msg, position) {
+      throw H.wrapException(P.FormatException$("Illegal IPv4 address, " + msg, this.host, position));
+    },
+    $signature: 68
+  };
+  P.Uri_parseIPv6Address_error.prototype = {
+    call$2: function(msg, position) {
+      throw H.wrapException(P.FormatException$("Illegal IPv6 address, " + msg, this.host, position));
+    },
+    call$1: function(msg) {
+      return this.call$2(msg, null);
+    },
+    $signature: 67
+  };
+  P.Uri_parseIPv6Address_parseHex.prototype = {
+    call$2: function(start, end) {
+      var value;
+      if (end - start > 4)
+        this.error.call$2("an IPv6 part can only contain a maximum of 4 hex digits", start);
+      value = P.int_parse(C.JSString_methods.substring$2(this.host, start, end), null, 16);
+      if (typeof value !== "number")
+        return value.$lt();
+      if (value < 0 || value > 65535)
+        this.error.call$2("each part must be in the range of `0x0..0xFFFF`", start);
+      return value;
+    },
+    $signature: 65
+  };
+  P._Uri.prototype = {
+    get$userInfo: function() {
+      return this._userInfo;
+    },
+    get$host: function(_) {
+      var t1 = this._host;
+      if (t1 == null)
+        return "";
+      if (C.JSString_methods.startsWith$1(t1, "["))
+        return C.JSString_methods.substring$2(t1, 1, t1.length - 1);
+      return t1;
+    },
+    get$port: function(_) {
+      var t1 = this._port;
+      if (t1 == null)
+        return P._Uri__defaultPort(this.scheme);
+      return t1;
+    },
+    get$query: function() {
+      var t1 = this._query;
+      return t1 == null ? "" : t1;
+    },
+    get$fragment: function() {
+      var t1 = this._fragment;
+      return t1 == null ? "" : t1;
+    },
+    replace$2$path$pathSegments: function(_, path, pathSegments) {
+      var scheme, isFile, userInfo, port, host, hasAuthority, t1, _this = this;
+      type$.Iterable_String._check(pathSegments);
+      type$.Map_String_dynamic._check(null);
+      scheme = _this.scheme;
+      isFile = scheme === "file";
+      userInfo = _this._userInfo;
+      port = _this._port;
+      host = _this._host;
+      if (!(host != null))
+        host = userInfo.length !== 0 || port != null || isFile ? "" : null;
+      hasAuthority = host != null;
+      t1 = path == null;
+      if (!t1 || pathSegments != null)
+        path = P._Uri__makePath(path, 0, t1 ? 0 : path.length, pathSegments, scheme, hasAuthority);
+      else {
+        path = _this.path;
+        if (!isFile)
+          t1 = hasAuthority && path.length !== 0;
+        else
+          t1 = true;
+        if (t1 && !C.JSString_methods.startsWith$1(path, "/"))
+          path = "/" + path;
+      }
+      return new P._Uri(scheme, userInfo, host, port, path, _this._query, _this._fragment);
+    },
+    replace$1$path: function($receiver, path) {
+      return this.replace$2$path$pathSegments($receiver, path, null);
+    },
+    replace$1$pathSegments: function($receiver, pathSegments) {
+      return this.replace$2$path$pathSegments($receiver, null, pathSegments);
+    },
+    get$pathSegments: function() {
+      var pathToSplit,
+        result = this._pathSegments;
+      if (result != null)
+        return result;
+      pathToSplit = this.path;
+      if (pathToSplit.length !== 0 && C.JSString_methods._codeUnitAt$1(pathToSplit, 0) === 47)
+        pathToSplit = C.JSString_methods.substring$1(pathToSplit, 1);
+      result = pathToSplit === "" ? C.List_empty : P.List_List$unmodifiable(new H.MappedListIterable(H.setRuntimeTypeInfo(pathToSplit.split("/"), type$.JSArray_String), type$.dynamic_Function_String._check(P.core_Uri_decodeComponent$closure()), type$.MappedListIterable_String_dynamic), type$.String);
+      this.set$_pathSegments(result);
+      return result;
+    },
+    _mergePaths$2: function(base, reference) {
+      var backCount, refStart, baseEnd, newEnd, delta, t1;
+      for (backCount = 0, refStart = 0; C.JSString_methods.startsWith$2(reference, "../", refStart);) {
+        refStart += 3;
+        ++backCount;
+      }
+      baseEnd = C.JSString_methods.lastIndexOf$1(base, "/");
+      while (true) {
+        if (!(baseEnd > 0 && backCount > 0))
+          break;
+        newEnd = C.JSString_methods.lastIndexOf$2(base, "/", baseEnd - 1);
+        if (newEnd < 0)
+          break;
+        delta = baseEnd - newEnd;
+        t1 = delta !== 2;
+        if (!t1 || delta === 3)
+          if (C.JSString_methods.codeUnitAt$1(base, newEnd + 1) === 46)
+            t1 = !t1 || C.JSString_methods.codeUnitAt$1(base, newEnd + 2) === 46;
+          else
+            t1 = false;
+        else
+          t1 = false;
+        if (t1)
+          break;
+        --backCount;
+        baseEnd = newEnd;
+      }
+      return C.JSString_methods.replaceRange$3(base, baseEnd + 1, null, C.JSString_methods.substring$1(reference, refStart - 3 * backCount));
+    },
+    resolve$1: function(reference) {
+      return this.resolveUri$1(P.Uri_parse(reference));
+    },
+    resolveUri$1: function(reference) {
+      var targetScheme, targetUserInfo, targetHost, targetPort, targetPath, targetQuery, t1, mergedPath, t2, _this = this, _null = null;
+      if (reference.get$scheme().length !== 0) {
+        targetScheme = reference.get$scheme();
+        if (reference.get$hasAuthority()) {
+          targetUserInfo = reference.get$userInfo();
+          targetHost = reference.get$host(reference);
+          targetPort = reference.get$hasPort() ? reference.get$port(reference) : _null;
+        } else {
+          targetPort = _null;
+          targetHost = targetPort;
+          targetUserInfo = "";
+        }
+        targetPath = P._Uri__removeDotSegments(reference.get$path(reference));
+        targetQuery = reference.get$hasQuery() ? reference.get$query() : _null;
+      } else {
+        targetScheme = _this.scheme;
+        if (reference.get$hasAuthority()) {
+          targetUserInfo = reference.get$userInfo();
+          targetHost = reference.get$host(reference);
+          targetPort = P._Uri__makePort(reference.get$hasPort() ? reference.get$port(reference) : _null, targetScheme);
+          targetPath = P._Uri__removeDotSegments(reference.get$path(reference));
+          targetQuery = reference.get$hasQuery() ? reference.get$query() : _null;
+        } else {
+          targetUserInfo = _this._userInfo;
+          targetHost = _this._host;
+          targetPort = _this._port;
+          if (reference.get$path(reference) === "") {
+            targetPath = _this.path;
+            targetQuery = reference.get$hasQuery() ? reference.get$query() : _this._query;
+          } else {
+            if (reference.get$hasAbsolutePath())
+              targetPath = P._Uri__removeDotSegments(reference.get$path(reference));
+            else {
+              t1 = _this.path;
+              if (t1.length === 0)
+                if (targetHost == null)
+                  targetPath = targetScheme.length === 0 ? reference.get$path(reference) : P._Uri__removeDotSegments(reference.get$path(reference));
+                else
+                  targetPath = P._Uri__removeDotSegments("/" + reference.get$path(reference));
+              else {
+                mergedPath = _this._mergePaths$2(t1, reference.get$path(reference));
+                t2 = targetScheme.length === 0;
+                if (!t2 || targetHost != null || C.JSString_methods.startsWith$1(t1, "/"))
+                  targetPath = P._Uri__removeDotSegments(mergedPath);
+                else
+                  targetPath = P._Uri__normalizeRelativePath(mergedPath, !t2 || targetHost != null);
+              }
+            }
+            targetQuery = reference.get$hasQuery() ? reference.get$query() : _null;
+          }
+        }
+      }
+      return new P._Uri(targetScheme, targetUserInfo, targetHost, targetPort, targetPath, targetQuery, reference.get$hasFragment() ? reference.get$fragment() : _null);
+    },
+    get$hasAuthority: function() {
+      return this._host != null;
+    },
+    get$hasPort: function() {
+      return this._port != null;
+    },
+    get$hasQuery: function() {
+      return this._query != null;
+    },
+    get$hasFragment: function() {
+      return this._fragment != null;
+    },
+    get$hasAbsolutePath: function() {
+      return C.JSString_methods.startsWith$1(this.path, "/");
+    },
+    toFilePath$0: function() {
+      var windows, pathSegments, _this = this,
+        t1 = _this.scheme;
+      if (t1 !== "" && t1 !== "file")
+        throw H.wrapException(P.UnsupportedError$("Cannot extract a file path from a " + H.S(t1) + " URI"));
+      t1 = _this._query;
+      if ((t1 == null ? "" : t1) !== "")
+        throw H.wrapException(P.UnsupportedError$("Cannot extract a file path from a URI with a query component"));
+      t1 = _this._fragment;
+      if ((t1 == null ? "" : t1) !== "")
+        throw H.wrapException(P.UnsupportedError$("Cannot extract a file path from a URI with a fragment component"));
+      windows = $.$get$_Uri__isWindowsCached();
+      if (H.boolConversionCheck(windows))
+        t1 = P._Uri__toWindowsFilePath(_this);
+      else {
+        if (_this._host != null && _this.get$host(_this) !== "")
+          H.throwExpression(P.UnsupportedError$("Cannot extract a non-Windows file path from a file URI with an authority"));
+        pathSegments = _this.get$pathSegments();
+        P._Uri__checkNonWindowsPathReservedCharacters(pathSegments, false);
+        t1 = P.StringBuffer__writeAll(C.JSString_methods.startsWith$1(_this.path, "/") ? "/" : "", pathSegments, "/");
+        t1 = t1.charCodeAt(0) == 0 ? t1 : t1;
+      }
+      return t1;
+    },
+    toString$0: function(_) {
+      var t2, t3, t4, _this = this,
+        t1 = _this._text;
+      if (t1 == null) {
+        t1 = _this.scheme;
+        t2 = t1.length !== 0 ? t1 + ":" : "";
+        t3 = _this._host;
+        t4 = t3 == null;
+        if (!t4 || t1 === "file") {
+          t1 = t2 + "//";
+          t2 = _this._userInfo;
+          if (t2.length !== 0)
+            t1 = t1 + t2 + "@";
+          if (!t4)
+            t1 += t3;
+          t2 = _this._port;
+          if (t2 != null)
+            t1 = t1 + ":" + H.S(t2);
+        } else
+          t1 = t2;
+        t1 += _this.path;
+        t2 = _this._query;
+        if (t2 != null)
+          t1 = t1 + "?" + t2;
+        t2 = _this._fragment;
+        if (t2 != null)
+          t1 = t1 + "#" + t2;
+        t1 = _this._text = t1.charCodeAt(0) == 0 ? t1 : t1;
+      }
+      return t1;
+    },
+    $eq: function(_, other) {
+      var t1, t2, _this = this;
+      if (other == null)
+        return false;
+      if (_this === other)
+        return true;
+      if (type$.Uri._is(other))
+        if (_this.scheme == other.get$scheme())
+          if (_this._host != null === other.get$hasAuthority())
+            if (_this._userInfo == other.get$userInfo())
+              if (_this.get$host(_this) == other.get$host(other))
+                if (_this.get$port(_this) == other.get$port(other))
+                  if (_this.path === other.get$path(other)) {
+                    t1 = _this._query;
+                    t2 = t1 == null;
+                    if (!t2 === other.get$hasQuery()) {
+                      if (t2)
+                        t1 = "";
+                      if (t1 === other.get$query()) {
+                        t1 = _this._fragment;
+                        t2 = t1 == null;
+                        if (!t2 === other.get$hasFragment()) {
+                          if (t2)
+                            t1 = "";
+                          t1 = t1 === other.get$fragment();
+                        } else
+                          t1 = false;
+                      } else
+                        t1 = false;
+                    } else
+                      t1 = false;
+                  } else
+                    t1 = false;
+                else
+                  t1 = false;
+              else
+                t1 = false;
+            else
+              t1 = false;
+          else
+            t1 = false;
+        else
+          t1 = false;
+      else
+        t1 = false;
+      return t1;
+    },
+    get$hashCode: function(_) {
+      var t1 = this._hashCodeCache;
+      return t1 == null ? this._hashCodeCache = C.JSString_methods.get$hashCode(this.toString$0(0)) : t1;
+    },
+    set$_pathSegments: function(_pathSegments) {
+      this._pathSegments = type$.List_String._check(_pathSegments);
+    },
+    $isUri: 1,
+    get$scheme: function() {
+      return this.scheme;
+    },
+    get$path: function(receiver) {
+      return this.path;
+    }
+  };
+  P._Uri__Uri$notSimple_closure.prototype = {
+    call$1: function(_) {
+      throw H.wrapException(P.FormatException$("Invalid port", this.uri, this.portStart + 1));
+    },
+    $signature: 30
+  };
+  P._Uri__checkNonWindowsPathReservedCharacters_closure.prototype = {
+    call$1: function(segment) {
+      var _s23_ = "Illegal path character ";
+      H._checkStringNullable(segment);
+      if (J.contains$1$asx(segment, "/"))
+        if (this.argumentError)
+          throw H.wrapException(P.ArgumentError$(_s23_ + segment));
+        else
+          throw H.wrapException(P.UnsupportedError$(_s23_ + segment));
+    },
+    $signature: 30
+  };
+  P._Uri__makePath_closure.prototype = {
+    call$1: function(s) {
+      return P._Uri__uriEncode(C.List_qg40, H._checkStringNullable(s), C.C_Utf8Codec, false);
+    },
+    $signature: 7
+  };
+  P.UriData.prototype = {
+    get$uri: function() {
+      var t2, queryIndex, end, query, _this = this, _null = null,
+        t1 = _this._uriCache;
+      if (t1 != null)
+        return t1;
+      t1 = _this._separatorIndices;
+      if (0 >= t1.length)
+        return H.ioore(t1, 0);
+      t2 = _this._text;
+      t1 = t1[0] + 1;
+      queryIndex = C.JSString_methods.indexOf$2(t2, "?", t1);
+      end = t2.length;
+      if (queryIndex >= 0) {
+        query = P._Uri__normalizeOrSubstring(t2, queryIndex + 1, end, C.List_CVk, false);
+        end = queryIndex;
+      } else
+        query = _null;
+      return _this._uriCache = new P._DataUri("data", _null, _null, _null, P._Uri__normalizeOrSubstring(t2, t1, end, C.List_qg4, false), query, _null);
+    },
+    toString$0: function(_) {
+      var t2,
+        t1 = this._separatorIndices;
+      if (0 >= t1.length)
+        return H.ioore(t1, 0);
+      t2 = this._text;
+      return t1[0] === -1 ? "data:" + t2 : t2;
+    }
+  };
+  P._createTables_closure.prototype = {
+    call$1: function(_) {
+      return new Uint8Array(96);
+    },
+    $signature: 64
+  };
+  P._createTables_build.prototype = {
+    call$2: function(state, defaultTransition) {
+      var t1 = this.tables;
+      if (state >= t1.length)
+        return H.ioore(t1, state);
+      t1 = t1[state];
+      J.fillRange$3$ax(t1, 0, 96, defaultTransition);
+      return t1;
+    },
+    $signature: 62
+  };
+  P._createTables_setChars.prototype = {
+    call$3: function(target, chars, transition) {
+      var t1, t2, i, t3;
+      for (t1 = chars.length, t2 = target.length, i = 0; i < t1; ++i) {
+        t3 = C.JSString_methods._codeUnitAt$1(chars, i) ^ 96;
+        if (t3 >= t2)
+          return H.ioore(target, t3);
+        target[t3] = transition;
+      }
+    },
+    $signature: 41
+  };
+  P._createTables_setRange.prototype = {
+    call$3: function(target, range, transition) {
+      var i, n, t1, t2;
+      for (i = C.JSString_methods._codeUnitAt$1(range, 0), n = C.JSString_methods._codeUnitAt$1(range, 1), t1 = target.length; i <= n; ++i) {
+        t2 = (i ^ 96) >>> 0;
+        if (t2 >= t1)
+          return H.ioore(target, t2);
+        target[t2] = transition;
+      }
+    },
+    $signature: 41
+  };
+  P._SimpleUri.prototype = {
+    get$hasAuthority: function() {
+      return this._hostStart > 0;
+    },
+    get$hasPort: function() {
+      return this._hostStart > 0 && this._portStart + 1 < this._pathStart;
+    },
+    get$hasQuery: function() {
+      return this._queryStart < this._fragmentStart;
+    },
+    get$hasFragment: function() {
+      return this._fragmentStart < this._uri.length;
+    },
+    get$_isFile: function() {
+      return this._schemeEnd === 4 && C.JSString_methods.startsWith$1(this._uri, "file");
+    },
+    get$_isHttp: function() {
+      return this._schemeEnd === 4 && C.JSString_methods.startsWith$1(this._uri, "http");
+    },
+    get$_isHttps: function() {
+      return this._schemeEnd === 5 && C.JSString_methods.startsWith$1(this._uri, "https");
+    },
+    get$hasAbsolutePath: function() {
+      return C.JSString_methods.startsWith$2(this._uri, "/", this._pathStart);
+    },
+    get$scheme: function() {
+      var t2, _this = this,
+        _s7_ = "package",
+        t1 = _this._schemeEnd;
+      if (t1 <= 0)
+        return "";
+      t2 = _this._schemeCache;
+      if (t2 != null)
+        return t2;
+      if (_this.get$_isHttp())
+        t1 = _this._schemeCache = "http";
+      else if (_this.get$_isHttps()) {
+        _this._schemeCache = "https";
+        t1 = "https";
+      } else if (_this.get$_isFile()) {
+        _this._schemeCache = "file";
+        t1 = "file";
+      } else if (t1 === 7 && C.JSString_methods.startsWith$1(_this._uri, _s7_)) {
+        _this._schemeCache = _s7_;
+        t1 = _s7_;
+      } else {
+        t1 = C.JSString_methods.substring$2(_this._uri, 0, t1);
+        _this._schemeCache = t1;
+      }
+      return t1;
+    },
+    get$userInfo: function() {
+      var t1 = this._hostStart,
+        t2 = this._schemeEnd + 3;
+      return t1 > t2 ? C.JSString_methods.substring$2(this._uri, t2, t1 - 1) : "";
+    },
+    get$host: function(_) {
+      var t1 = this._hostStart;
+      return t1 > 0 ? C.JSString_methods.substring$2(this._uri, t1, this._portStart) : "";
+    },
+    get$port: function(_) {
+      var _this = this;
+      if (_this.get$hasPort())
+        return P.int_parse(C.JSString_methods.substring$2(_this._uri, _this._portStart + 1, _this._pathStart), null, null);
+      if (_this.get$_isHttp())
+        return 80;
+      if (_this.get$_isHttps())
+        return 443;
+      return 0;
+    },
+    get$path: function(_) {
+      return C.JSString_methods.substring$2(this._uri, this._pathStart, this._queryStart);
+    },
+    get$query: function() {
+      var t1 = this._queryStart,
+        t2 = this._fragmentStart;
+      return t1 < t2 ? C.JSString_methods.substring$2(this._uri, t1 + 1, t2) : "";
+    },
+    get$fragment: function() {
+      var t1 = this._fragmentStart,
+        t2 = this._uri;
+      return t1 < t2.length ? C.JSString_methods.substring$1(t2, t1 + 1) : "";
+    },
+    get$pathSegments: function() {
+      var parts, i,
+        start = this._pathStart,
+        end = this._queryStart,
+        t1 = this._uri;
+      if (C.JSString_methods.startsWith$2(t1, "/", start))
+        ++start;
+      if (start === end)
+        return C.List_empty;
+      parts = H.setRuntimeTypeInfo([], type$.JSArray_String);
+      for (i = start; i < end; ++i)
+        if (C.JSString_methods.codeUnitAt$1(t1, i) === 47) {
+          C.JSArray_methods.add$1(parts, C.JSString_methods.substring$2(t1, start, i));
+          start = i + 1;
+        }
+      C.JSArray_methods.add$1(parts, C.JSString_methods.substring$2(t1, start, end));
+      return P.List_List$unmodifiable(parts, type$.String);
+    },
+    _isPort$1: function(port) {
+      var portDigitStart = this._portStart + 1;
+      return portDigitStart + port.length === this._pathStart && C.JSString_methods.startsWith$2(this._uri, port, portDigitStart);
+    },
+    removeFragment$0: function() {
+      var _this = this,
+        t1 = _this._fragmentStart,
+        t2 = _this._uri;
+      if (t1 >= t2.length)
+        return _this;
+      return new P._SimpleUri(C.JSString_methods.substring$2(t2, 0, t1), _this._schemeEnd, _this._hostStart, _this._portStart, _this._pathStart, _this._queryStart, t1, _this._schemeCache);
+    },
+    replace$2$path$pathSegments: function(_, path, pathSegments) {
+      var scheme, isFile, t1, userInfo, port, host, hasAuthority, t2, query, fragment, _this = this, _null = null;
+      type$.Iterable_String._check(pathSegments);
+      type$.Map_String_dynamic._check(null);
+      scheme = _this.get$scheme();
+      isFile = scheme === "file";
+      t1 = _this._hostStart;
+      userInfo = t1 > 0 ? C.JSString_methods.substring$2(_this._uri, _this._schemeEnd + 3, t1) : "";
+      port = _this.get$hasPort() ? _this.get$port(_this) : _null;
+      t1 = _this._hostStart;
+      if (t1 > 0)
+        host = C.JSString_methods.substring$2(_this._uri, t1, _this._portStart);
+      else
+        host = userInfo.length !== 0 || port != null || isFile ? "" : _null;
+      hasAuthority = host != null;
+      t1 = path == null;
+      if (!t1 || pathSegments != null)
+        path = P._Uri__makePath(path, 0, t1 ? 0 : path.length, pathSegments, scheme, hasAuthority);
+      else {
+        path = C.JSString_methods.substring$2(_this._uri, _this._pathStart, _this._queryStart);
+        if (!isFile)
+          t1 = hasAuthority && path.length !== 0;
+        else
+          t1 = true;
+        if (t1 && !C.JSString_methods.startsWith$1(path, "/"))
+          path = "/" + path;
+      }
+      t1 = _this._queryStart;
+      t2 = _this._fragmentStart;
+      query = t1 < t2 ? C.JSString_methods.substring$2(_this._uri, t1 + 1, t2) : _null;
+      t1 = _this._fragmentStart;
+      t2 = _this._uri;
+      fragment = t1 < t2.length ? C.JSString_methods.substring$1(t2, t1 + 1) : _null;
+      return new P._Uri(scheme, userInfo, host, port, path, query, fragment);
+    },
+    replace$1$path: function($receiver, path) {
+      return this.replace$2$path$pathSegments($receiver, path, null);
+    },
+    replace$1$pathSegments: function($receiver, pathSegments) {
+      return this.replace$2$path$pathSegments($receiver, null, pathSegments);
+    },
+    resolve$1: function(reference) {
+      return this.resolveUri$1(P.Uri_parse(reference));
+    },
+    resolveUri$1: function(reference) {
+      if (reference instanceof P._SimpleUri)
+        return this._simpleMerge$2(this, reference);
+      return this._toNonSimple$0().resolveUri$1(reference);
+    },
+    _simpleMerge$2: function(base, ref) {
+      var t2, t3, isSimple, delta, refStart, baseStart, baseEnd, baseUri, baseStart0, backCount, refStart0, insert,
+        t1 = ref._schemeEnd;
+      if (t1 > 0)
+        return ref;
+      t2 = ref._hostStart;
+      if (t2 > 0) {
+        t3 = base._schemeEnd;
+        if (t3 <= 0)
+          return ref;
+        if (base.get$_isFile())
+          isSimple = ref._pathStart !== ref._queryStart;
+        else if (base.get$_isHttp())
+          isSimple = !ref._isPort$1("80");
+        else
+          isSimple = !base.get$_isHttps() || !ref._isPort$1("443");
+        if (isSimple) {
+          delta = t3 + 1;
+          return new P._SimpleUri(C.JSString_methods.substring$2(base._uri, 0, delta) + C.JSString_methods.substring$1(ref._uri, t1 + 1), t3, t2 + delta, ref._portStart + delta, ref._pathStart + delta, ref._queryStart + delta, ref._fragmentStart + delta, base._schemeCache);
+        } else
+          return this._toNonSimple$0().resolveUri$1(ref);
+      }
+      refStart = ref._pathStart;
+      t1 = ref._queryStart;
+      if (refStart === t1) {
+        t2 = ref._fragmentStart;
+        if (t1 < t2) {
+          t3 = base._queryStart;
+          delta = t3 - t1;
+          return new P._SimpleUri(C.JSString_methods.substring$2(base._uri, 0, t3) + C.JSString_methods.substring$1(ref._uri, t1), base._schemeEnd, base._hostStart, base._portStart, base._pathStart, t1 + delta, t2 + delta, base._schemeCache);
+        }
+        t1 = ref._uri;
+        if (t2 < t1.length) {
+          t3 = base._fragmentStart;
+          return new P._SimpleUri(C.JSString_methods.substring$2(base._uri, 0, t3) + C.JSString_methods.substring$1(t1, t2), base._schemeEnd, base._hostStart, base._portStart, base._pathStart, base._queryStart, t2 + (t3 - t2), base._schemeCache);
+        }
+        return base.removeFragment$0();
+      }
+      t2 = ref._uri;
+      if (C.JSString_methods.startsWith$2(t2, "/", refStart)) {
+        t3 = base._pathStart;
+        delta = t3 - refStart;
+        return new P._SimpleUri(C.JSString_methods.substring$2(base._uri, 0, t3) + C.JSString_methods.substring$1(t2, refStart), base._schemeEnd, base._hostStart, base._portStart, t3, t1 + delta, ref._fragmentStart + delta, base._schemeCache);
+      }
+      baseStart = base._pathStart;
+      baseEnd = base._queryStart;
+      if (baseStart === baseEnd && base._hostStart > 0) {
+        for (; C.JSString_methods.startsWith$2(t2, "../", refStart);)
+          refStart += 3;
+        delta = baseStart - refStart + 1;
+        return new P._SimpleUri(C.JSString_methods.substring$2(base._uri, 0, baseStart) + "/" + C.JSString_methods.substring$1(t2, refStart), base._schemeEnd, base._hostStart, base._portStart, baseStart, t1 + delta, ref._fragmentStart + delta, base._schemeCache);
+      }
+      baseUri = base._uri;
+      for (baseStart0 = baseStart; C.JSString_methods.startsWith$2(baseUri, "../", baseStart0);)
+        baseStart0 += 3;
+      backCount = 0;
+      while (true) {
+        refStart0 = refStart + 3;
+        if (!(refStart0 <= t1 && C.JSString_methods.startsWith$2(t2, "../", refStart)))
+          break;
+        ++backCount;
+        refStart = refStart0;
+      }
+      for (insert = ""; baseEnd > baseStart0;) {
+        --baseEnd;
+        if (C.JSString_methods.codeUnitAt$1(baseUri, baseEnd) === 47) {
+          if (backCount === 0) {
+            insert = "/";
+            break;
+          }
+          --backCount;
+          insert = "/";
+        }
+      }
+      if (baseEnd === baseStart0 && base._schemeEnd <= 0 && !C.JSString_methods.startsWith$2(baseUri, "/", baseStart)) {
+        refStart -= backCount * 3;
+        insert = "";
+      }
+      delta = baseEnd - refStart + insert.length;
+      return new P._SimpleUri(C.JSString_methods.substring$2(baseUri, 0, baseEnd) + insert + C.JSString_methods.substring$1(t2, refStart), base._schemeEnd, base._hostStart, base._portStart, baseStart, t1 + delta, ref._fragmentStart + delta, base._schemeCache);
+    },
+    toFilePath$0: function() {
+      var t1, t2, windows, _this = this;
+      if (_this._schemeEnd >= 0 && !_this.get$_isFile())
+        throw H.wrapException(P.UnsupportedError$("Cannot extract a file path from a " + H.S(_this.get$scheme()) + " URI"));
+      t1 = _this._queryStart;
+      t2 = _this._uri;
+      if (t1 < t2.length) {
+        if (t1 < _this._fragmentStart)
+          throw H.wrapException(P.UnsupportedError$("Cannot extract a file path from a URI with a query component"));
+        throw H.wrapException(P.UnsupportedError$("Cannot extract a file path from a URI with a fragment component"));
+      }
+      windows = $.$get$_Uri__isWindowsCached();
+      if (H.boolConversionCheck(windows))
+        t1 = P._Uri__toWindowsFilePath(_this);
+      else {
+        if (_this._hostStart < _this._portStart)
+          H.throwExpression(P.UnsupportedError$("Cannot extract a non-Windows file path from a file URI with an authority"));
+        t1 = C.JSString_methods.substring$2(t2, _this._pathStart, t1);
+      }
+      return t1;
+    },
+    get$hashCode: function(_) {
+      var t1 = this._hashCodeCache;
+      return t1 == null ? this._hashCodeCache = C.JSString_methods.get$hashCode(this._uri) : t1;
+    },
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      if (this === other)
+        return true;
+      return type$.Uri._is(other) && this._uri === other.toString$0(0);
+    },
+    _toNonSimple$0: function() {
+      var _this = this, _null = null,
+        t1 = _this.get$scheme(),
+        t2 = _this.get$userInfo(),
+        t3 = _this._hostStart > 0 ? _this.get$host(_this) : _null,
+        t4 = _this.get$hasPort() ? _this.get$port(_this) : _null,
+        t5 = _this._uri,
+        t6 = _this._queryStart,
+        t7 = C.JSString_methods.substring$2(t5, _this._pathStart, t6),
+        t8 = _this._fragmentStart;
+      t6 = t6 < t8 ? _this.get$query() : _null;
+      return new P._Uri(t1, t2, t3, t4, t7, t6, t8 < t5.length ? _this.get$fragment() : _null);
+    },
+    toString$0: function(_) {
+      return this._uri;
+    },
+    $isUri: 1
+  };
+  P._DataUri.prototype = {};
+  W.ApplicationCacheErrorEvent.prototype = {
+    get$message: function(receiver) {
+      return receiver.message;
+    }
+  };
+  W.Blob.prototype = {$isBlob: 1};
+  W.DomError.prototype = {
+    get$message: function(receiver) {
+      return receiver.message;
+    }
+  };
+  W.DomException.prototype = {
+    toString$0: function(receiver) {
+      return String(receiver);
+    },
+    get$message: function(receiver) {
+      return receiver.message;
+    }
+  };
+  W.ErrorEvent.prototype = {
+    get$message: function(receiver) {
+      return receiver.message;
+    }
+  };
+  W.Event.prototype = {$isEvent: 1};
+  W.EventTarget.prototype = {
+    addEventListener$3: function(receiver, type, listener, useCapture) {
+      type$.dynamic_Function_Event._check(listener);
+      if (listener != null)
+        this._addEventListener$3(receiver, type, listener, false);
+    },
+    _addEventListener$3: function(receiver, type, listener, options) {
+      return receiver.addEventListener(type, H.convertDartClosureToJS(type$.dynamic_Function_Event._check(listener), 1), false);
+    },
+    _removeEventListener$3: function(receiver, type, listener, options) {
+      return receiver.removeEventListener(type, H.convertDartClosureToJS(type$.dynamic_Function_Event._check(listener), 1), false);
+    },
+    $isEventTarget: 1
+  };
+  W.File.prototype = {$isFile: 1};
+  W.Location.prototype = {
+    get$origin: function(receiver) {
+      if ("origin" in receiver)
+        return receiver.origin;
+      return H.S(receiver.protocol) + "//" + H.S(receiver.host);
+    },
+    toString$0: function(receiver) {
+      return String(receiver);
+    }
+  };
+  W.MediaError.prototype = {
+    get$message: function(receiver) {
+      return receiver.message;
+    }
+  };
+  W.MediaKeyMessageEvent.prototype = {
+    get$message: function(receiver) {
+      return receiver.message;
+    }
+  };
+  W.MessageEvent.prototype = {$isMessageEvent: 1};
+  W.MessagePort.prototype = {
+    addEventListener$3: function(receiver, type, listener, useCapture) {
+      type$.dynamic_Function_Event._check(listener);
+      if (type === "message")
+        receiver.start();
+      this.super$EventTarget$addEventListener(receiver, type, listener, false);
+    },
+    postMessage$1: function(receiver, message) {
+      type$.List_Object._check(null);
+      receiver.postMessage(new P._StructuredCloneDart2Js([], []).walk$1(message));
+      return;
+    },
+    $isMessagePort: 1
+  };
+  W.NavigatorUserMediaError.prototype = {
+    get$message: function(receiver) {
+      return receiver.message;
+    }
+  };
+  W.OverconstrainedError.prototype = {
+    get$message: function(receiver) {
+      return receiver.message;
+    }
+  };
+  W.PositionError.prototype = {
+    get$message: function(receiver) {
+      return receiver.message;
+    }
+  };
+  W.PresentationConnectionCloseEvent.prototype = {
+    get$message: function(receiver) {
+      return receiver.message;
+    }
+  };
+  W.SpeechRecognitionError.prototype = {
+    get$message: function(receiver) {
+      return receiver.message;
+    }
+  };
+  W.EventStreamProvider.prototype = {};
+  W._EventStream.prototype = {
+    get$isBroadcast: function() {
+      return true;
+    },
+    listen$4$cancelOnError$onDone$onError: function(onData, cancelOnError, onDone, onError) {
+      var t1 = this.$ti;
+      t1._eval$1("~(1)")._check(onData);
+      type$.void_Function._check(onDone);
+      H._checkBoolNullable(cancelOnError);
+      return W._EventStreamSubscription$(this._html$_target, this._eventType, onData, false, t1._precomputed1);
+    },
+    listen$3$onDone$onError: function(onData, onDone, onError) {
+      return this.listen$4$cancelOnError$onDone$onError(onData, null, onDone, onError);
+    },
+    listen$1: function(onData) {
+      return this.listen$4$cancelOnError$onDone$onError(onData, null, null, null);
+    }
+  };
+  W._EventStreamSubscription.prototype = {
+    cancel$0: function() {
+      var _this = this;
+      if (_this._html$_target == null)
+        return null;
+      _this._unlisten$0();
+      _this._html$_target = null;
+      _this.set$_html$_onData(null);
+      return null;
+    },
+    pause$1: function(resumeSignal) {
+      if (this._html$_target == null)
+        return;
+      ++this._pauseCount;
+      this._unlisten$0();
+    },
+    pause$0: function() {
+      return this.pause$1(null);
+    },
+    resume$0: function() {
+      var _this = this;
+      if (_this._html$_target == null || _this._pauseCount <= 0)
+        return;
+      --_this._pauseCount;
+      _this._tryResume$0();
+    },
+    _tryResume$0: function() {
+      var _this = this,
+        t1 = _this._html$_onData;
+      if (t1 != null && _this._pauseCount <= 0)
+        J.addEventListener$3$x(_this._html$_target, _this._eventType, t1, false);
+    },
+    _unlisten$0: function() {
+      var t3,
+        t1 = this._html$_onData,
+        t2 = t1 != null;
+      if (t2) {
+        t3 = this._html$_target;
+        t3.toString;
+        type$.dynamic_Function_Event._check(t1);
+        if (t2)
+          J._removeEventListener$3$x(t3, this._eventType, t1, false);
+      }
+    },
+    set$_html$_onData: function(_onData) {
+      this._html$_onData = type$.dynamic_Function_Event._check(_onData);
+    }
+  };
+  W._EventStreamSubscription_closure.prototype = {
+    call$1: function(e) {
+      return this.onData.call$1(type$.Event._check(e));
+    },
+    $signature: 61
+  };
+  P._StructuredClone.prototype = {
+    findSlot$1: function(value) {
+      var i,
+        t1 = this.values,
+        $length = t1.length;
+      for (i = 0; i < $length; ++i)
+        if (t1[i] === value)
+          return i;
+      C.JSArray_methods.add$1(t1, value);
+      C.JSArray_methods.add$1(this.copies, null);
+      return $length;
+    },
+    walk$1: function(e) {
+      var slot, t2, copy, _this = this, t1 = {};
+      if (e == null)
+        return e;
+      if (H._isBool(e))
+        return e;
+      if (typeof e == "number")
+        return e;
+      if (typeof e == "string")
+        return e;
+      if (e instanceof P.DateTime)
+        return new Date(e._value);
+      if (type$.RegExp._is(e))
+        throw H.wrapException(P.UnimplementedError$("structured clone of RegExp"));
+      if (type$.File._is(e))
+        return e;
+      if (type$.Blob._is(e))
+        return e;
+      if (type$.NativeByteBuffer._is(e) || type$.NativeTypedData._is(e) || type$.MessagePort._is(e))
+        return e;
+      if (type$.Map_dynamic_dynamic._is(e)) {
+        slot = _this.findSlot$1(e);
+        t2 = _this.copies;
+        if (slot >= t2.length)
+          return H.ioore(t2, slot);
+        copy = t1.copy = t2[slot];
+        if (copy != null)
+          return copy;
+        copy = {};
+        t1.copy = copy;
+        C.JSArray_methods.$indexSet(t2, slot, copy);
+        e.forEach$1(0, new P._StructuredClone_walk_closure(t1, _this));
+        return t1.copy;
+      }
+      if (type$.List_dynamic._is(e)) {
+        slot = _this.findSlot$1(e);
+        t1 = _this.copies;
+        if (slot >= t1.length)
+          return H.ioore(t1, slot);
+        copy = t1[slot];
+        if (copy != null)
+          return copy;
+        return _this.copyList$2(e, slot);
+      }
+      if (type$.JSObject._is(e)) {
+        slot = _this.findSlot$1(e);
+        t2 = _this.copies;
+        if (slot >= t2.length)
+          return H.ioore(t2, slot);
+        copy = t1.copy = t2[slot];
+        if (copy != null)
+          return copy;
+        copy = {};
+        t1.copy = copy;
+        C.JSArray_methods.$indexSet(t2, slot, copy);
+        _this.forEachObjectKey$2(e, new P._StructuredClone_walk_closure0(t1, _this));
+        return t1.copy;
+      }
+      throw H.wrapException(P.UnimplementedError$("structured clone of other type"));
+    },
+    copyList$2: function(e, slot) {
+      var i,
+        t1 = J.getInterceptor$asx(e),
+        $length = t1.get$length(e),
+        copy = new Array($length);
+      C.JSArray_methods.$indexSet(this.copies, slot, copy);
+      for (i = 0; i < $length; ++i)
+        C.JSArray_methods.$indexSet(copy, i, this.walk$1(t1.$index(e, i)));
+      return copy;
+    }
+  };
+  P._StructuredClone_walk_closure.prototype = {
+    call$2: function(key, value) {
+      this._box_0.copy[key] = this.$this.walk$1(value);
+    },
+    $signature: 6
+  };
+  P._StructuredClone_walk_closure0.prototype = {
+    call$2: function(key, value) {
+      this._box_0.copy[key] = this.$this.walk$1(value);
+    },
+    $signature: 6
+  };
+  P._AcceptStructuredClone.prototype = {
+    findSlot$1: function(value) {
+      var i,
+        t1 = this.values,
+        $length = t1.length;
+      for (i = 0; i < $length; ++i)
+        if (t1[i] === value)
+          return i;
+      C.JSArray_methods.add$1(t1, value);
+      C.JSArray_methods.add$1(this.copies, null);
+      return $length;
+    },
+    walk$1: function(e) {
+      var millisSinceEpoch, t1, proto, slot, copy, t2, l, $length, i, _this = this, _box_0 = {};
+      if (e == null)
+        return e;
+      if (H._isBool(e))
+        return e;
+      if (typeof e == "number")
+        return e;
+      if (typeof e == "string")
+        return e;
+      if (e instanceof Date) {
+        millisSinceEpoch = e.getTime();
+        if (Math.abs(millisSinceEpoch) <= 864e13)
+          t1 = false;
+        else
+          t1 = true;
+        if (t1)
+          H.throwExpression(P.ArgumentError$("DateTime is outside valid range: " + millisSinceEpoch));
+        return new P.DateTime(millisSinceEpoch, true);
+      }
+      if (e instanceof RegExp)
+        throw H.wrapException(P.UnimplementedError$("structured clone of RegExp"));
+      if (typeof Promise != "undefined" && e instanceof Promise)
+        return P.promiseToFuture(e, type$.dynamic);
+      proto = Object.getPrototypeOf(e);
+      if (proto === Object.prototype || proto === null) {
+        slot = _this.findSlot$1(e);
+        t1 = _this.copies;
+        if (slot >= t1.length)
+          return H.ioore(t1, slot);
+        copy = _box_0.copy = t1[slot];
+        if (copy != null)
+          return copy;
+        t2 = type$.dynamic;
+        copy = P.LinkedHashMap_LinkedHashMap$_empty(t2, t2);
+        _box_0.copy = copy;
+        C.JSArray_methods.$indexSet(t1, slot, copy);
+        _this.forEachJsField$2(e, new P._AcceptStructuredClone_walk_closure(_box_0, _this));
+        return _box_0.copy;
+      }
+      if (e instanceof Array) {
+        l = e;
+        slot = _this.findSlot$1(l);
+        t1 = _this.copies;
+        if (slot >= t1.length)
+          return H.ioore(t1, slot);
+        copy = t1[slot];
+        if (copy != null)
+          return copy;
+        t2 = J.getInterceptor$asx(l);
+        $length = t2.get$length(l);
+        copy = _this.mustCopy ? new Array($length) : l;
+        C.JSArray_methods.$indexSet(t1, slot, copy);
+        for (t1 = J.getInterceptor$ax(copy), i = 0; i < $length; ++i)
+          t1.$indexSet(copy, i, _this.walk$1(t2.$index(l, i)));
+        return copy;
+      }
+      return e;
+    },
+    convertNativeToDart_AcceptStructuredClone$2$mustCopy: function(object, mustCopy) {
+      this.mustCopy = true;
+      return this.walk$1(object);
+    }
+  };
+  P._AcceptStructuredClone_walk_closure.prototype = {
+    call$2: function(key, value) {
+      var t1 = this._box_0.copy,
+        t2 = this.$this.walk$1(value);
+      J.$indexSet$ax(t1, key, t2);
+      return t2;
+    },
+    $signature: 60
+  };
+  P._StructuredCloneDart2Js.prototype = {
+    forEachObjectKey$2: function(object, action) {
+      var t1, t2, _i, key;
+      type$.dynamic_Function_dynamic_dynamic._check(action);
+      for (t1 = Object.keys(object), t2 = t1.length, _i = 0; _i < t2; ++_i) {
+        key = t1[_i];
+        action.call$2(key, object[key]);
+      }
+    }
+  };
+  P._AcceptStructuredCloneDart2Js.prototype = {
+    forEachJsField$2: function(object, action) {
+      var t1, t2, _i, key;
+      type$.dynamic_Function_dynamic_dynamic._check(action);
+      for (t1 = Object.keys(object), t2 = t1.length, _i = 0; _i < t1.length; t1.length === t2 || (0, H.throwConcurrentModificationError)(t1), ++_i) {
+        key = t1[_i];
+        action.call$2(key, object[key]);
+      }
+    }
+  };
+  P._convertDataTree__convert.prototype = {
+    call$1: function(o) {
+      var convertedMap, key, convertedList,
+        t1 = this._convertedObjects;
+      if (t1.containsKey$1(o))
+        return t1.$index(0, o);
+      if (type$.Map_dynamic_dynamic._is(o)) {
+        convertedMap = {};
+        t1.$indexSet(0, o, convertedMap);
+        for (t1 = o.get$keys(), t1 = t1.get$iterator(t1); t1.moveNext$0();) {
+          key = t1.get$current();
+          convertedMap[key] = this.call$1(o.$index(0, key));
+        }
+        return convertedMap;
+      } else if (type$.Iterable_dynamic._is(o)) {
+        convertedList = [];
+        t1.$indexSet(0, o, convertedList);
+        C.JSArray_methods.addAll$1(convertedList, J.map$1$1$ax(o, this, type$.dynamic));
+        return convertedList;
+      } else
+        return o;
+    },
+    $signature: 18
+  };
+  P.promiseToFuture_closure.prototype = {
+    call$1: function(r) {
+      return this.completer.complete$1(this.T._eval$1("0/")._check(r));
+    },
+    $signature: 15
+  };
+  P.promiseToFuture_closure0.prototype = {
+    call$1: function(e) {
+      return this.completer.completeError$1(e);
+    },
+    $signature: 15
+  };
+  P.ByteBuffer.prototype = {};
+  P.ByteData.prototype = {};
+  P.Int8List.prototype = {$isEfficientLengthIterable: 1, $isIterable: 1, $isList: 1};
+  P.Uint8List.prototype = {$isEfficientLengthIterable: 1, $isIterable: 1, $isList: 1};
+  P.Uint8ClampedList.prototype = {$isEfficientLengthIterable: 1, $isIterable: 1, $isList: 1};
+  P.Int16List.prototype = {$isEfficientLengthIterable: 1, $isIterable: 1, $isList: 1};
+  P.Uint16List.prototype = {$isEfficientLengthIterable: 1, $isIterable: 1, $isList: 1};
+  P.Int32List.prototype = {$isEfficientLengthIterable: 1, $isIterable: 1, $isList: 1};
+  P.Uint32List.prototype = {$isEfficientLengthIterable: 1, $isIterable: 1, $isList: 1};
+  P.Float32List.prototype = {$isEfficientLengthIterable: 1, $isIterable: 1, $isList: 1};
+  P.Float64List.prototype = {$isEfficientLengthIterable: 1, $isIterable: 1, $isList: 1};
+  P.SqlError.prototype = {
+    get$message: function(receiver) {
+      return receiver.message;
+    }
+  };
+  S.AsyncMemoizer.prototype = {
+    runOnce$1: function(computation) {
+      var t2, t3,
+        t1 = this.$ti;
+      t1._eval$1("1/()")._check(computation);
+      t2 = this._async_memoizer$_completer;
+      t3 = t2.future;
+      if (t3._state === 0)
+        t2.complete$1(P.Future_Future$sync(computation, t1._precomputed1));
+      return t3;
+    }
+  };
+  O.DelegatingSink.prototype = {$isSink: 1};
+  Y.DelegatingStreamSubscription.prototype = {
+    onData$1: function(handleData) {
+      this._stream_subscription$_source.onData$1(this.$ti._eval$1("~(1)")._check(handleData));
+    },
+    onError$1: function(_, handleError) {
+      this._stream_subscription$_source.onError$1(0, handleError);
+    },
+    onDone$1: function(handleDone) {
+      this._stream_subscription$_source.onDone$1(type$.void_Function._check(handleDone));
+    },
+    pause$1: function(resumeFuture) {
+      this._stream_subscription$_source.pause$1(resumeFuture);
+    },
+    pause$0: function() {
+      return this.pause$1(null);
+    },
+    resume$0: function() {
+      this._stream_subscription$_source.resume$0();
+    },
+    cancel$0: function() {
+      return this._stream_subscription$_source.cancel$0();
+    },
+    $isStreamSubscription: 1
+  };
+  F.FutureGroup.prototype = {
+    add$1: function(_, task) {
+      var t1, index, _this = this;
+      _this.$ti._eval$1("Future<1>")._check(task);
+      if (_this._future_group$_closed)
+        throw H.wrapException(P.StateError$("The FutureGroup is closed."));
+      t1 = _this._values;
+      index = t1.length;
+      C.JSArray_methods.add$1(t1, null);
+      ++_this._future_group$_pending;
+      task.then$1$1(new F.FutureGroup_add_closure(_this, index), type$.Null).catchError$1(new F.FutureGroup_add_closure0(_this));
+    },
+    close$0: function(_) {
+      var t1, _this = this;
+      _this._future_group$_closed = true;
+      if (_this._future_group$_pending !== 0)
+        return;
+      t1 = _this._future_group$_completer;
+      if (t1.future._state !== 0)
+        return;
+      t1.complete$1(_this._values);
+    },
+    $isSink: 1
+  };
+  F.FutureGroup_add_closure.prototype = {
+    call$1: function(value) {
+      var t2, t3,
+        t1 = this.$this;
+      t1.$ti._precomputed1._check(value);
+      t2 = t1._future_group$_completer;
+      if (t2.future._state !== 0)
+        return null;
+      --t1._future_group$_pending;
+      t3 = t1._values;
+      C.JSArray_methods.$indexSet(t3, this.index, value);
+      if (t1._future_group$_pending !== 0)
+        return null;
+      if (!t1._future_group$_closed)
+        return null;
+      t2.complete$1(t3);
+    },
+    $signature: function() {
+      return this.$this.$ti._eval$1("Null(1)");
+    }
+  };
+  F.FutureGroup_add_closure0.prototype = {
+    call$2: function(error, stackTrace) {
+      var t1 = this.$this._future_group$_completer;
+      if (t1.future._state !== 0)
+        return null;
+      t1.completeError$2(error, type$.StackTrace._check(stackTrace));
+    },
+    $signature: 6
+  };
+  S.NullStreamSink.prototype = {
+    add$1: function(_, data) {
+      this.$ti._precomputed1._check(data);
+      this._checkEventAllowed$0();
+    },
+    addStream$1: function(stream) {
+      var future, _this = this;
+      _this.$ti._eval$1("Stream<1>")._check(stream);
+      _this._checkEventAllowed$0();
+      _this._addingStream = true;
+      future = stream.listen$1(null).cancel$0();
+      if (future == null) {
+        future = new P._Future($.Zone__current, type$._Future_dynamic);
+        future._asyncComplete$1(null);
+      }
+      return future.whenComplete$1(new S.NullStreamSink_addStream_closure(_this));
+    },
+    _checkEventAllowed$0: function() {
+      if (this._null_stream_sink$_closed)
+        throw H.wrapException(P.StateError$("Cannot add to a closed sink."));
+      if (this._addingStream)
+        throw H.wrapException(P.StateError$("Cannot add to a sink while adding a stream."));
+    },
+    close$0: function(_) {
+      this._null_stream_sink$_closed = true;
+      return this.done;
+    },
+    $isEventSink: 1,
+    $isStreamConsumer: 1,
+    $isStreamSink: 1,
+    $isSink: 1,
+    get$done: function() {
+      return this.done;
+    }
+  };
+  S.NullStreamSink_addStream_closure.prototype = {
+    call$0: function() {
+      this.$this._addingStream = false;
+    },
+    $signature: 0
+  };
+  V.ErrorResult.prototype = {
+    complete$1: function(completer) {
+      completer.completeError$2(this.error, this.stackTrace);
+    },
+    addTo$1: function(sink) {
+      sink.addError$2(this.error, this.stackTrace);
+    },
+    get$hashCode: function(_) {
+      return (J.get$hashCode$(this.error) ^ J.get$hashCode$(this.stackTrace) ^ 492929599) >>> 0;
+    },
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      return other instanceof V.ErrorResult && J.$eq$(this.error, other.error) && this.stackTrace == other.stackTrace;
+    },
+    $isResult: 1
+  };
+  E.Result.prototype = {};
+  F.ValueResult.prototype = {
+    complete$1: function(completer) {
+      this.$ti._eval$1("Completer<1>")._check(completer).complete$1(this.value);
+    },
+    addTo$1: function(sink) {
+      this.$ti._eval$1("EventSink<1>")._check(sink).add$1(0, this.value);
+    },
+    get$hashCode: function(_) {
+      return (J.get$hashCode$(this.value) ^ 842997089) >>> 0;
+    },
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      return other instanceof F.ValueResult && J.$eq$(this.value, other.value);
+    },
+    $isResult: 1
+  };
+  Y.StreamCompleter.prototype = {
+    setSourceStream$1: function(sourceStream) {
+      var t1;
+      this.$ti._eval$1("Stream<1>")._check(sourceStream);
+      t1 = this._stream;
+      if (t1._sourceStream != null)
+        throw H.wrapException(P.StateError$("Source stream already set"));
+      t1.set$_sourceStream(t1.$ti._eval$1("Stream<1>")._check(sourceStream));
+      if (t1._stream_completer$_controller != null)
+        t1._linkStreamToController$0();
+    }
+  };
+  Y._CompleterStream.prototype = {
+    listen$4$cancelOnError$onDone$onError: function(onData, cancelOnError, onDone, onError) {
+      var t1, _this = this;
+      _this.$ti._eval$1("@(1)")._check(onData);
+      type$.void_Function._check(onDone);
+      H._checkBoolNullable(cancelOnError);
+      if (_this._stream_completer$_controller == null) {
+        t1 = _this._sourceStream;
+        if (t1 != null && !t1.get$isBroadcast())
+          return _this._sourceStream.listen$4$cancelOnError$onDone$onError(onData, cancelOnError, onDone, onError);
+        _this._createController$0();
+        if (_this._sourceStream != null)
+          _this._linkStreamToController$0();
+      }
+      t1 = _this._stream_completer$_controller;
+      t1.toString;
+      return new P._ControllerStream(t1, H._instanceType(t1)._eval$1("_ControllerStream<1>")).listen$4$cancelOnError$onDone$onError(onData, cancelOnError, onDone, onError);
+    },
+    listen$3$onDone$onError: function(onData, onDone, onError) {
+      return this.listen$4$cancelOnError$onDone$onError(onData, null, onDone, onError);
+    },
+    listen$1: function(onData) {
+      return this.listen$4$cancelOnError$onDone$onError(onData, null, null, null);
+    },
+    _linkStreamToController$0: function() {
+      var t1, t2, _this = this;
+      H.assertHelper(_this._stream_completer$_controller != null);
+      H.assertHelper(_this._sourceStream != null);
+      t1 = _this._stream_completer$_controller.addStream$2$cancelOnError(_this._sourceStream, false);
+      t2 = _this._stream_completer$_controller;
+      t1.whenComplete$1(t2.get$close(t2));
+    },
+    _createController$0: function() {
+      H.assertHelper(this._stream_completer$_controller == null);
+      this.set$_stream_completer$_controller(P.StreamController_StreamController(null, null, true, this.$ti._precomputed1));
+    },
+    set$_stream_completer$_controller: function(_controller) {
+      this._stream_completer$_controller = this.$ti._eval$1("StreamController<1>")._check(_controller);
+    },
+    set$_sourceStream: function(_sourceStream) {
+      this._sourceStream = this.$ti._eval$1("Stream<1>")._check(_sourceStream);
+    }
+  };
+  L.StreamGroup.prototype = {
+    add$1: function(_, stream) {
+      var t1, _this = this;
+      _this.$ti._eval$1("Stream<1>")._check(stream);
+      if (_this._stream_group$_closed)
+        throw H.wrapException(P.StateError$("Can't add a Stream to a closed StreamGroup."));
+      t1 = _this._stream_group$_state;
+      if (t1 === C._StreamGroupState_dormant)
+        _this._stream_group$_subscriptions.putIfAbsent$2(stream, new L.StreamGroup_add_closure());
+      else if (t1 === C._StreamGroupState_canceled)
+        return stream.listen$1(null).cancel$0();
+      else
+        _this._stream_group$_subscriptions.putIfAbsent$2(stream, new L.StreamGroup_add_closure0(_this, stream));
+      return null;
+    },
+    _onListen$0: function() {
+      this._stream_group$_state = C._StreamGroupState_listening;
+      this._stream_group$_subscriptions.forEach$1(0, new L.StreamGroup__onListen_closure(this));
+    },
+    _onCancelBroadcast$0: function() {
+      this._stream_group$_state = C._StreamGroupState_dormant;
+      this._stream_group$_subscriptions.forEach$1(0, new L.StreamGroup__onCancelBroadcast_closure(this));
+    },
+    _listenToStream$1: function(stream) {
+      var t1, subscription, _this = this;
+      _this.$ti._eval$1("Stream<1>")._check(stream);
+      t1 = _this._stream_group$_controller;
+      subscription = stream.listen$3$onDone$onError(t1.get$add(t1), new L.StreamGroup__listenToStream_closure(_this, stream), t1.get$addError());
+      if (_this._stream_group$_state === C._StreamGroupState_paused)
+        subscription.pause$0();
+      return subscription;
+    },
+    close$0: function(_) {
+      var t1, _this = this;
+      if (_this._stream_group$_closed)
+        return _this._stream_group$_controller._ensureDoneFuture$0();
+      _this._stream_group$_closed = true;
+      t1 = _this._stream_group$_subscriptions;
+      if (t1.get$isEmpty(t1))
+        _this._stream_group$_controller.close$0(0);
+      return _this._stream_group$_controller._ensureDoneFuture$0();
+    },
+    set$_stream_group$_controller: function(_controller) {
+      this._stream_group$_controller = this.$ti._eval$1("StreamController<1>")._check(_controller);
+    },
+    $isSink: 1
+  };
+  L.StreamGroup_add_closure.prototype = {
+    call$0: function() {
+      return null;
+    },
+    $signature: 0
+  };
+  L.StreamGroup_add_closure0.prototype = {
+    call$0: function() {
+      return this.$this._listenToStream$1(this.stream);
+    },
+    $signature: function() {
+      return this.$this.$ti._eval$1("StreamSubscription<1>()");
+    }
+  };
+  L.StreamGroup__onListen_closure.prototype = {
+    call$2: function(stream, subscription) {
+      var t1 = this.$this,
+        t2 = t1.$ti;
+      t2._eval$1("Stream<1>")._check(stream);
+      if (t2._eval$1("StreamSubscription<1>")._check(subscription) != null)
+        return;
+      t1._stream_group$_subscriptions.$indexSet(0, stream, t1._listenToStream$1(stream));
+    },
+    $signature: function() {
+      return this.$this.$ti._eval$1("Null(Stream<1>,StreamSubscription<1>)");
+    }
+  };
+  L.StreamGroup__onCancelBroadcast_closure.prototype = {
+    call$2: function(stream, subscription) {
+      var t1 = this.$this,
+        t2 = t1.$ti;
+      t2._eval$1("Stream<1>")._check(stream);
+      t2._eval$1("StreamSubscription<1>")._check(subscription);
+      if (!stream.get$isBroadcast())
+        return;
+      subscription.cancel$0();
+      t1._stream_group$_subscriptions.$indexSet(0, stream, null);
+    },
+    $signature: function() {
+      return this.$this.$ti._eval$1("Null(Stream<1>,StreamSubscription<1>)");
+    }
+  };
+  L.StreamGroup__listenToStream_closure.prototype = {
+    call$0: function() {
+      var t1 = this.$this,
+        t2 = t1._stream_group$_subscriptions,
+        subscription = t2.remove$1(0, t1.$ti._eval$1("Stream<1>")._check(this.stream)),
+        future = subscription == null ? null : subscription.cancel$0();
+      if (t1._stream_group$_closed && t2.get$isEmpty(t2))
+        t1._stream_group$_controller.close$0(0);
+      return future;
+    },
+    $signature: 14
+  };
+  L._StreamGroupState.prototype = {
+    toString$0: function(_) {
+      return this.name;
+    }
+  };
+  G.StreamQueue.prototype = {
+    get$next: function() {
+      var t1, t2, _this = this;
+      if (!_this._isClosed) {
+        t1 = _this.$ti;
+        t2 = new P._Future($.Zone__current, t1._eval$1("_Future<1>"));
+        _this._addRequest$1(new G._NextRequest(new P._AsyncCompleter(t2, t1._eval$1("_AsyncCompleter<1>")), t1._eval$1("_NextRequest<1>")));
+        return t2;
+      }
+      throw H.wrapException(_this._failClosed$0());
+    },
+    _updateRequests$0: function() {
+      var t1, t2, t3, t4, _this = this;
+      for (t1 = _this._requestQueue, t2 = _this._eventQueue; !t1.get$isEmpty(t1);) {
+        t3 = t1._head;
+        if (t3 === t1._tail)
+          H.throwExpression(H.IterableElementError_noElement());
+        t4 = t1._table;
+        if (t3 >= t4.length)
+          return H.ioore(t4, t3);
+        if (t4[t3].update$2(t2, _this._isDone))
+          t1.removeFirst$0();
+        else
+          return;
+      }
+      if (!_this._isDone)
+        _this._stream_queue$_subscription.pause$0();
+    },
+    _extractStream$0: function() {
+      var t1, wasPaused, _this = this, _null = null;
+      H.assertHelper(_this._isClosed);
+      if (_this._isDone)
+        return new P._EmptyStream(_this.$ti._eval$1("_EmptyStream<1>"));
+      _this._isDone = true;
+      t1 = _this._stream_queue$_subscription;
+      if (t1 == null)
+        return _this._stream_queue$_source;
+      _this.set$_stream_queue$_subscription(_null);
+      wasPaused = t1.get$isPaused();
+      t1.pause$0();
+      t1.onData$1(_null);
+      t1.onError$1(0, _null);
+      t1.onDone$1(_null);
+      if (wasPaused)
+        t1.resume$0();
+      return new T.SubscriptionStream(t1, _this.$ti._eval$1("SubscriptionStream<1>"));
+    },
+    _ensureListening$0: function() {
+      var t1, _this = this;
+      if (_this._isDone)
+        return;
+      t1 = _this._stream_queue$_subscription;
+      if (t1 == null)
+        _this.set$_stream_queue$_subscription(_this._stream_queue$_source.listen$3$onDone$onError(new G.StreamQueue__ensureListening_closure(_this), new G.StreamQueue__ensureListening_closure0(_this), new G.StreamQueue__ensureListening_closure1(_this)));
+      else
+        t1.resume$0();
+    },
+    _addResult$1: function(result) {
+      var t1, _this = this;
+      _this.$ti._eval$1("Result<1>")._check(result);
+      ++_this._eventsReceived;
+      t1 = _this._eventQueue;
+      t1._queue_list$_add$1(t1.$ti._precomputed1._check(result));
+      _this._updateRequests$0();
+    },
+    _failClosed$0: function() {
+      return new P.StateError("Already cancelled");
+    },
+    _addRequest$1: function(request) {
+      var t1, _this = this;
+      _this.$ti._eval$1("_EventRequest<1>")._check(request);
+      t1 = _this._requestQueue;
+      if (t1._head === t1._tail) {
+        if (request.update$2(_this._eventQueue, _this._isDone))
+          return;
+        _this._ensureListening$0();
+      }
+      t1._collection$_add$1(t1.$ti._precomputed1._check(request));
+    },
+    set$_stream_queue$_subscription: function(_subscription) {
+      this._stream_queue$_subscription = this.$ti._eval$1("StreamSubscription<1>")._check(_subscription);
+    }
+  };
+  G.StreamQueue__ensureListening_closure.prototype = {
+    call$1: function(data) {
+      var t1 = this.$this,
+        t2 = t1.$ti;
+      t1._addResult$1(new F.ValueResult(t2._precomputed1._check(data), t2._eval$1("ValueResult<1>")));
+    },
+    $signature: function() {
+      return this.$this.$ti._eval$1("Null(1)");
+    }
+  };
+  G.StreamQueue__ensureListening_closure1.prototype = {
+    call$2: function(error, stackTrace) {
+      this.$this._addResult$1(new V.ErrorResult(error, type$.StackTrace._check(stackTrace)));
+    },
+    $signature: 5
+  };
+  G.StreamQueue__ensureListening_closure0.prototype = {
+    call$0: function() {
+      var t1 = this.$this;
+      t1.set$_stream_queue$_subscription(null);
+      t1._isDone = true;
+      t1._updateRequests$0();
+    },
+    $signature: 0
+  };
+  G._EventRequest.prototype = {};
+  G._NextRequest.prototype = {
+    update$2: function(events, isDone) {
+      this.$ti._eval$1("QueueList<Result<1>>")._check(events);
+      if (events.get$length(events) !== 0) {
+        events.removeFirst$0().complete$1(this._completer);
+        return true;
+      }
+      if (isDone) {
+        this._completer.completeError$2(new P.StateError("No elements"), P.StackTrace_current());
+        return true;
+      }
+      return false;
+    },
+    $is_EventRequest: 1
+  };
+  G._RestRequest.prototype = {
+    update$2: function(events, isDone) {
+      var t2, controller, _this = this,
+        t1 = _this.$ti;
+      t1._eval$1("QueueList<Result<1>>")._check(events);
+      if (events.get$length(events) === 0) {
+        t1 = _this._streamQueue;
+        t2 = _this._completer;
+        if (t1._isDone) {
+          t1 = t2._stream;
+          t2 = t1._sourceStream == null;
+          if (!t2)
+            H.throwExpression(P.StateError$("Source stream already set"));
+          H.assertHelper(t2);
+          if (t1._stream_completer$_controller == null)
+            t1._createController$0();
+          t2 = t1._stream_completer$_controller;
+          t2.toString;
+          t1.set$_sourceStream(new P._ControllerStream(t2, H._instanceType(t2)._eval$1("_ControllerStream<1>")));
+          t1._stream_completer$_controller.close$0(0);
+        } else
+          t2.setSourceStream$1(t1._extractStream$0());
+      } else {
+        controller = P.StreamController_StreamController(null, null, false, t1._precomputed1);
+        for (t1 = new H.ListIterator(events, events.get$length(events), events.$ti._eval$1("ListIterator<ListMixin.E>")); t1.moveNext$0();)
+          t1.__internal$_current.addTo$1(controller);
+        controller.addStream$2$cancelOnError(_this._streamQueue._extractStream$0(), false).whenComplete$1(controller.get$close(controller));
+        _this._completer.setSourceStream$1(new P._ControllerStream(controller, H._instanceType(controller)._eval$1("_ControllerStream<1>")));
+      }
+      return true;
+    },
+    $is_EventRequest: 1
+  };
+  T.StreamSinkCompleter.prototype = {};
+  T._CompleterSink.prototype = {
+    get$_canSendDirectly: function() {
+      return this._stream_sink_completer$_controller == null && this._destinationSink != null;
+    },
+    get$done: function() {
+      var t1 = this._stream_sink_completer$_doneCompleter;
+      if (t1 != null)
+        return t1.future;
+      t1 = this._destinationSink;
+      if (t1 == null) {
+        t1 = new P._Future($.Zone__current, type$._Future_dynamic);
+        this._stream_sink_completer$_doneCompleter = new P._SyncCompleter(t1, type$._SyncCompleter_dynamic);
+        return t1;
+      }
+      return t1.get$done();
+    },
+    addStream$1: function(stream) {
+      var _this = this;
+      _this.$ti._eval$1("Stream<1>")._check(stream);
+      if (_this.get$_canSendDirectly())
+        return _this._destinationSink.addStream$1(stream);
+      _this._ensureController$0();
+      return _this._stream_sink_completer$_controller.addStream$2$cancelOnError(stream, false);
+    },
+    close$0: function(_) {
+      var _this = this;
+      if (_this.get$_canSendDirectly())
+        _this._destinationSink.close$0(0);
+      else {
+        _this._ensureController$0();
+        _this._stream_sink_completer$_controller.close$0(0);
+      }
+      return _this.get$done();
+    },
+    _ensureController$0: function() {
+      if (this._stream_sink_completer$_controller == null)
+        this.set$_stream_sink_completer$_controller(P.StreamController_StreamController(null, null, true, this.$ti._precomputed1));
+    },
+    _setDestinationSink$1: function(sink) {
+      var t1, _this = this;
+      _this.$ti._eval$1("StreamSink<1>")._check(sink);
+      H.assertHelper(_this._destinationSink == null);
+      _this.set$_destinationSink(sink);
+      t1 = _this._stream_sink_completer$_controller;
+      if (t1 != null)
+        sink.addStream$1(new P._ControllerStream(t1, H._instanceType(t1)._eval$1("_ControllerStream<1>"))).whenComplete$1(sink.get$close(sink)).catchError$1(new T._CompleterSink__setDestinationSink_closure());
+      t1 = _this._stream_sink_completer$_doneCompleter;
+      if (t1 != null)
+        t1.complete$1(sink.get$done());
+    },
+    set$_stream_sink_completer$_controller: function(_controller) {
+      this._stream_sink_completer$_controller = this.$ti._eval$1("StreamController<1>")._check(_controller);
+    },
+    set$_destinationSink: function(_destinationSink) {
+      this._destinationSink = this.$ti._eval$1("StreamSink<1>")._check(_destinationSink);
+    },
+    $isEventSink: 1,
+    $isStreamConsumer: 1,
+    $isStreamSink: 1,
+    $isSink: 1
+  };
+  T._CompleterSink__setDestinationSink_closure.prototype = {
+    call$1: function(_) {
+    },
+    $signature: 3
+  };
+  T.SubscriptionStream.prototype = {
+    listen$4$cancelOnError$onDone$onError: function(onData, cancelOnError, onDone, onError) {
+      var result, result0,
+        t1 = this.$ti;
+      t1._eval$1("~(1)")._check(onData);
+      type$.void_Function._check(onDone);
+      H._checkBoolNullable(cancelOnError);
+      result = this._subscription_stream$_source;
+      if (result == null)
+        throw H.wrapException(P.StateError$("Stream has already been listened to."));
+      this.set$_subscription_stream$_source(null);
+      result0 = true === cancelOnError ? new T._CancelOnErrorSubscriptionWrapper(result, t1._eval$1("_CancelOnErrorSubscriptionWrapper<1>")) : result;
+      result0.onData$1(onData);
+      result0.onError$1(0, onError);
+      result0.onDone$1(onDone);
+      result.resume$0();
+      return result0;
+    },
+    listen$3$onDone$onError: function(onData, onDone, onError) {
+      return this.listen$4$cancelOnError$onDone$onError(onData, null, onDone, onError);
+    },
+    listen$1: function(onData) {
+      return this.listen$4$cancelOnError$onDone$onError(onData, null, null, null);
+    },
+    set$_subscription_stream$_source: function(_source) {
+      this._subscription_stream$_source = this.$ti._eval$1("StreamSubscription<1>")._check(_source);
+    }
+  };
+  T._CancelOnErrorSubscriptionWrapper.prototype = {
+    onError$1: function(_, handleError) {
+      this.super$DelegatingStreamSubscription$onError(0, new T._CancelOnErrorSubscriptionWrapper_onError_closure(this, handleError));
+    }
+  };
+  T._CancelOnErrorSubscriptionWrapper_onError_closure.prototype = {
+    call$2: function(error, stackTrace) {
+      var cancelFuture, t1;
+      type$.StackTrace._check(stackTrace);
+      cancelFuture = this.$this.super$DelegatingStreamSubscription$cancel();
+      if (cancelFuture != null)
+        cancelFuture.whenComplete$1(new T._CancelOnErrorSubscriptionWrapper_onError__closure(this.handleError, error, stackTrace));
+      else {
+        t1 = this.handleError;
+        if (type$.dynamic_Function_dynamic_dynamic._is(t1))
+          t1.call$2(error, stackTrace);
+        else
+          t1.call$1(error);
+      }
+    },
+    $signature: 5
+  };
+  T._CancelOnErrorSubscriptionWrapper_onError__closure.prototype = {
+    call$0: function() {
+      var t1 = this.handleError,
+        t2 = this.error;
+      if (type$.dynamic_Function_dynamic_dynamic._is(t1))
+        t1.call$2(t2, this.stackTrace);
+      else
+        t1.call$1(t2);
+    },
+    $signature: 0
+  };
+  X.BooleanSelector.prototype = {};
+  X.All.prototype = {
+    evaluate$1: function(semantics) {
+      return true;
+    },
+    intersection$1: function(other) {
+      return other;
+    },
+    validate$1: function(isDefined) {
+      type$.bool_Function_String._check(isDefined);
+    },
+    toString$0: function(_) {
+      return "<all>";
+    },
+    $isBooleanSelector: 1
+  };
+  U.VariableNode.prototype = {
+    accept$1: function(visitor) {
+      return visitor.visitVariable$1(this);
+    },
+    toString$0: function(_) {
+      return this.name;
+    },
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      return other instanceof U.VariableNode && this.name == other.name;
+    },
+    get$hashCode: function(_) {
+      return J.get$hashCode$(this.name);
+    },
+    $isNode: 1,
+    get$span: function() {
+      return this.span;
+    }
+  };
+  U.NotNode.prototype = {
+    accept$1: function(visitor) {
+      return visitor.visitNot$1(this);
+    },
+    toString$0: function(_) {
+      var t1 = this.child;
+      return t1 instanceof U.VariableNode || t1 instanceof U.NotNode ? "!" + t1.toString$0(0) : "!(" + t1.toString$0(0) + ")";
+    },
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      return other instanceof U.NotNode && this.child.$eq(0, other.child);
+    },
+    get$hashCode: function(_) {
+      var t1 = this.child;
+      return ~t1.get$hashCode(t1) >>> 0;
+    },
+    $isNode: 1,
+    get$span: function() {
+      return this.span;
+    }
+  };
+  U.OrNode.prototype = {
+    get$span: function() {
+      return U._expandSafe(this.left.get$span(), this.right.get$span());
+    },
+    accept$1: function(visitor) {
+      return visitor.visitOr$1(this);
+    },
+    toString$0: function(_) {
+      var string2,
+        string1 = this.left;
+      if (string1 instanceof U.AndNode || string1 instanceof U.ConditionalNode)
+        string1 = "(" + string1.toString$0(0) + ")";
+      string2 = this.right;
+      if (string2 instanceof U.AndNode || string2 instanceof U.ConditionalNode)
+        string2 = "(" + string2.toString$0(0) + ")";
+      return H.S(string1) + " || " + H.S(string2);
+    },
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      return other instanceof U.OrNode && this.left.$eq(0, other.left) && this.right.$eq(0, other.right);
+    },
+    get$hashCode: function(_) {
+      var t1 = this.left,
+        t2 = this.right;
+      return (t1.get$hashCode(t1) ^ t2.get$hashCode(t2)) >>> 0;
+    },
+    $isNode: 1
+  };
+  U.AndNode.prototype = {
+    get$span: function() {
+      return U._expandSafe(this.left.get$span(), this.right.get$span());
+    },
+    accept$1: function(visitor) {
+      return visitor.visitAnd$1(this);
+    },
+    toString$0: function(_) {
+      var string2,
+        string1 = this.left;
+      if (string1 instanceof U.OrNode || string1 instanceof U.ConditionalNode)
+        string1 = "(" + string1.toString$0(0) + ")";
+      string2 = this.right;
+      if (string2 instanceof U.OrNode || string2 instanceof U.ConditionalNode)
+        string2 = "(" + string2.toString$0(0) + ")";
+      return H.S(string1) + " && " + H.S(string2);
+    },
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      return other instanceof U.AndNode && this.left.$eq(0, other.left) && this.right.$eq(0, other.right);
+    },
+    get$hashCode: function(_) {
+      var t1 = this.left,
+        t2 = this.right;
+      return (t1.get$hashCode(t1) ^ t2.get$hashCode(t2)) >>> 0;
+    },
+    $isNode: 1
+  };
+  U.ConditionalNode.prototype = {
+    get$span: function() {
+      return U._expandSafe(this.condition.get$span(), this.whenFalse.get$span());
+    },
+    accept$1: function(visitor) {
+      return visitor.visitConditional$1(this);
+    },
+    toString$0: function(_) {
+      var trueString,
+        conditionString = this.condition;
+      if (conditionString instanceof U.ConditionalNode)
+        conditionString = "(" + conditionString.toString$0(0) + ")";
+      trueString = this.whenTrue;
+      if (trueString instanceof U.ConditionalNode)
+        trueString = "(" + trueString.toString$0(0) + ")";
+      return H.S(conditionString) + " ? " + H.S(trueString) + " : " + this.whenFalse.toString$0(0);
+    },
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      return other instanceof U.ConditionalNode && this.condition.$eq(0, other.condition) && this.whenTrue.$eq(0, other.whenTrue) && this.whenFalse.$eq(0, other.whenFalse);
+    },
+    get$hashCode: function(_) {
+      var t1 = this.condition,
+        t2 = this.whenTrue,
+        t3 = this.whenFalse;
+      return (t1.get$hashCode(t1) ^ t2.get$hashCode(t2) ^ t3.get$hashCode(t3)) >>> 0;
+    },
+    $isNode: 1
+  };
+  T.Evaluator.prototype = {
+    visitVariable$1: function(node) {
+      return this._semantics.call$1(node.name);
+    },
+    visitNot$1: function(node) {
+      return !H.boolConversionCheck(node.child.accept$1(this));
+    },
+    visitOr$1: function(node) {
+      return H.boolConversionCheck(node.left.accept$1(this)) || H.boolConversionCheck(node.right.accept$1(this));
+    },
+    visitAnd$1: function(node) {
+      return H.boolConversionCheck(node.left.accept$1(this)) && H.boolConversionCheck(node.right.accept$1(this));
+    },
+    visitConditional$1: function(node) {
+      return H.boolConversionCheck(node.condition.accept$1(this)) ? node.whenTrue.accept$1(this) : node.whenFalse.accept$1(this);
+    },
+    $isVisitor: 1
+  };
+  Y.BooleanSelectorImpl.prototype = {
+    evaluate$1: function(semantics) {
+      var t1;
+      if (type$.Iterable_dynamic._is(semantics)) {
+        t1 = semantics.toSet$0(0);
+        t1 = t1.get$contains(t1);
+      } else {
+        type$.bool_Function_String._as(semantics);
+        t1 = semantics;
+      }
+      return this._selector.accept$1(new T.Evaluator(t1));
+    },
+    intersection$1: function(other) {
+      var t1 = J.getInterceptor$(other);
+      if (t1.$eq(other, C.C_All))
+        return this;
+      if (t1.$eq(other, C.C_None))
+        return other;
+      return other instanceof Y.BooleanSelectorImpl ? new Y.BooleanSelectorImpl(new U.AndNode(this._selector, other._selector)) : new R.IntersectionSelector(this, other);
+    },
+    validate$1: function(isDefined) {
+      this._selector.accept$1(new S.Validator(type$.bool_Function_String._check(isDefined)));
+    },
+    toString$0: function(_) {
+      return this._selector.toString$0(0);
+    },
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      return other instanceof Y.BooleanSelectorImpl && this._selector.$eq(0, other._selector);
+    },
+    get$hashCode: function(_) {
+      var t1 = this._selector;
+      return t1.get$hashCode(t1);
+    },
+    $isBooleanSelector: 1
+  };
+  R.IntersectionSelector.prototype = {
+    evaluate$1: function(semantics) {
+      return H.boolConversionCheck(this._selector1.evaluate$1(semantics)) && H.boolConversionCheck(this._selector2.evaluate$1(semantics));
+    },
+    intersection$1: function(other) {
+      return new R.IntersectionSelector(this, other);
+    },
+    validate$1: function(isDefined) {
+      type$.bool_Function_String._check(isDefined);
+      this._selector1.validate$1(isDefined);
+      this._selector2.validate$1(isDefined);
+    },
+    toString$0: function(_) {
+      return "(" + this._selector1.toString$0(0) + ") && (" + H.S(this._selector2) + ")";
+    },
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      return other instanceof R.IntersectionSelector && this._selector1.$eq(0, other._selector1) && J.$eq$(this._selector2, other._selector2);
+    },
+    get$hashCode: function(_) {
+      var t1 = this._selector1;
+      return (t1.get$hashCode(t1) ^ J.get$hashCode$(this._selector2)) >>> 0;
+    },
+    $isBooleanSelector: 1
+  };
+  O.None.prototype = {
+    evaluate$1: function(semantics) {
+      return false;
+    },
+    intersection$1: function(other) {
+      return this;
+    },
+    validate$1: function(isDefined) {
+      type$.bool_Function_String._check(isDefined);
+    },
+    toString$0: function(_) {
+      return "<none>";
+    },
+    $isBooleanSelector: 1
+  };
+  G.Parser.prototype = {
+    parse$0: function() {
+      var selector = this._conditional$0(),
+        t1 = this._parser0$_scanner,
+        t2 = t1.peek$0();
+      if (t2.get$type(t2) !== C.TokenType_wwi)
+        throw H.wrapException(G.SourceSpanFormatException$("Expected end of input.", t1.peek$0().get$span(), null));
+      return selector;
+    },
+    _conditional$0: function() {
+      var whenTrue, _this = this,
+        condition = _this._or$0(),
+        t1 = _this._parser0$_scanner;
+      if (!t1.scan$1(C.TokenType_69P))
+        return condition;
+      whenTrue = _this._conditional$0();
+      if (!t1.scan$1(C.TokenType_colon))
+        throw H.wrapException(G.SourceSpanFormatException$('Expected ":".', t1.peek$0().get$span(), null));
+      return new U.ConditionalNode(condition, whenTrue, _this._conditional$0());
+    },
+    _or$0: function() {
+      var left = this._and$0();
+      if (!this._parser0$_scanner.scan$1(C.TokenType_or))
+        return left;
+      return new U.OrNode(left, this._or$0());
+    },
+    _and$0: function() {
+      var left = this._simpleExpression$0();
+      if (!this._parser0$_scanner.scan$1(C.TokenType_and))
+        return left;
+      return new U.AndNode(left, this._and$0());
+    },
+    _simpleExpression$0: function() {
+      var child,
+        t1 = this._parser0$_scanner,
+        token = t1.next$0();
+      switch (token.get$type(token)) {
+        case C.TokenType_not:
+          child = this._simpleExpression$0();
+          return new U.NotNode(token.get$span().expand$1(0, child.get$span()), child);
+        case C.TokenType_e7P:
+          child = this._conditional$0();
+          if (!t1.scan$1(C.TokenType_31K))
+            throw H.wrapException(G.SourceSpanFormatException$('Expected ")".', t1.peek$0().get$span(), null));
+          return child;
+        case C.TokenType_identifier:
+          type$.IdentifierToken._as(token);
+          return new U.VariableNode(token.span, token.name);
+        default:
+          throw H.wrapException(G.SourceSpanFormatException$("Expected expression.", token.get$span(), null));
+      }
+    }
+  };
+  O.Scanner.prototype = {
+    peek$0: function() {
+      var t1 = this._scanner$_next;
+      return t1 == null ? this._scanner$_next = this._getNext$0() : t1;
+    },
+    next$0: function() {
+      var _this = this,
+        token = _this._scanner$_next;
+      if (token == null)
+        token = _this._getNext$0();
+      _this._endOfFileEmitted = token.get$type(token) === C.TokenType_wwi;
+      _this._scanner$_next = null;
+      return token;
+    },
+    scan$1: function(type) {
+      var t1 = this.peek$0();
+      if (t1.get$type(t1) !== type)
+        return false;
+      this.next$0();
+      return true;
+    },
+    _getNext$0: function() {
+      var t1, t2, _this = this;
+      if (_this._endOfFileEmitted)
+        throw H.wrapException(P.StateError$("No more tokens."));
+      _this._consumeWhitespace$0();
+      t1 = _this._scanner;
+      t2 = t1._string_scanner$_position;
+      if (t2 === t1.string.length)
+        return new L.Token(C.TokenType_wwi, t1.spanFrom$1(new S._SpanScannerState(t1, t2)));
+      switch (t1.peekChar$0()) {
+        case 40:
+          return _this._scanOperator$1(C.TokenType_e7P);
+        case 41:
+          return _this._scanOperator$1(C.TokenType_31K);
+        case 63:
+          return _this._scanOperator$1(C.TokenType_69P);
+        case 58:
+          return _this._scanOperator$1(C.TokenType_colon);
+        case 33:
+          return _this._scanOperator$1(C.TokenType_not);
+        case 124:
+          t2 = t1._string_scanner$_position;
+          t1.expect$1("||");
+          return new L.Token(C.TokenType_or, t1.spanFrom$1(new S._SpanScannerState(t1, t2)));
+        case 38:
+          t2 = t1._string_scanner$_position;
+          t1.expect$1("&&");
+          return new L.Token(C.TokenType_and, t1.spanFrom$1(new S._SpanScannerState(t1, t2)));
+        default:
+          t1.expect$2$name($.$get$_hyphenatedIdentifier0(), "expression");
+          t2 = t1.get$lastMatch().$index(0, 0);
+          if (t1.get$lastMatch() == null)
+            t1._lastSpan = null;
+          return new L.IdentifierToken(t1._lastSpan, t2);
+      }
+    },
+    _scanOperator$1: function(type) {
+      var t1 = this._scanner,
+        t2 = t1._string_scanner$_position,
+        t3 = t1.string;
+      if (t2 === t3.length)
+        t1.error$3$length$position(0, "expected more input.", 0, t2);
+      J.codeUnitAt$1$s(t3, t1._string_scanner$_position++);
+      return new L.Token(type, t1.spanFrom$1(new S._SpanScannerState(t1, t2)));
+    },
+    _consumeWhitespace$0: function() {
+      var success,
+        t1 = this._scanner;
+      while (true) {
+        success = t1.matches$1(0, $.$get$_whitespaceAndSingleLineComments());
+        if (success)
+          t1._lastMatchPosition = t1._string_scanner$_position = t1._lastMatch.get$end();
+        if (!(success || this._multiLineComment$0()))
+          break;
+      }
+    },
+    _multiLineComment$0: function() {
+      var success,
+        t1 = this._scanner;
+      if (!t1.scan$1("/*"))
+        return false;
+      while (true) {
+        success = t1.matches$1(0, $.$get$_multiLineCommentBody());
+        if (success)
+          t1._lastMatchPosition = t1._string_scanner$_position = t1._lastMatch.get$end();
+        if (!(success || this._multiLineComment$0()))
+          break;
+      }
+      t1.expect$1("*/");
+      return true;
+    }
+  };
+  L.Token.prototype = {
+    get$type: function(receiver) {
+      return this.type;
+    },
+    get$span: function() {
+      return this.span;
+    }
+  };
+  L.IdentifierToken.prototype = {
+    toString$0: function(_) {
+      return 'identifier "' + H.S(this.name) + '"';
+    },
+    $isToken: 1,
+    get$type: function() {
+      return C.TokenType_identifier;
+    },
+    get$span: function() {
+      return this.span;
+    }
+  };
+  L.TokenType.prototype = {
+    toString$0: function(_) {
+      return this.name;
+    }
+  };
+  S.Validator.prototype = {
+    visitVariable$1: function(node) {
+      if (H.boolConversionCheck(this._isDefined.call$1(node.name)))
+        return;
+      throw H.wrapException(G.SourceSpanFormatException$("Undefined variable.", node.span, null));
+    }
+  };
+  B.RecursiveVisitor.prototype = {
+    visitNot$1: function(node) {
+      node.child.accept$1(this);
+    },
+    visitOr$1: function(node) {
+      node.left.accept$1(this);
+      node.right.accept$1(this);
+    },
+    visitAnd$1: function(node) {
+      node.left.accept$1(this);
+      node.right.accept$1(this);
+    },
+    visitConditional$1: function(node) {
+      node.condition.accept$1(this);
+      node.whenTrue.accept$1(this);
+      node.whenFalse.accept$1(this);
+    },
+    $isVisitor: 1
+  };
+  O.EmptyUnmodifiableSet.prototype = {
+    get$iterator: function(_) {
+      return C.C_EmptyIterator;
+    },
+    get$length: function(_) {
+      return 0;
+    },
+    contains$1: function(_, element) {
+      return false;
+    },
+    toSet$0: function(_) {
+      return P.LinkedHashSet_LinkedHashSet(this.$ti._precomputed1);
+    },
+    $isEfficientLengthIterable: 1,
+    $isSet: 1
+  };
+  Y.mapMap_closure.prototype = {
+    call$2: function(mapKey, _) {
+      this.K1._check(mapKey);
+      this.V1._check(_);
+      return this.K2._as(mapKey);
+    },
+    $signature: function() {
+      return this.K2._eval$1("@<0>")._bind$1(this.K1)._bind$1(this.V1)._eval$1("1(2,3)");
+    }
+  };
+  Y.mapMap_closure0.prototype = {
+    call$2: function(mapKey, mapValue) {
+      var t1, _this = this;
+      _this.K1._check(mapKey);
+      _this.V1._check(mapValue);
+      t1 = _this._box_0;
+      _this.result.$indexSet(0, t1.key.call$2(mapKey, mapValue), t1.value.call$2(mapKey, mapValue));
+    },
+    $signature: function() {
+      return this.K1._eval$1("@<0>")._bind$1(this.V1)._eval$1("Null(1,2)");
+    }
+  };
+  Y.mergeMaps_closure.prototype = {
+    call$2: function(key, mapValue) {
+      var t1, _this = this;
+      _this.K._check(key);
+      _this.V._check(mapValue);
+      t1 = _this.result;
+      t1.$indexSet(0, key, t1.containsKey$1(key) ? _this.value.call$2(t1.$index(0, key), mapValue) : mapValue);
+    },
+    $signature: function() {
+      return this.K._eval$1("@<0>")._bind$1(this.V)._eval$1("Null(1,2)");
+    }
+  };
+  Q.QueueList.prototype = {
+    toString$0: function(_) {
+      return P.IterableBase_iterableToFullString(this, "{", "}");
+    },
+    removeFirst$0: function() {
+      var t2, result, _this = this,
+        t1 = _this._queue_list$_head;
+      if (t1 === _this._queue_list$_tail)
+        throw H.wrapException(P.StateError$("No element"));
+      t2 = _this._queue_list$_table;
+      if (t1 >= t2.length)
+        return H.ioore(t2, t1);
+      result = t2[t1];
+      C.JSArray_methods.$indexSet(t2, t1, null);
+      _this._queue_list$_head = (_this._queue_list$_head + 1 & _this._queue_list$_table.length - 1) >>> 0;
+      return result;
+    },
+    get$length: function(_) {
+      return (this._queue_list$_tail - this._queue_list$_head & this._queue_list$_table.length - 1) >>> 0;
+    },
+    set$length: function(_, value) {
+      var delta, t1, newTail, t2, _this = this;
+      if (value < 0)
+        throw H.wrapException(P.RangeError$("Length " + value + " may not be negative."));
+      delta = value - _this.get$length(_this);
+      if (delta >= 0) {
+        if (_this._queue_list$_table.length <= value)
+          _this._preGrow$1(value);
+        _this._queue_list$_tail = (_this._queue_list$_tail + delta & _this._queue_list$_table.length - 1) >>> 0;
+        return;
+      }
+      t1 = _this._queue_list$_tail;
+      newTail = t1 + delta;
+      t2 = _this._queue_list$_table;
+      if (newTail >= 0)
+        C.JSArray_methods.fillRange$3(t2, newTail, t1, null);
+      else {
+        newTail += t2.length;
+        C.JSArray_methods.fillRange$3(t2, 0, t1, null);
+        t1 = _this._queue_list$_table;
+        C.JSArray_methods.fillRange$3(t1, newTail, t1.length, null);
+      }
+      _this._queue_list$_tail = newTail;
+    },
+    $index: function(_, index) {
+      var t1, t2, t3, _this = this;
+      H._checkIntNullable(index);
+      if (index < 0 || index >= _this.get$length(_this))
+        throw H.wrapException(P.RangeError$("Index " + index + " must be in the range [0.." + _this.get$length(_this) + ")."));
+      t1 = _this._queue_list$_table;
+      t2 = t1.length;
+      t3 = (_this._queue_list$_head + index & t2 - 1) >>> 0;
+      if (t3 < 0 || t3 >= t2)
+        return H.ioore(t1, t3);
+      return t1[t3];
+    },
+    $indexSet: function(_, index, value) {
+      var t1, _this = this;
+      H._checkIntNullable(index);
+      _this.$ti._precomputed1._check(value);
+      if (typeof index !== "number")
+        return index.$lt();
+      if (index < 0 || index >= _this.get$length(_this))
+        throw H.wrapException(P.RangeError$("Index " + index + " must be in the range [0.." + _this.get$length(_this) + ")."));
+      t1 = _this._queue_list$_table;
+      C.JSArray_methods.$indexSet(t1, (_this._queue_list$_head + index & t1.length - 1) >>> 0, value);
+    },
+    _queue_list$_add$1: function(element) {
+      var t2, t3, newTable, split, _this = this,
+        t1 = _this.$ti;
+      t1._precomputed1._check(element);
+      C.JSArray_methods.$indexSet(_this._queue_list$_table, _this._queue_list$_tail, element);
+      t2 = _this._queue_list$_tail;
+      t3 = _this._queue_list$_table.length;
+      t2 = (t2 + 1 & t3 - 1) >>> 0;
+      _this._queue_list$_tail = t2;
+      if (_this._queue_list$_head === t2) {
+        t2 = new Array(t3 * 2);
+        t2.fixed$length = Array;
+        newTable = H.setRuntimeTypeInfo(t2, t1._eval$1("JSArray<1>"));
+        t1 = _this._queue_list$_table;
+        t2 = _this._queue_list$_head;
+        split = t1.length - t2;
+        C.JSArray_methods.setRange$4(newTable, 0, split, t1, t2);
+        C.JSArray_methods.setRange$4(newTable, split, split + _this._queue_list$_head, _this._queue_list$_table, 0);
+        _this._queue_list$_head = 0;
+        _this._queue_list$_tail = _this._queue_list$_table.length;
+        _this.set$_queue_list$_table(newTable);
+      }
+    },
+    _writeToList$1: function(target) {
+      var t1, t2, t3, $length, firstPartSize, _this = this;
+      _this.$ti._eval$1("List<1>")._check(target);
+      H.assertHelper(target.length >= _this.get$length(_this));
+      t1 = _this._queue_list$_head;
+      t2 = _this._queue_list$_tail;
+      t3 = _this._queue_list$_table;
+      if (t1 <= t2) {
+        $length = t2 - t1;
+        C.JSArray_methods.setRange$4(target, 0, $length, t3, t1);
+        return $length;
+      } else {
+        firstPartSize = t3.length - t1;
+        C.JSArray_methods.setRange$4(target, 0, firstPartSize, t3, t1);
+        C.JSArray_methods.setRange$4(target, firstPartSize, firstPartSize + _this._queue_list$_tail, _this._queue_list$_table, 0);
+        return _this._queue_list$_tail + firstPartSize;
+      }
+    },
+    _preGrow$1: function(newElementCount) {
+      var newCapacity, t1, newTable, _this = this;
+      H.assertHelper(newElementCount >= _this.get$length(_this));
+      newCapacity = Q.QueueList__nextPowerOf2(newElementCount + C.JSInt_methods._shrOtherPositive$1(newElementCount, 1));
+      if (typeof newCapacity !== "number")
+        return H.iae(newCapacity);
+      t1 = new Array(newCapacity);
+      t1.fixed$length = Array;
+      newTable = H.setRuntimeTypeInfo(t1, _this.$ti._eval$1("JSArray<1>"));
+      _this._queue_list$_tail = _this._writeToList$1(newTable);
+      _this.set$_queue_list$_table(newTable);
+      _this._queue_list$_head = 0;
+    },
+    set$_queue_list$_table: function(_table) {
+      this._queue_list$_table = this.$ti._eval$1("List<1>")._check(_table);
+    },
+    $isEfficientLengthIterable: 1,
+    $isQueue: 1,
+    $isIterable: 1,
+    $isList: 1
+  };
+  Q._QueueList_Object_ListMixin.prototype = {};
+  M.UnionSet.prototype = {
+    get$length: function(_) {
+      var t1 = this._sets.fold$1$2(0, 0, new M.UnionSet_length_closure(this), type$.int);
+      return t1;
+    },
+    get$iterator: function(_) {
+      var t1 = this.get$_union_set$_iterable();
+      return t1.get$iterator(t1);
+    },
+    get$_union_set$_iterable: function() {
+      var t1 = this._sets,
+        t2 = this.$ti._precomputed1,
+        t3 = H._instanceType(t1),
+        t4 = t3._bind$1(t2)._eval$1("Iterable<1>(2)")._check(new M.UnionSet__iterable_closure(this));
+      return new H.ExpandIterable(t1, t4, t3._eval$1("@<1>")._bind$1(t2)._eval$1("ExpandIterable<1,2>"));
+    },
+    toSet$0: function(_) {
+      var t1,
+        result = P.LinkedHashSet_LinkedHashSet(this.$ti._precomputed1);
+      for (t1 = this._sets, t1 = P._LinkedHashSetIterator$(t1, t1._collection$_modifications, H._instanceType(t1)._precomputed1); t1.moveNext$0();)
+        result.addAll$1(0, t1._collection$_current);
+      return result;
+    }
+  };
+  M.UnionSet_length_closure.prototype = {
+    call$2: function($length, set) {
+      var t1;
+      H._checkIntNullable($length);
+      this.$this.$ti._eval$1("Set<1>")._check(set);
+      t1 = set.get$length(set);
+      if (typeof $length !== "number")
+        return $length.$add();
+      if (typeof t1 !== "number")
+        return H.iae(t1);
+      return $length + t1;
+    },
+    $signature: function() {
+      return this.$this.$ti._eval$1("int(int,Set<1>)");
+    }
+  };
+  M.UnionSet__iterable_closure.prototype = {
+    call$1: function(set) {
+      return this.$this.$ti._eval$1("Set<1>")._check(set);
+    },
+    $signature: function() {
+      return this.$this.$ti._eval$1("Set<1>(Set<1>)");
+    }
+  };
+  M._UnionSet_SetBase_UnmodifiableSetMixin.prototype = {};
+  Y.UnionSetController.prototype = {
+    set$_union_set_controller$_set: function(_set) {
+      this._union_set_controller$_set = this.$ti._eval$1("UnionSet<1>")._check(_set);
+    }
+  };
+  L.UnmodifiableSetView.prototype = {};
+  L.UnmodifiableSetMixin.prototype = {};
+  L._UnmodifiableSetView_DelegatingSet_UnmodifiableSetMixin.prototype = {};
+  M._DelegatingIterableBase.prototype = {
+    contains$1: function(_, element) {
+      return this._base.contains$1(0, element);
+    },
+    every$1: function(_, test) {
+      return this._base.every$1(0, H._instanceType(this)._eval$1("bool(1)")._check(test));
+    },
+    get$first: function(_) {
+      var t1 = this._base;
+      return t1.get$first(t1);
+    },
+    get$isEmpty: function(_) {
+      var t1 = this._base;
+      return t1.get$isEmpty(t1);
+    },
+    get$iterator: function(_) {
+      var t1 = this._base;
+      return t1.get$iterator(t1);
+    },
+    get$last: function(_) {
+      var t1 = this._base;
+      return t1.get$last(t1);
+    },
+    get$length: function(_) {
+      var t1 = this._base;
+      return t1.get$length(t1);
+    },
+    map$1$1: function(_, f, $T) {
+      return this._base.map$1$1(0, H._instanceType(this)._bind$1($T)._eval$1("1(2)")._check(f), $T);
+    },
+    toList$1$growable: function(_, growable) {
+      return this._base.toList$1$growable(0, true);
+    },
+    toList$0: function($receiver) {
+      return this.toList$1$growable($receiver, true);
+    },
+    toSet$0: function(_) {
+      return this._base.toSet$0(0);
+    },
+    where$1: function(_, test) {
+      return this._base.where$1(0, H._instanceType(this)._eval$1("bool(1)")._check(test));
+    },
+    toString$0: function(_) {
+      return this._base.toString$0(0);
+    },
+    $isIterable: 1
+  };
+  M.DelegatingIterable.prototype = {};
+  M.DelegatingSet.prototype = {
+    union$1: function(other) {
+      var t1 = H._instanceType(this)._eval$1("Set<1>");
+      t1._check(other);
+      return t1._check(this._base).union$1(other);
+    },
+    toSet$0: function(_) {
+      var t1 = H._instanceType(this);
+      return new M.DelegatingSet(t1._eval$1("Set<1>")._check(this._base).toSet$0(0), t1._eval$1("DelegatingSet<1>"));
+    },
+    $isEfficientLengthIterable: 1,
+    $isSet: 1
+  };
+  Y._IsTrue.prototype = {
+    matches$2: function(_, item, matchState) {
+      return J.$eq$(item, true);
+    },
+    describe$1: function(description) {
+      description._out._contents += "true";
+      return description;
+    }
+  };
+  Y._Predicate.prototype = {
+    typedMatches$2: function(item, matchState) {
+      return this._matcher.call$1(this.$ti._precomputed1._check(item));
+    },
+    describe$1: function(description) {
+      description._out._contents += this._core_matchers$_description;
+      return description;
+    }
+  };
+  E.StringDescription.prototype = {
+    get$length: function(_) {
+      return this._out._contents.length;
+    },
+    toString$0: function(_) {
+      var t1 = this._out._contents;
+      return t1.charCodeAt(0) == 0 ? t1 : t1;
+    },
+    addDescriptionOf$1: function(value) {
+      if (value instanceof G.Matcher)
+        value.describe$1(this);
+      else
+        this._out._contents += Z.prettyPrint(value, 25, 80);
+      return this;
+    },
+    $isDescription: 1
+  };
+  D._StringEqualsMatcher.prototype = {
+    typedMatches$2: function(item, matchState) {
+      return this._equals_matcher$_value === H._checkStringNullable(item);
+    },
+    describe$1: function(description) {
+      return description.addDescriptionOf$1(this._equals_matcher$_value);
+    },
+    describeTypedMismatch$4: function(item, mismatchDescription, matchState, verbose) {
+      var buff, escapedItem, escapedValue, minLength, minLength0, minLength1, start, t1, i;
+      H._checkStringNullable(true);
+      buff = new P.StringBuffer("");
+      buff._contents = "is different.";
+      escapedItem = M.escape(true);
+      escapedValue = M.escape(this._equals_matcher$_value);
+      minLength = escapedItem.length;
+      minLength0 = escapedValue.length;
+      minLength1 = minLength < minLength0 ? minLength : minLength0;
+      for (start = 0; start < minLength1; ++start)
+        if (C.JSString_methods._codeUnitAt$1(escapedValue, start) !== C.JSString_methods._codeUnitAt$1(escapedItem, start))
+          break;
+      if (start === minLength1) {
+        t1 = buff._contents;
+        if (minLength0 < minLength) {
+          buff._contents = t1 + " Both strings start the same, but the actual value also has the following trailing characters: ";
+          D._StringEqualsMatcher__writeTrailing(buff, escapedItem, minLength0);
+        } else {
+          buff._contents = t1 + " Both strings start the same, but the actual value is missing the following trailing characters: ";
+          D._StringEqualsMatcher__writeTrailing(buff, escapedValue, minLength);
+        }
+      } else {
+        buff._contents += "\nExpected: ";
+        D._StringEqualsMatcher__writeLeading(buff, escapedValue, start);
+        D._StringEqualsMatcher__writeTrailing(buff, escapedValue, start);
+        buff._contents += "\n  Actual: ";
+        D._StringEqualsMatcher__writeLeading(buff, escapedItem, start);
+        D._StringEqualsMatcher__writeTrailing(buff, escapedItem, start);
+        t1 = buff._contents += "\n          ";
+        i = start > 10 ? 14 : start;
+        for (; i > 0; --i) {
+          t1 += " ";
+          buff._contents = t1;
+        }
+        buff._contents += "^\n Differ at offset " + start;
+      }
+      t1 = buff._contents;
+      mismatchDescription._out._contents += t1.charCodeAt(0) == 0 ? t1 : t1;
+      return mismatchDescription;
+    }
+  };
+  D._DeepMatcher.prototype = {
+    _compareIterables$5: function(expected, actual, matcher, depth, $location) {
+      var expectedIterator, actualIterator, index, expectedNext, actualNext, t1, newLocation, rp;
+      type$.List_String_Function_dynamic_dynamic_String_int._check(matcher);
+      if (type$.Iterable_dynamic._is(actual)) {
+        expectedIterator = J.get$iterator$ax(expected);
+        actualIterator = J.get$iterator$ax(actual);
+        for (index = 0; true; ++index) {
+          expectedNext = expectedIterator.moveNext$0();
+          actualNext = actualIterator.moveNext$0();
+          t1 = !expectedNext;
+          if (t1 && !actualNext)
+            return null;
+          newLocation = $location + "[" + index + "]";
+          if (t1)
+            return H.setRuntimeTypeInfo(["longer than expected", newLocation], type$.JSArray_String);
+          if (!actualNext)
+            return H.setRuntimeTypeInfo(["shorter than expected", newLocation], type$.JSArray_String);
+          rp = matcher.call$4(expectedIterator.get$current(), actualIterator.get$current(), newLocation, depth);
+          if (rp != null)
+            return rp;
+        }
+      } else
+        return H.setRuntimeTypeInfo(["is not Iterable", $location], type$.JSArray_String);
+    },
+    _compareSets$5: function(expected, actual, matcher, depth, $location) {
+      var other, t1, expectedElement, t2;
+      type$.List_String_Function_dynamic_dynamic_String_int._check(matcher);
+      if (type$.Iterable_dynamic._is(actual)) {
+        other = J.toSet$0$ax(actual);
+        for (t1 = expected.get$iterator(expected); t1.moveNext$0();) {
+          expectedElement = t1.get$current();
+          if (other.every$1(0, new D._DeepMatcher__compareSets_closure(matcher, expectedElement, $location, depth)))
+            return H.setRuntimeTypeInfo(["does not contain " + H.S(expectedElement), $location], type$.JSArray_String);
+        }
+        t1 = other.get$length(other);
+        t2 = expected.get$length(expected);
+        if (typeof t2 !== "number")
+          return H.iae(t2);
+        if (t1 > t2)
+          return H.setRuntimeTypeInfo(["larger than expected", $location], type$.JSArray_String);
+        else {
+          t1 = other.get$length(other);
+          t2 = expected.get$length(expected);
+          if (typeof t2 !== "number")
+            return H.iae(t2);
+          if (t1 < t2)
+            return H.setRuntimeTypeInfo(["smaller than expected", $location], type$.JSArray_String);
+          else
+            return null;
+        }
+      } else
+        return H.setRuntimeTypeInfo(["is not Iterable", $location], type$.JSArray_String);
+    },
+    _recursiveMatch$4: function(expected, actual, $location, depth) {
+      var e, t1, description, exception, err, key, t2, rp, _this = this;
+      if (expected instanceof G.Matcher) {
+        t1 = type$.dynamic;
+        if (expected.matches$2(0, actual, P.LinkedHashMap_LinkedHashMap$_empty(t1, t1)))
+          return null;
+        description = new E.StringDescription(new P.StringBuffer(""));
+        expected.describe$1(description);
+        return H.setRuntimeTypeInfo(["does not match " + description.toString$0(0), $location], type$.JSArray_String);
+      } else
+        try {
+          if (J.$eq$(expected, actual))
+            return null;
+        } catch (exception) {
+          e = H.unwrapException(exception);
+          t1 = H.setRuntimeTypeInfo(['== threw "' + H.S(e) + '"', $location], type$.JSArray_String);
+          return t1;
+        }
+      t1 = _this._limit;
+      if (depth > t1)
+        return H.setRuntimeTypeInfo(["recursion depth limit exceeded", $location], type$.JSArray_String);
+      if (depth === 0 || t1 > 1)
+        if (type$.Set_dynamic._is(expected))
+          return _this._compareSets$5(expected, actual, _this.get$_recursiveMatch(), depth + 1, $location);
+        else if (type$.Iterable_dynamic._is(expected))
+          return _this._compareIterables$5(expected, actual, _this.get$_recursiveMatch(), depth + 1, $location);
+        else {
+          t1 = type$.Map_dynamic_dynamic;
+          if (t1._is(expected)) {
+            if (!t1._is(actual))
+              return H.setRuntimeTypeInfo(["expected a map", $location], type$.JSArray_String);
+            err = expected.get$length(expected) == actual.get$length(actual) ? "" : "has different length and ";
+            for (t1 = expected.get$keys(), t1 = t1.get$iterator(t1); t1.moveNext$0();) {
+              key = t1.get$current();
+              if (!actual.containsKey$1(key))
+                return H.setRuntimeTypeInfo([err + "is missing map key '" + H.S(key) + "'", $location], type$.JSArray_String);
+            }
+            for (t1 = actual.get$keys(), t1 = t1.get$iterator(t1); t1.moveNext$0();) {
+              key = t1.get$current();
+              if (!expected.containsKey$1(key))
+                return H.setRuntimeTypeInfo([err + "has extra map key '" + H.S(key) + "'", $location], type$.JSArray_String);
+            }
+            for (t1 = expected.get$keys(), t1 = t1.get$iterator(t1), t2 = depth + 1; t1.moveNext$0();) {
+              key = t1.get$current();
+              rp = _this._recursiveMatch$4(expected.$index(0, key), actual.$index(0, key), $location + "['" + H.S(key) + "']", t2);
+              if (rp != null)
+                return rp;
+            }
+            return null;
+          }
+        }
+      t1 = new P.StringBuffer("");
+      if (depth > 0) {
+        t1._contents = "was ";
+        t2 = new E.StringDescription(t1).addDescriptionOf$1(actual);
+        t2._out._contents += " instead of ";
+        t2.addDescriptionOf$1(expected);
+        t1 = t1._contents;
+        return H.setRuntimeTypeInfo([t1.charCodeAt(0) == 0 ? t1 : t1, $location], type$.JSArray_String);
+      }
+      return H.setRuntimeTypeInfo(["", $location], type$.JSArray_String);
+    },
+    _equals_matcher$_match$3: function(expected, actual, matchState) {
+      var t1, t2, reason, innerState,
+        rp = this._recursiveMatch$4(expected, actual, "", 0);
+      if (rp == null)
+        return null;
+      t1 = J.getInterceptor$asx(rp);
+      t2 = t1.$index(rp, 0);
+      t2.toString;
+      if (J.get$length$asx(t2) !== 0) {
+        t2 = t1.$index(rp, 1);
+        t2.toString;
+        reason = J.get$length$asx(t2) !== 0 ? H.S(t1.$index(rp, 0)) + " at location " + H.S(t1.$index(rp, 1)) : t1.$index(rp, 0);
+      } else
+        reason = "";
+      t1 = type$.dynamic;
+      t2 = P.LinkedHashMap_LinkedHashMap$_literal(["reason", reason], t1, t1);
+      innerState = P.LinkedHashMap_LinkedHashMap$from(matchState, t1, t1);
+      matchState.clear$0(0);
+      matchState.$indexSet(0, "state", innerState);
+      matchState.addAll$1(0, t2);
+      return reason;
+    },
+    matches$2: function(_, item, matchState) {
+      return this._equals_matcher$_match$3(this._expected, item, matchState) == null;
+    },
+    describe$1: function(description) {
+      return description.addDescriptionOf$1(this._expected);
+    },
+    describeMismatch$4: function(item, mismatchDescription, matchState, verbose) {
+      var t1, t2, t3,
+        reason = H._asStringNullable(matchState.$index(0, "reason"));
+      if (reason == null)
+        reason = "";
+      t1 = reason.length === 0 && mismatchDescription._out._contents.length > 0;
+      t2 = mismatchDescription._out;
+      t3 = t2._contents;
+      if (t1) {
+        t2._contents = t3 + "is ";
+        mismatchDescription.addDescriptionOf$1(true);
+      } else
+        t2._contents = t3 + reason;
+      return mismatchDescription;
+    }
+  };
+  D._DeepMatcher__compareSets_closure.prototype = {
+    call$1: function(actualElement) {
+      var _this = this;
+      return _this.matcher.call$4(_this.expectedElement, actualElement, _this.location, _this.depth) != null;
+    },
+    $signature: 9
+  };
+  E.FeatureMatcher.prototype = {
+    matches$2: function(_, item, matchState) {
+      return this.super$TypeMatcher$matches(0, item, matchState) && H.boolConversionCheck(this.typedMatches$2(H._instanceType(this)._eval$1("FeatureMatcher.T")._check(item), matchState));
+    },
+    describeMismatch$4: function(item, mismatchDescription, matchState, verbose) {
+      if (H._instanceType(this)._eval$1("FeatureMatcher.T")._is(true))
+        return this.describeTypedMismatch$4(true, mismatchDescription, matchState, false);
+      mismatchDescription._out._contents += "not an ";
+      return this.super$TypeMatcher$describe(mismatchDescription);
+    },
+    describeTypedMismatch$4: function(item, mismatchDescription, matchState, verbose) {
+      H._instanceType(this)._eval$1("FeatureMatcher.T")._check(true);
+      return mismatchDescription;
+    }
+  };
+  G.Matcher.prototype = {
+    describeMismatch$4: function(item, mismatchDescription, matchState, verbose) {
+      return mismatchDescription;
+    }
+  };
+  Z.prettyPrint__prettyPrint.prototype = {
+    call$4: function(object, indent, seen, $top) {
+      var description, type, t2, strings, t3, singleLine, value, defaultToString, _this = this, t1 = {};
+      t1.seen = seen;
+      if (object instanceof G.Matcher) {
+        description = new E.StringDescription(new P.StringBuffer(""));
+        object.describe$1(description);
+        return "<" + description.toString$0(0) + ">";
+      }
+      if (seen.contains$1(0, object))
+        return "(recursive)";
+      t1.seen = seen.union$1(P.LinkedHashSet_LinkedHashSet$_literal([object], type$.dynamic));
+      t1 = new Z.prettyPrint__prettyPrint_pp(t1, _this, indent);
+      if (type$.Iterable_dynamic._is(object)) {
+        type = type$.List_dynamic._is(object) ? "" : Z._typeName(object) + ":";
+        t2 = type$.String;
+        strings = J.map$1$1$ax(object, t1, t2).toList$0(0);
+        t1 = strings.length;
+        t3 = _this.maxItems;
+        if (t1 > t3)
+          C.JSArray_methods.replaceRange$3(strings, t3 - 1, t1, H.setRuntimeTypeInfo(["..."], type$.JSArray_String));
+        singleLine = type + "[" + C.JSArray_methods.join$1(strings, ", ") + "]";
+        if (singleLine.length + indent <= _this.maxLineLength && !C.JSString_methods.contains$1(singleLine, "\n"))
+          return singleLine;
+        t1 = H._arrayInstanceType(strings);
+        return type + "[\n" + new H.MappedListIterable(strings, t1._eval$1("String(1)")._check(new Z.prettyPrint__prettyPrint_closure(indent)), t1._eval$1("MappedListIterable<1,String>")).join$1(0, ",\n") + "\n" + C.JSArray_methods.join$1(P.List_List$filled(indent, " ", t2), "") + "]";
+      } else if (type$.Map_dynamic_dynamic._is(object)) {
+        t2 = type$.String;
+        strings = object.get$keys().map$1$1(0, new Z.prettyPrint__prettyPrint_closure0(t1, object), t2).toList$0(0);
+        t1 = strings.length;
+        t3 = _this.maxItems;
+        if (t1 > t3)
+          C.JSArray_methods.replaceRange$3(strings, t3 - 1, t1, H.setRuntimeTypeInfo(["..."], type$.JSArray_String));
+        singleLine = "{" + C.JSArray_methods.join$1(strings, ", ") + "}";
+        if (singleLine.length + indent <= _this.maxLineLength && !C.JSString_methods.contains$1(singleLine, "\n"))
+          return singleLine;
+        t1 = H._arrayInstanceType(strings);
+        return "{\n" + new H.MappedListIterable(strings, t1._eval$1("String(1)")._check(new Z.prettyPrint__prettyPrint_closure1(indent)), t1._eval$1("MappedListIterable<1,String>")).join$1(0, ",\n") + "\n" + C.JSArray_methods.join$1(P.List_List$filled(indent, " ", t2), "") + "}";
+      } else {
+        t1 = type$.String;
+        if (typeof object == "string")
+          return "'" + new H.MappedListIterable(H.setRuntimeTypeInfo(object.split("\n"), type$.JSArray_String), type$.String_Function_String._check(Z.pretty_print___escapeString$closure()), type$.MappedListIterable_String_String).join$1(0, "\\n'\n" + C.JSArray_methods.join$1(P.List_List$filled(indent + 2, " ", t1), "") + "'") + "'";
+        else {
+          t2 = J.toString$0$(object);
+          t1 = C.JSArray_methods.join$1(P.List_List$filled(indent, " ", t1), "") + "\n";
+          t2.toString;
+          value = H.stringReplaceAllUnchecked(t2, "\n", t1);
+          defaultToString = C.JSString_methods.startsWith$1(value, "Instance of ");
+          if ($top)
+            value = "<" + value + ">";
+          if (typeof object == "number" || H._isBool(object) || type$.Function._is(object) || type$.RegExp._is(object) || object instanceof P.MapEntry || object instanceof P.Expando || object == null || defaultToString)
+            return value;
+          else
+            return Z._typeName(object) + ":" + value;
+        }
+      }
+    },
+    $signature: 55
+  };
+  Z.prettyPrint__prettyPrint_pp.prototype = {
+    call$1: function(child) {
+      return this._prettyPrint.call$4(child, this.indent + 2, this._box_0.seen, false);
+    },
+    $signature: 40
+  };
+  Z.prettyPrint__prettyPrint_closure.prototype = {
+    call$1: function(string) {
+      H._checkStringNullable(string);
+      return C.JSString_methods.$add(C.JSArray_methods.join$1(P.List_List$filled(this.indent + 2, " ", type$.String), ""), string);
+    },
+    $signature: 7
+  };
+  Z.prettyPrint__prettyPrint_closure0.prototype = {
+    call$1: function(key) {
+      var t1 = this.pp;
+      return H.S(t1.call$1(key)) + ": " + H.S(t1.call$1(this.object.$index(0, key)));
+    },
+    $signature: 40
+  };
+  Z.prettyPrint__prettyPrint_closure1.prototype = {
+    call$1: function(string) {
+      H._checkStringNullable(string);
+      return C.JSString_methods.$add(C.JSArray_methods.join$1(P.List_List$filled(this.indent + 2, " ", type$.String), ""), string);
+    },
+    $signature: 7
+  };
+  M.TypeMatcher.prototype = {
+    describe$1: function(description) {
+      var $name,
+        t1 = H._rtiToString(H.createRuntimeType(H._instanceType(this)._eval$1("TypeMatcher.T"))._rti, null),
+        t2 = $.$get$_dart2DynamicArgs();
+      t1.toString;
+      $name = H.stringReplaceAllUnchecked(t1, t2, "");
+      description._out._contents += "<Instance of '" + $name + "'>";
+      return description;
+    },
+    matches$2: function(_, item, matchState) {
+      return H._instanceType(this)._eval$1("TypeMatcher.T")._is(item);
+    }
+  };
+  M.wrapMatcher_closure.prototype = {
+    call$1: function(a) {
+      return H._checkBoolNullable(this.x.call$1(a));
+    },
+    $signature: 9
+  };
+  M.escape_closure.prototype = {
+    call$1: function(match) {
+      var mapped = C.Map_F9GZw.$index(0, match.$index(0, 0));
+      if (mapped != null)
+        return mapped;
+      return M._getHexLiteral(match.$index(0, 0));
+    },
+    $signature: 24
+  };
+  F.PackageConfigResolver.prototype = {$isSyncPackageResolver: 1,
+    get$packageRoot: function() {
+      return null;
+    },
+    get$packageConfigMap: function() {
+      return this.packageConfigMap;
+    }
+  };
+  F.PackageConfigResolver__normalizeMap_closure.prototype = {
+    call$2: function(_, uri) {
+      return B.ensureTrailingSlash(type$.Uri._check(uri));
+    },
+    $signature: 51
+  };
+  D.PackageRootResolver.prototype = {$isSyncPackageResolver: 1,
+    get$packageConfigMap: function() {
+      return null;
+    },
+    get$packageRoot: function() {
+      return this.packageRoot;
+    }
+  };
+  M.Context.prototype = {
+    absolute$7: function(_, part1, part2, part3, part4, part5, part6, part7) {
+      var t1;
+      M._validateArgList("absolute", H.setRuntimeTypeInfo([part1, part2, part3, part4, part5, part6, part7], type$.JSArray_String));
+      t1 = this.style;
+      t1 = t1.rootLength$1(part1) > 0 && !t1.isRootRelative$1(part1);
+      if (t1)
+        return part1;
+      t1 = this._context$_current;
+      return this.join$8(0, t1 != null ? t1 : D.current(), part1, part2, part3, part4, part5, part6, part7);
+    },
+    absolute$1: function($receiver, part1) {
+      return this.absolute$7($receiver, part1, null, null, null, null, null, null);
+    },
+    join$8: function(_, part1, part2, part3, part4, part5, part6, part7, part8) {
+      var parts = H.setRuntimeTypeInfo([part1, part2, part3, part4, part5, part6, part7, part8], type$.JSArray_String);
+      M._validateArgList("join", parts);
+      return this.joinAll$1(new H.WhereIterable(parts, type$.bool_Function_String._check(new M.Context_join_closure()), type$.WhereIterable_String));
+    },
+    join$2: function($receiver, part1, part2) {
+      return this.join$8($receiver, part1, part2, null, null, null, null, null, null);
+    },
+    joinAll$1: function(parts) {
+      var t1, t2, t3, needsSeparator, isAbsoluteAndNotRootRelative, t4, t5, parsed, path, t6;
+      type$.Iterable_String._check(parts);
+      for (t1 = parts.$ti, t2 = t1._eval$1("bool(Iterable.E)")._check(new M.Context_joinAll_closure()), t3 = parts.get$iterator(parts), t1 = new H.WhereIterator(t3, t2, t1._eval$1("WhereIterator<Iterable.E>")), t2 = this.style, needsSeparator = false, isAbsoluteAndNotRootRelative = false, t4 = ""; t1.moveNext$0();) {
+        t5 = t3.get$current();
+        if (t2.isRootRelative$1(t5) && isAbsoluteAndNotRootRelative) {
+          parsed = X.ParsedPath_ParsedPath$parse(t5, t2);
+          path = t4.charCodeAt(0) == 0 ? t4 : t4;
+          t4 = C.JSString_methods.substring$2(path, 0, t2.rootLength$2$withDrive(path, true));
+          parsed.root = t4;
+          if (t2.needsSeparator$1(t4))
+            C.JSArray_methods.$indexSet(parsed.separators, 0, t2.get$separator());
+          t4 = parsed.toString$0(0);
+        } else if (t2.rootLength$1(t5) > 0) {
+          isAbsoluteAndNotRootRelative = !t2.isRootRelative$1(t5);
+          t4 = H.S(t5);
+        } else {
+          t6 = t5.length;
+          if (t6 !== 0) {
+            if (0 >= t6)
+              return H.ioore(t5, 0);
+            t6 = t2.containsSeparator$1(t5[0]);
+          } else
+            t6 = false;
+          if (!t6)
+            if (needsSeparator)
+              t4 += t2.get$separator();
+          t4 += t5;
+        }
+        needsSeparator = t2.needsSeparator$1(t5);
+      }
+      return t4.charCodeAt(0) == 0 ? t4 : t4;
+    },
+    split$1: function(_, path) {
+      var parsed = X.ParsedPath_ParsedPath$parse(path, this.style),
+        t1 = parsed.parts,
+        t2 = H._arrayInstanceType(t1),
+        t3 = t2._eval$1("WhereIterable<1>");
+      parsed.set$parts(P.List_List$from(new H.WhereIterable(t1, t2._eval$1("bool(1)")._check(new M.Context_split_closure()), t3), true, t3._eval$1("Iterable.E")));
+      t1 = parsed.root;
+      if (t1 != null)
+        C.JSArray_methods.insert$2(parsed.parts, 0, t1);
+      return parsed.parts;
+    },
+    normalize$1: function(path) {
+      var parsed;
+      if (!this._needsNormalization$1(path))
+        return path;
+      parsed = X.ParsedPath_ParsedPath$parse(path, this.style);
+      parsed.normalize$0();
+      return parsed.toString$0(0);
+    },
+    _needsNormalization$1: function(path) {
+      var t1, root, i, start, previous, t2, t3, previousPrevious, codeUnit, t4;
+      path.toString;
+      t1 = this.style;
+      root = t1.rootLength$1(path);
+      if (root !== 0) {
+        if (t1 === $.$get$Style_windows())
+          for (i = 0; i < root; ++i)
+            if (C.JSString_methods._codeUnitAt$1(path, i) === 47)
+              return true;
+        start = root;
+        previous = 47;
+      } else {
+        start = 0;
+        previous = null;
+      }
+      for (t2 = new H.CodeUnits(path)._string, t3 = t2.length, i = start, previousPrevious = null; i < t3; ++i, previousPrevious = previous, previous = codeUnit) {
+        codeUnit = C.JSString_methods.codeUnitAt$1(t2, i);
+        if (t1.isSeparator$1(codeUnit)) {
+          if (t1 === $.$get$Style_windows() && codeUnit === 47)
+            return true;
+          if (previous != null && t1.isSeparator$1(previous))
+            return true;
+          if (previous === 46)
+            t4 = previousPrevious == null || previousPrevious === 46 || t1.isSeparator$1(previousPrevious);
+          else
+            t4 = false;
+          if (t4)
+            return true;
+        }
+      }
+      if (previous == null)
+        return true;
+      if (t1.isSeparator$1(previous))
+        return true;
+      if (previous === 46)
+        t1 = previousPrevious == null || t1.isSeparator$1(previousPrevious) || previousPrevious === 46;
+      else
+        t1 = false;
+      if (t1)
+        return true;
+      return false;
+    },
+    relative$2$from: function(path, from) {
+      var fromParsed, pathParsed, t2, t3, t4, t5, _this = this,
+        _s26_ = 'Unable to find a path to "',
+        t1 = from == null;
+      if (t1 && _this.style.rootLength$1(path) <= 0)
+        return _this.normalize$1(path);
+      if (t1) {
+        t1 = _this._context$_current;
+        from = t1 != null ? t1 : D.current();
+      } else
+        from = _this.absolute$1(0, from);
+      t1 = _this.style;
+      if (t1.rootLength$1(from) <= 0 && t1.rootLength$1(path) > 0)
+        return _this.normalize$1(path);
+      if (t1.rootLength$1(path) <= 0 || t1.isRootRelative$1(path))
+        path = _this.absolute$1(0, path);
+      if (t1.rootLength$1(path) <= 0 && t1.rootLength$1(from) > 0)
+        throw H.wrapException(X.PathException$(_s26_ + H.S(path) + '" from "' + H.S(from) + '".'));
+      fromParsed = X.ParsedPath_ParsedPath$parse(from, t1);
+      fromParsed.normalize$0();
+      pathParsed = X.ParsedPath_ParsedPath$parse(path, t1);
+      pathParsed.normalize$0();
+      t2 = fromParsed.parts;
+      t3 = t2.length;
+      if (t3 !== 0) {
+        if (0 >= t3)
+          return H.ioore(t2, 0);
+        t2 = J.$eq$(t2[0], ".");
+      } else
+        t2 = false;
+      if (t2)
+        return pathParsed.toString$0(0);
+      t2 = fromParsed.root;
+      t3 = pathParsed.root;
+      if (t2 != t3)
+        t2 = t2 == null || t3 == null || !t1.pathsEqual$2(t2, t3);
+      else
+        t2 = false;
+      if (t2)
+        return pathParsed.toString$0(0);
+      while (true) {
+        t2 = fromParsed.parts;
+        t3 = t2.length;
+        if (t3 !== 0) {
+          t4 = pathParsed.parts;
+          t5 = t4.length;
+          if (t5 !== 0) {
+            if (0 >= t3)
+              return H.ioore(t2, 0);
+            t2 = t2[0];
+            if (0 >= t5)
+              return H.ioore(t4, 0);
+            t4 = t1.pathsEqual$2(t2, t4[0]);
+            t2 = t4;
+          } else
+            t2 = false;
+        } else
+          t2 = false;
+        if (!t2)
+          break;
+        C.JSArray_methods.removeAt$1(fromParsed.parts, 0);
+        C.JSArray_methods.removeAt$1(fromParsed.separators, 1);
+        C.JSArray_methods.removeAt$1(pathParsed.parts, 0);
+        C.JSArray_methods.removeAt$1(pathParsed.separators, 1);
+      }
+      t2 = fromParsed.parts;
+      t3 = t2.length;
+      if (t3 !== 0) {
+        if (0 >= t3)
+          return H.ioore(t2, 0);
+        t2 = J.$eq$(t2[0], "..");
+      } else
+        t2 = false;
+      if (t2)
+        throw H.wrapException(X.PathException$(_s26_ + H.S(path) + '" from "' + H.S(from) + '".'));
+      t2 = type$.String;
+      C.JSArray_methods.insertAll$2(pathParsed.parts, 0, P.List_List$filled(fromParsed.parts.length, "..", t2));
+      C.JSArray_methods.$indexSet(pathParsed.separators, 0, "");
+      C.JSArray_methods.insertAll$2(pathParsed.separators, 1, P.List_List$filled(fromParsed.parts.length, t1.get$separator(), t2));
+      t1 = pathParsed.parts;
+      t2 = t1.length;
+      if (t2 === 0)
+        return ".";
+      if (t2 > 1 && J.$eq$(C.JSArray_methods.get$last(t1), ".")) {
+        C.JSArray_methods.removeLast$0(pathParsed.parts);
+        t1 = pathParsed.separators;
+        C.JSArray_methods.removeLast$0(t1);
+        C.JSArray_methods.removeLast$0(t1);
+        C.JSArray_methods.add$1(t1, "");
+      }
+      pathParsed.root = "";
+      pathParsed.removeTrailingSeparators$0();
+      return pathParsed.toString$0(0);
+    },
+    relative$1: function(path) {
+      return this.relative$2$from(path, null);
+    },
+    _isWithinOrEquals$2: function($parent, child) {
+      var relative, childIsRootRelative, parentIsRootRelative, result, exception, _this = this,
+        t1 = _this.style,
+        parentIsAbsolute = t1.rootLength$1(H._checkStringNullable($parent)) > 0,
+        childIsAbsolute = t1.rootLength$1(H._checkStringNullable(child)) > 0;
+      if (parentIsAbsolute && !childIsAbsolute) {
+        child = _this.absolute$1(0, child);
+        if (t1.isRootRelative$1($parent))
+          $parent = _this.absolute$1(0, $parent);
+      } else if (childIsAbsolute && !parentIsAbsolute) {
+        $parent = _this.absolute$1(0, $parent);
+        if (t1.isRootRelative$1(child))
+          child = _this.absolute$1(0, child);
+      } else if (childIsAbsolute && parentIsAbsolute) {
+        childIsRootRelative = t1.isRootRelative$1(child);
+        parentIsRootRelative = t1.isRootRelative$1($parent);
+        if (childIsRootRelative && !parentIsRootRelative)
+          child = _this.absolute$1(0, child);
+        else if (parentIsRootRelative && !childIsRootRelative)
+          $parent = _this.absolute$1(0, $parent);
+      }
+      result = _this._isWithinOrEqualsFast$2($parent, child);
+      if (result !== C._PathRelation_inconclusive)
+        return result;
+      relative = null;
+      try {
+        relative = _this.relative$2$from(child, $parent);
+      } catch (exception) {
+        if (H.unwrapException(exception) instanceof X.PathException)
+          return C._PathRelation_different;
+        else
+          throw exception;
+      }
+      if (t1.rootLength$1(H._checkStringNullable(relative)) > 0)
+        return C._PathRelation_different;
+      if (J.$eq$(relative, "."))
+        return C._PathRelation_equal;
+      if (J.$eq$(relative, ".."))
+        return C._PathRelation_different;
+      return J.get$length$asx(relative) >= 3 && J.startsWith$1$s(relative, "..") && t1.isSeparator$1(J.codeUnitAt$1$s(relative, 2)) ? C._PathRelation_different : C._PathRelation_within;
+    },
+    _isWithinOrEqualsFast$2: function($parent, child) {
+      var t1, parentRootLength, childRootLength, t2, t3, i, childIndex, parentIndex, lastCodeUnit, lastParentSeparator, parentCodeUnit, childCodeUnit, parentIndex0, t4, direction, _this = this;
+      if ($parent === ".")
+        $parent = "";
+      t1 = _this.style;
+      parentRootLength = t1.rootLength$1($parent);
+      childRootLength = t1.rootLength$1(child);
+      if (parentRootLength !== childRootLength)
+        return C._PathRelation_different;
+      for (t2 = J.getInterceptor$s($parent), t3 = J.getInterceptor$s(child), i = 0; i < parentRootLength; ++i)
+        if (!t1.codeUnitsEqual$2(t2._codeUnitAt$1($parent, i), t3._codeUnitAt$1(child, i)))
+          return C._PathRelation_different;
+      t2 = $parent.length;
+      childIndex = childRootLength;
+      parentIndex = parentRootLength;
+      lastCodeUnit = 47;
+      lastParentSeparator = null;
+      while (true) {
+        if (!(parentIndex < t2 && childIndex < child.length))
+          break;
+        c$0: {
+          parentCodeUnit = C.JSString_methods.codeUnitAt$1($parent, parentIndex);
+          childCodeUnit = t3.codeUnitAt$1(child, childIndex);
+          if (t1.codeUnitsEqual$2(parentCodeUnit, childCodeUnit)) {
+            if (t1.isSeparator$1(parentCodeUnit))
+              lastParentSeparator = parentIndex;
+            ++parentIndex;
+            ++childIndex;
+            lastCodeUnit = parentCodeUnit;
+            break c$0;
+          }
+          if (t1.isSeparator$1(parentCodeUnit) && t1.isSeparator$1(lastCodeUnit)) {
+            parentIndex0 = parentIndex + 1;
+            lastParentSeparator = parentIndex;
+            parentIndex = parentIndex0;
+            break c$0;
+          } else if (t1.isSeparator$1(childCodeUnit) && t1.isSeparator$1(lastCodeUnit)) {
+            ++childIndex;
+            break c$0;
+          }
+          if (parentCodeUnit === 46 && t1.isSeparator$1(lastCodeUnit)) {
+            ++parentIndex;
+            if (parentIndex === t2)
+              break;
+            parentCodeUnit = C.JSString_methods.codeUnitAt$1($parent, parentIndex);
+            if (t1.isSeparator$1(parentCodeUnit)) {
+              parentIndex0 = parentIndex + 1;
+              lastParentSeparator = parentIndex;
+              parentIndex = parentIndex0;
+              break c$0;
+            }
+            if (parentCodeUnit === 46) {
+              ++parentIndex;
+              if (parentIndex === t2 || t1.isSeparator$1(C.JSString_methods.codeUnitAt$1($parent, parentIndex)))
+                return C._PathRelation_inconclusive;
+            }
+          }
+          if (childCodeUnit === 46 && t1.isSeparator$1(lastCodeUnit)) {
+            ++childIndex;
+            t4 = child.length;
+            if (childIndex === t4)
+              break;
+            childCodeUnit = C.JSString_methods.codeUnitAt$1(child, childIndex);
+            if (t1.isSeparator$1(childCodeUnit)) {
+              ++childIndex;
+              break c$0;
+            }
+            if (childCodeUnit === 46) {
+              ++childIndex;
+              if (childIndex === t4 || t1.isSeparator$1(C.JSString_methods.codeUnitAt$1(child, childIndex)))
+                return C._PathRelation_inconclusive;
+            }
+          }
+          if (_this._pathDirection$2(child, childIndex) !== C._PathDirection_988)
+            return C._PathRelation_inconclusive;
+          if (_this._pathDirection$2($parent, parentIndex) !== C._PathDirection_988)
+            return C._PathRelation_inconclusive;
+          return C._PathRelation_different;
+        }
+      }
+      if (childIndex === child.length) {
+        if (parentIndex === t2 || t1.isSeparator$1(C.JSString_methods.codeUnitAt$1($parent, parentIndex)))
+          lastParentSeparator = parentIndex;
+        else if (lastParentSeparator == null)
+          lastParentSeparator = Math.max(0, parentRootLength - 1);
+        direction = _this._pathDirection$2($parent, lastParentSeparator);
+        if (direction === C._PathDirection_8Gl)
+          return C._PathRelation_equal;
+        return direction === C._PathDirection_ZGD ? C._PathRelation_inconclusive : C._PathRelation_different;
+      }
+      direction = _this._pathDirection$2(child, childIndex);
+      if (direction === C._PathDirection_8Gl)
+        return C._PathRelation_equal;
+      if (direction === C._PathDirection_ZGD)
+        return C._PathRelation_inconclusive;
+      return t1.isSeparator$1(C.JSString_methods.codeUnitAt$1(child, childIndex)) || t1.isSeparator$1(lastCodeUnit) ? C._PathRelation_within : C._PathRelation_different;
+    },
+    _pathDirection$2: function(path, index) {
+      var t1, t2, i, depth, reachedRoot, i0, t3;
+      for (t1 = path.length, t2 = this.style, i = index, depth = 0, reachedRoot = false; i < t1;) {
+        while (true) {
+          if (!(i < t1 && t2.isSeparator$1(C.JSString_methods.codeUnitAt$1(path, i))))
+            break;
+          ++i;
+        }
+        if (i === t1)
+          break;
+        i0 = i;
+        while (true) {
+          if (!(i0 < t1 && !t2.isSeparator$1(C.JSString_methods.codeUnitAt$1(path, i0))))
+            break;
+          ++i0;
+        }
+        t3 = i0 - i;
+        if (!(t3 === 1 && C.JSString_methods.codeUnitAt$1(path, i) === 46))
+          if (t3 === 2 && C.JSString_methods.codeUnitAt$1(path, i) === 46 && C.JSString_methods.codeUnitAt$1(path, i + 1) === 46) {
+            --depth;
+            if (depth < 0)
+              break;
+            if (depth === 0)
+              reachedRoot = true;
+          } else
+            ++depth;
+        if (i0 === t1)
+          break;
+        i = i0 + 1;
+      }
+      if (depth < 0)
+        return C._PathDirection_ZGD;
+      if (depth === 0)
+        return C._PathDirection_8Gl;
+      if (reachedRoot)
+        return C._PathDirection_FIw;
+      return C._PathDirection_988;
+    },
+    toUri$1: function(path) {
+      var t2,
+        t1 = this.style;
+      if (t1.rootLength$1(path) <= 0)
+        return t1.relativePathToUri$1(path);
+      else {
+        t2 = this._context$_current;
+        return t1.absolutePathToUri$1(this.join$2(0, t2 != null ? t2 : D.current(), path));
+      }
+    },
+    prettyUri$1: function(uri) {
+      var path, rel, _this = this,
+        typedUri = M._parseUri(uri);
+      if (typedUri.get$scheme() === "file" && _this.style == $.$get$Style_url())
+        return typedUri.toString$0(0);
+      else if (typedUri.get$scheme() !== "file" && typedUri.get$scheme() !== "" && _this.style != $.$get$Style_url())
+        return typedUri.toString$0(0);
+      path = _this.normalize$1(_this.style.pathFromUri$1(M._parseUri(typedUri)));
+      rel = _this.relative$1(path);
+      return _this.split$1(0, rel).length > _this.split$1(0, path).length ? path : rel;
+    }
+  };
+  M.Context_join_closure.prototype = {
+    call$1: function(part) {
+      return H._checkStringNullable(part) != null;
+    },
+    $signature: 4
+  };
+  M.Context_joinAll_closure.prototype = {
+    call$1: function(part) {
+      return H._checkStringNullable(part) !== "";
+    },
+    $signature: 4
+  };
+  M.Context_split_closure.prototype = {
+    call$1: function(part) {
+      return H._checkStringNullable(part).length !== 0;
+    },
+    $signature: 4
+  };
+  M._validateArgList_closure.prototype = {
+    call$1: function(arg) {
+      H._checkStringNullable(arg);
+      return arg == null ? "null" : '"' + arg + '"';
+    },
+    $signature: 7
+  };
+  M._PathDirection.prototype = {
+    toString$0: function(_) {
+      return this.name;
+    }
+  };
+  M._PathRelation.prototype = {
+    toString$0: function(_) {
+      return this.name;
+    }
+  };
+  B.InternalStyle.prototype = {
+    getRoot$1: function(path) {
+      var t1,
+        $length = this.rootLength$1(path);
+      if ($length > 0)
+        return J.substring$2$s(path, 0, $length);
+      if (this.isRootRelative$1(path)) {
+        if (0 >= path.length)
+          return H.ioore(path, 0);
+        t1 = path[0];
+      } else
+        t1 = null;
+      return t1;
+    },
+    relativePathToUri$1: function(path) {
+      var segments = M.Context_Context(this).split$1(0, path);
+      if (this.isSeparator$1(J.codeUnitAt$1$s(path, path.length - 1)))
+        C.JSArray_methods.add$1(segments, "");
+      return P._Uri__Uri(null, null, segments, null);
+    },
+    codeUnitsEqual$2: function(codeUnit1, codeUnit2) {
+      return codeUnit1 === codeUnit2;
+    },
+    pathsEqual$2: function(path1, path2) {
+      return path1 == path2;
+    }
+  };
+  X.ParsedPath.prototype = {
+    get$hasTrailingSeparator: function() {
+      var t1 = this.parts;
+      if (t1.length !== 0)
+        t1 = J.$eq$(C.JSArray_methods.get$last(t1), "") || !J.$eq$(C.JSArray_methods.get$last(this.separators), "");
+      else
+        t1 = false;
+      return t1;
+    },
+    removeTrailingSeparators$0: function() {
+      var t1, t2, _this = this;
+      while (true) {
+        t1 = _this.parts;
+        if (!(t1.length !== 0 && J.$eq$(C.JSArray_methods.get$last(t1), "")))
+          break;
+        C.JSArray_methods.removeLast$0(_this.parts);
+        C.JSArray_methods.removeLast$0(_this.separators);
+      }
+      t1 = _this.separators;
+      t2 = t1.length;
+      if (t2 !== 0)
+        C.JSArray_methods.$indexSet(t1, t2 - 1, "");
+    },
+    normalize$0: function() {
+      var t1, t2, leadingDoubles, _i, part, t3, newSeparators, _this = this,
+        newParts = H.setRuntimeTypeInfo([], type$.JSArray_String);
+      for (t1 = _this.parts, t2 = t1.length, leadingDoubles = 0, _i = 0; _i < t1.length; t1.length === t2 || (0, H.throwConcurrentModificationError)(t1), ++_i) {
+        part = t1[_i];
+        t3 = J.getInterceptor$(part);
+        if (!(t3.$eq(part, ".") || t3.$eq(part, "")))
+          if (t3.$eq(part, "..")) {
+            t3 = newParts.length;
+            if (t3 !== 0) {
+              if (0 >= t3)
+                return H.ioore(newParts, -1);
+              newParts.pop();
+            } else
+              ++leadingDoubles;
+          } else
+            C.JSArray_methods.add$1(newParts, part);
+      }
+      if (_this.root == null)
+        C.JSArray_methods.insertAll$2(newParts, 0, P.List_List$filled(leadingDoubles, "..", type$.String));
+      if (newParts.length === 0 && _this.root == null)
+        C.JSArray_methods.add$1(newParts, ".");
+      newSeparators = P.List_List$generate(newParts.length, new X.ParsedPath_normalize_closure(_this), true, type$.String);
+      t1 = _this.root;
+      C.JSArray_methods.insert$2(newSeparators, 0, t1 != null && newParts.length !== 0 && _this.style.needsSeparator$1(t1) ? _this.style.get$separator() : "");
+      _this.set$parts(newParts);
+      _this.set$separators(newSeparators);
+      t1 = _this.root;
+      if (t1 != null && _this.style === $.$get$Style_windows()) {
+        t1.toString;
+        _this.root = H.stringReplaceAllUnchecked(t1, "/", "\\");
+      }
+      _this.removeTrailingSeparators$0();
+    },
+    toString$0: function(_) {
+      var i, t2, _this = this,
+        t1 = _this.root;
+      t1 = t1 != null ? t1 : "";
+      for (i = 0; i < _this.parts.length; ++i) {
+        t2 = _this.separators;
+        if (i >= t2.length)
+          return H.ioore(t2, i);
+        t2 = t1 + H.S(t2[i]);
+        t1 = _this.parts;
+        if (i >= t1.length)
+          return H.ioore(t1, i);
+        t1 = t2 + H.S(t1[i]);
+      }
+      t1 += H.S(C.JSArray_methods.get$last(_this.separators));
+      return t1.charCodeAt(0) == 0 ? t1 : t1;
+    },
+    set$parts: function(parts) {
+      this.parts = type$.List_String._check(parts);
+    },
+    set$separators: function(separators) {
+      this.separators = type$.List_String._check(separators);
+    }
+  };
+  X.ParsedPath_normalize_closure.prototype = {
+    call$1: function(_) {
+      return this.$this.style.get$separator();
+    },
+    $signature: 25
+  };
+  X.PathException.prototype = {
+    toString$0: function(_) {
+      return "PathException: " + this.message;
+    },
+    $isException: 1,
+    get$message: function(receiver) {
+      return this.message;
+    }
+  };
+  O.Style.prototype = {
+    toString$0: function(_) {
+      return this.get$name(this);
+    }
+  };
+  E.PosixStyle.prototype = {
+    containsSeparator$1: function(path) {
+      return C.JSString_methods.contains$1(path, "/");
+    },
+    isSeparator$1: function(codeUnit) {
+      return codeUnit === 47;
+    },
+    needsSeparator$1: function(path) {
+      var t1 = path.length;
+      return t1 !== 0 && C.JSString_methods.codeUnitAt$1(path, t1 - 1) !== 47;
+    },
+    rootLength$2$withDrive: function(path, withDrive) {
+      if (path.length !== 0 && C.JSString_methods._codeUnitAt$1(path, 0) === 47)
+        return 1;
+      return 0;
+    },
+    rootLength$1: function(path) {
+      return this.rootLength$2$withDrive(path, false);
+    },
+    isRootRelative$1: function(path) {
+      return false;
+    },
+    pathFromUri$1: function(uri) {
+      var t1;
+      if (uri.get$scheme() === "" || uri.get$scheme() === "file") {
+        t1 = uri.get$path(uri);
+        return P._Uri__uriDecode(t1, 0, t1.length, C.C_Utf8Codec, false);
+      }
+      throw H.wrapException(P.ArgumentError$("Uri " + uri.toString$0(0) + " must have scheme 'file:'."));
+    },
+    absolutePathToUri$1: function(path) {
+      var parsed = X.ParsedPath_ParsedPath$parse(path, this),
+        t1 = parsed.parts;
+      if (t1.length === 0)
+        C.JSArray_methods.addAll$1(t1, H.setRuntimeTypeInfo(["", ""], type$.JSArray_String));
+      else if (parsed.get$hasTrailingSeparator())
+        C.JSArray_methods.add$1(parsed.parts, "");
+      return P._Uri__Uri(null, null, parsed.parts, "file");
+    },
+    get$name: function() {
+      return "posix";
+    },
+    get$separator: function() {
+      return "/";
+    }
+  };
+  F.UrlStyle.prototype = {
+    containsSeparator$1: function(path) {
+      return C.JSString_methods.contains$1(path, "/");
+    },
+    isSeparator$1: function(codeUnit) {
+      return codeUnit === 47;
+    },
+    needsSeparator$1: function(path) {
+      var t1 = path.length;
+      if (t1 === 0)
+        return false;
+      if (C.JSString_methods.codeUnitAt$1(path, t1 - 1) !== 47)
+        return true;
+      return C.JSString_methods.endsWith$1(path, "://") && this.rootLength$1(path) === t1;
+    },
+    rootLength$2$withDrive: function(path, withDrive) {
+      var i, codeUnit, index, t2,
+        t1 = path.length;
+      if (t1 === 0)
+        return 0;
+      if (C.JSString_methods._codeUnitAt$1(path, 0) === 47)
+        return 1;
+      for (i = 0; i < t1; ++i) {
+        codeUnit = C.JSString_methods._codeUnitAt$1(path, i);
+        if (codeUnit === 47)
+          return 0;
+        if (codeUnit === 58) {
+          if (i === 0)
+            return 0;
+          index = C.JSString_methods.indexOf$2(path, "/", C.JSString_methods.startsWith$2(path, "//", i + 1) ? i + 3 : i);
+          if (index <= 0)
+            return t1;
+          if (!withDrive || t1 < index + 3)
+            return index;
+          if (!C.JSString_methods.startsWith$1(path, "file://"))
+            return index;
+          if (!B.isDriveLetter(path, index + 1))
+            return index;
+          t2 = index + 3;
+          return t1 === t2 ? t2 : index + 4;
+        }
+      }
+      return 0;
+    },
+    rootLength$1: function(path) {
+      return this.rootLength$2$withDrive(path, false);
+    },
+    isRootRelative$1: function(path) {
+      return path.length !== 0 && C.JSString_methods._codeUnitAt$1(path, 0) === 47;
+    },
+    pathFromUri$1: function(uri) {
+      return J.toString$0$(uri);
+    },
+    relativePathToUri$1: function(path) {
+      return P.Uri_parse(path);
+    },
+    absolutePathToUri$1: function(path) {
+      return P.Uri_parse(path);
+    },
+    get$name: function() {
+      return "url";
+    },
+    get$separator: function() {
+      return "/";
+    }
+  };
+  L.WindowsStyle.prototype = {
+    containsSeparator$1: function(path) {
+      return C.JSString_methods.contains$1(path, "/");
+    },
+    isSeparator$1: function(codeUnit) {
+      return codeUnit === 47 || codeUnit === 92;
+    },
+    needsSeparator$1: function(path) {
+      var t1 = path.length;
+      if (t1 === 0)
+        return false;
+      t1 = C.JSString_methods.codeUnitAt$1(path, t1 - 1);
+      return !(t1 === 47 || t1 === 92);
+    },
+    rootLength$2$withDrive: function(path, withDrive) {
+      var t2, index,
+        t1 = path.length;
+      if (t1 === 0)
+        return 0;
+      t2 = C.JSString_methods._codeUnitAt$1(path, 0);
+      if (t2 === 47)
+        return 1;
+      if (t2 === 92) {
+        if (t1 < 2 || C.JSString_methods._codeUnitAt$1(path, 1) !== 92)
+          return 1;
+        index = C.JSString_methods.indexOf$2(path, "\\", 2);
+        if (index > 0) {
+          index = C.JSString_methods.indexOf$2(path, "\\", index + 1);
+          if (index > 0)
+            return index;
+        }
+        return t1;
+      }
+      if (t1 < 3)
+        return 0;
+      if (!B.isAlphabetic(t2))
+        return 0;
+      if (C.JSString_methods._codeUnitAt$1(path, 1) !== 58)
+        return 0;
+      t1 = C.JSString_methods._codeUnitAt$1(path, 2);
+      if (!(t1 === 47 || t1 === 92))
+        return 0;
+      return 3;
+    },
+    rootLength$1: function(path) {
+      return this.rootLength$2$withDrive(path, false);
+    },
+    isRootRelative$1: function(path) {
+      return this.rootLength$1(path) === 1;
+    },
+    pathFromUri$1: function(uri) {
+      var path, t1;
+      if (uri.get$scheme() !== "" && uri.get$scheme() !== "file")
+        throw H.wrapException(P.ArgumentError$("Uri " + uri.toString$0(0) + " must have scheme 'file:'."));
+      path = uri.get$path(uri);
+      if (uri.get$host(uri) === "") {
+        if (path.length >= 3 && C.JSString_methods.startsWith$1(path, "/") && B.isDriveLetter(path, 1))
+          path = C.JSString_methods.replaceFirst$2(path, "/", "");
+      } else
+        path = "\\\\" + H.S(uri.get$host(uri)) + path;
+      t1 = H.stringReplaceAllUnchecked(path, "/", "\\");
+      return P._Uri__uriDecode(t1, 0, t1.length, C.C_Utf8Codec, false);
+    },
+    absolutePathToUri$1: function(path) {
+      var rootParts, t2,
+        parsed = X.ParsedPath_ParsedPath$parse(path, this),
+        t1 = parsed.root;
+      if (J.startsWith$1$s(t1, "\\\\")) {
+        rootParts = new H.WhereIterable(H.setRuntimeTypeInfo(t1.split("\\"), type$.JSArray_String), type$.bool_Function_String._check(new L.WindowsStyle_absolutePathToUri_closure()), type$.WhereIterable_String);
+        C.JSArray_methods.insert$2(parsed.parts, 0, rootParts.get$last(rootParts));
+        if (parsed.get$hasTrailingSeparator())
+          C.JSArray_methods.add$1(parsed.parts, "");
+        return P._Uri__Uri(rootParts.get$first(rootParts), null, parsed.parts, "file");
+      } else {
+        if (parsed.parts.length === 0 || parsed.get$hasTrailingSeparator())
+          C.JSArray_methods.add$1(parsed.parts, "");
+        t1 = parsed.parts;
+        t2 = parsed.root;
+        t2.toString;
+        t2 = H.stringReplaceAllUnchecked(t2, "/", "");
+        C.JSArray_methods.insert$2(t1, 0, H.stringReplaceAllUnchecked(t2, "\\", ""));
+        return P._Uri__Uri(null, null, parsed.parts, "file");
+      }
+    },
+    codeUnitsEqual$2: function(codeUnit1, codeUnit2) {
+      var upperCase1;
+      if (codeUnit1 === codeUnit2)
+        return true;
+      if (codeUnit1 === 47)
+        return codeUnit2 === 92;
+      if (codeUnit1 === 92)
+        return codeUnit2 === 47;
+      if ((codeUnit1 ^ codeUnit2) !== 32)
+        return false;
+      upperCase1 = codeUnit1 | 32;
+      return upperCase1 >= 97 && upperCase1 <= 122;
+    },
+    pathsEqual$2: function(path1, path2) {
+      var t1, t2, i;
+      if (path1 == path2)
+        return true;
+      t1 = path1.length;
+      if (t1 !== path2.length)
+        return false;
+      for (t2 = J.getInterceptor$s(path2), i = 0; i < t1; ++i)
+        if (!this.codeUnitsEqual$2(C.JSString_methods._codeUnitAt$1(path1, i), t2._codeUnitAt$1(path2, i)))
+          return false;
+      return true;
+    },
+    get$name: function() {
+      return "windows";
+    },
+    get$separator: function() {
+      return "\\";
+    }
+  };
+  L.WindowsStyle_absolutePathToUri_closure.prototype = {
+    call$1: function(part) {
+      return H._checkStringNullable(part) !== "";
+    },
+    $signature: 4
+  };
+  O.Pool.prototype = {
+    request$0: function(_) {
+      var t1, t2, _this = this;
+      if (_this._pool$_closeMemo._async_memoizer$_completer.future._state !== 0)
+        throw H.wrapException(P.StateError$("request() may not be called on a closed Pool."));
+      t1 = _this._allocatedResources;
+      if (t1 < _this._maxAllocatedResources) {
+        _this._allocatedResources = t1 + 1;
+        t1 = new P._Future($.Zone__current, type$._Future_PoolResource);
+        t1._asyncComplete$1(new O.PoolResource(_this));
+        return t1;
+      } else {
+        t1 = _this._onReleaseCallbacks;
+        if (!t1.get$isEmpty(t1))
+          return _this._runOnRelease$1(t1.removeFirst$0());
+        else {
+          t1 = new P._Future($.Zone__current, type$._Future_PoolResource);
+          t2 = _this._requestedResources;
+          t2._collection$_add$1(t2.$ti._precomputed1._check(new P._AsyncCompleter(t1, type$._AsyncCompleter_PoolResource)));
+          _this._resetTimer$0();
+          return t1;
+        }
+      }
+    },
+    withResource$1$1: function(callback, $T) {
+      $T._eval$1("0/()")._check(callback);
+      return this.withResource$body$Pool(callback, $T, $T);
+    },
+    withResource$body$Pool: function(callback, $T, $async$type) {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter($async$type),
+        $async$returnValue, $async$handler = 2, $async$currentError, $async$next = [], $async$self = this, resource, t1;
+      var $async$withResource$1$1 = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1) {
+          $async$currentError = $async$result;
+          $async$goto = $async$handler;
+        }
+        while (true)
+          switch ($async$goto) {
+            case 0:
+              // Function start
+              if ($async$self._pool$_closeMemo._async_memoizer$_completer.future._state !== 0)
+                throw H.wrapException(P.StateError$("withResource() may not be called on a closed Pool."));
+              $async$goto = 3;
+              return P._asyncAwait($async$self.request$0(0), $async$withResource$1$1);
+            case 3:
+              // returning from await.
+              resource = $async$result;
+              $async$handler = 4;
+              $async$goto = 7;
+              return P._asyncAwait(callback.call$0(), $async$withResource$1$1);
+            case 7:
+              // returning from await.
+              t1 = $async$result;
+              $async$returnValue = t1;
+              $async$next = [1];
+              // goto finally
+              $async$goto = 5;
+              break;
+              $async$next.push(6);
+              // goto finally
+              $async$goto = 5;
+              break;
+            case 4:
+              // uncaught
+              $async$next = [2];
+            case 5:
+              // finally
+              $async$handler = 2;
+              resource.release$0();
+              // goto the next finally handler
+              $async$goto = $async$next.pop();
+              break;
+            case 6:
+              // after finally
+            case 1:
+              // return
+              return P._asyncReturn($async$returnValue, $async$completer);
+            case 2:
+              // rethrow
+              return P._asyncRethrow($async$currentError, $async$completer);
+          }
+      });
+      return P._asyncStartSync($async$withResource$1$1, $async$completer);
+    },
+    close$0: function(_) {
+      return this._pool$_closeMemo.runOnce$1(new O.Pool_close_closure(this));
+    },
+    _onResourceReleaseAllowed$1: function(onRelease) {
+      var t1, zone, t2, _this = this;
+      type$.dynamic_Function._check(onRelease);
+      _this._resetTimer$0();
+      t1 = _this._requestedResources;
+      if (!t1.get$isEmpty(t1))
+        t1.removeFirst$0().complete$1(_this._runOnRelease$1(onRelease));
+      else {
+        t1 = type$.dynamic;
+        if (_this._pool$_closeMemo._async_memoizer$_completer.future._state !== 0) {
+          _this._closeGroup.add$1(0, P.Future_Future$sync(onRelease, t1));
+          if (--_this._allocatedResources === 0)
+            _this._closeGroup.close$0(0);
+        } else {
+          zone = $.Zone__current;
+          t2 = _this._onReleaseCallbacks;
+          t2._collection$_add$1(t2.$ti._precomputed1._check(new O.Pool__onResourceReleaseAllowed_closure(zone, zone.registerCallback$1$1(onRelease, t1))));
+        }
+      }
+    },
+    _runOnRelease$1: function(onRelease) {
+      var t1, t2;
+      P.Future_Future$sync(type$.dynamic_Function._check(onRelease), type$.dynamic).then$1$1(new O.Pool__runOnRelease_closure(this), type$.Null).catchError$1(new O.Pool__runOnRelease_closure0(this));
+      t1 = new P._Future($.Zone__current, type$._Future_PoolResource);
+      t2 = this._onReleaseCompleters;
+      t2._collection$_add$1(t2.$ti._precomputed1._check(new P._SyncCompleter(t1, type$._SyncCompleter_PoolResource)));
+      return t1;
+    },
+    _resetTimer$0: function() {
+      var t2,
+        t1 = this._timer;
+      if (t1 == null)
+        return;
+      t2 = this._requestedResources;
+      if (t2._head === t2._tail)
+        t1._restartable_timer$_timer.cancel$0();
+      else {
+        t1._restartable_timer$_timer.cancel$0();
+        t1._restartable_timer$_timer = P.Timer_Timer(t1._restartable_timer$_duration, t1._callback);
+      }
+    }
+  };
+  O.Pool_close_closure.prototype = {
+    call$0: function() {
+      var t3, t4, callback,
+        t1 = this.$this,
+        t2 = t1._closeGroup;
+      if (t2 != null)
+        return t2._future_group$_completer.future;
+      t1._resetTimer$0();
+      t1._closeGroup = new F.FutureGroup(new P._AsyncCompleter(new P._Future($.Zone__current, type$._Future_List_dynamic), type$._AsyncCompleter_List_dynamic), H.setRuntimeTypeInfo([], type$.JSArray_dynamic), type$.FutureGroup_dynamic);
+      for (t2 = t1._onReleaseCallbacks, t3 = P._ListQueueIterator$(t2, t2.$ti._precomputed1), t4 = type$.dynamic; t3.moveNext$0();) {
+        callback = t3._collection$_current;
+        t1._closeGroup.add$1(0, P.Future_Future$sync(callback, t4));
+      }
+      t1._allocatedResources = t1._allocatedResources - t2.get$length(t2);
+      t2.clear$0(0);
+      if (t1._allocatedResources === 0)
+        t1._closeGroup.close$0(0);
+      return t1._closeGroup._future_group$_completer.future;
+    },
+    $signature: 50
+  };
+  O.Pool__onResourceReleaseAllowed_closure.prototype = {
+    call$0: function() {
+      return this.zone.run$1$1(this.registered, type$.void);
+    },
+    $signature: 1
+  };
+  O.Pool__runOnRelease_closure.prototype = {
+    call$1: function(value) {
+      var t1 = this.$this;
+      t1._onReleaseCompleters.removeFirst$0().complete$1(new O.PoolResource(t1));
+    },
+    $signature: 3
+  };
+  O.Pool__runOnRelease_closure0.prototype = {
+    call$2: function(error, stackTrace) {
+      type$.StackTrace._check(stackTrace);
+      this.$this._onReleaseCompleters.removeFirst$0().completeError$2(error, stackTrace);
+    },
+    $signature: 5
+  };
+  O.PoolResource.prototype = {
+    release$0: function() {
+      var t1, t2;
+      if (this._released)
+        throw H.wrapException(P.StateError$("A PoolResource may only be released once."));
+      this._released = true;
+      t1 = this._pool;
+      t1._resetTimer$0();
+      t2 = t1._requestedResources;
+      if (!t2.get$isEmpty(t2))
+        t2.removeFirst$0().complete$1(new O.PoolResource(t1));
+      else {
+        t2 = --t1._allocatedResources;
+        if (t1._pool$_closeMemo._async_memoizer$_completer.future._state !== 0 && t2 === 0)
+          t1._closeGroup.close$0(0);
+      }
+    }
+  };
+  O.mapStackTrace_closure.prototype = {
+    call$1: function(trace) {
+      var _this = this;
+      return Y.Trace_Trace$from(O.mapStackTrace(_this.sourceMap, type$.Trace._check(trace), _this.minified, _this._box_0.packageResolver, _this.sdkRoot));
+    },
+    $signature: 45
+  };
+  O.mapStackTrace_closure0.prototype = {
+    call$1: function(frame) {
+      var column, t1, t2, span, sourceUrl, t3, packageUrl, t4, _this = this;
+      type$.Frame._check(frame);
+      if (frame.get$line() == null)
+        return null;
+      column = frame.get$column() == null ? 0 : frame.get$column();
+      t1 = frame.get$line();
+      if (typeof t1 !== "number")
+        return t1.$sub();
+      if (typeof column !== "number")
+        return column.$sub();
+      t2 = frame.get$uri();
+      t2 = t2 == null ? null : t2.toString$0(0);
+      span = _this.sourceMap.spanFor$3$uri(t1 - 1, column - 1, t2);
+      if (span == null)
+        return null;
+      sourceUrl = J.toString$0$(span.get$sourceUrl());
+      if (_this.sdkRoot != null && $.$get$url()._isWithinOrEquals$2(_this.sdkLib, sourceUrl) === C._PathRelation_within)
+        sourceUrl = C.JSString_methods.$add("dart:", $.$get$url().relative$2$from(sourceUrl, _this.sdkLib));
+      else {
+        t1 = _this._box_0;
+        t2 = t1.packageResolver;
+        if (t2 != null)
+          if (t2.get$packageRoot() != null && $.$get$url()._isWithinOrEquals$2(J.toString$0$(t1.packageResolver.get$packageRoot()), sourceUrl) === C._PathRelation_within)
+            sourceUrl = C.JSString_methods.$add("package:", $.$get$url().relative$2$from(sourceUrl, J.toString$0$(t1.packageResolver.get$packageRoot())));
+          else if (t1.packageResolver.get$packageConfigMap() != null)
+            for (t2 = t1.packageResolver.get$packageConfigMap()._map.get$keys(), t2 = t2.get$iterator(t2); t2.moveNext$0();) {
+              t3 = t2.get$current();
+              packageUrl = J.toString$0$(t1.packageResolver.get$packageConfigMap()._map.$index(0, t3));
+              t4 = $.$get$url();
+              if (t4._isWithinOrEquals$2(packageUrl, sourceUrl) !== C._PathRelation_within)
+                continue;
+              sourceUrl = C.JSString_methods.$add("package:" + H.S(t3) + "/", t4.relative$2$from(sourceUrl, packageUrl));
+              break;
+            }
+      }
+      t1 = P.Uri_parse(sourceUrl);
+      t2 = span.get$start().get$line();
+      if (typeof t2 !== "number")
+        return t2.$add();
+      t3 = span.get$start().get$column();
+      if (_this.minified)
+        t4 = span.get$isIdentifier() ? span.get$text() : frame.get$member();
+      else
+        t4 = O._prettifyMember(frame.get$member());
+      return new A.Frame(t1, t2 + 1, t3 + 1, t4);
+    },
+    $signature: 46
+  };
+  O.mapStackTrace_closure1.prototype = {
+    call$1: function(frame) {
+      return type$.Frame._check(frame) != null;
+    },
+    $signature: 21
+  };
+  O._prettifyMember_closure.prototype = {
+    call$1: function(match) {
+      return C.JSString_methods.$mul(".<fn>", match.$index(0, 1).length);
+    },
+    $signature: 24
+  };
+  O._prettifyMember_closure0.prototype = {
+    call$1: function(match) {
+      return J.$add$ansx(match.$index(0, 1), ".");
+    },
+    $signature: 24
+  };
+  T.Mapping.prototype = {};
+  T.MultiSectionMapping.prototype = {
+    MultiSectionMapping$fromJson$3$mapUrl: function(sections, otherMaps, mapUrl) {
+      var t1, t2, t3, t4, t5, section, t6, line, column, url, map, _s6_ = "offset", _null = null;
+      for (t1 = J.get$iterator$ax(sections), t2 = this._maps, t3 = type$.Map_dynamic_dynamic, t4 = this._lineStart, t5 = this._columnStart; t1.moveNext$0();) {
+        section = t1.get$current();
+        t6 = J.getInterceptor$asx(section);
+        if (t6.$index(section, _s6_) == null)
+          throw H.wrapException(P.FormatException$("section missing offset", _null, _null));
+        line = J.$index$asx(t6.$index(section, _s6_), "line");
+        if (line == null)
+          throw H.wrapException(P.FormatException$("offset missing line", _null, _null));
+        column = J.$index$asx(t6.$index(section, _s6_), "column");
+        if (column == null)
+          throw H.wrapException(P.FormatException$("offset missing column", _null, _null));
+        C.JSArray_methods.add$1(t4, H._checkIntNullable(line));
+        C.JSArray_methods.add$1(t5, H._checkIntNullable(column));
+        url = t6.$index(section, "url");
+        map = t6.$index(section, "map");
+        t6 = url != null;
+        if (t6 && map != null)
+          throw H.wrapException(P.FormatException$("section can't use both url and map entries", _null, _null));
+        else if (t6) {
+          t6 = P.FormatException$("section contains refers to " + H.S(url) + ', but no map was given for it. Make sure a map is passed in "otherMaps"', _null, _null);
+          throw H.wrapException(t6);
+        } else if (map != null)
+          C.JSArray_methods.add$1(t2, T.parseJson(t3._check(map), mapUrl, otherMaps));
+        else
+          throw H.wrapException(P.FormatException$("section missing url or map", _null, _null));
+      }
+      if (t4.length === 0)
+        throw H.wrapException(P.FormatException$("expected at least one section", _null, _null));
+    },
+    _indexFor$2: function(line, column) {
+      var t1, t2, t3, t4, i, t5;
+      for (t1 = this._lineStart, t2 = t1.length, t3 = this._columnStart, t4 = t3.length, i = 0; i < t2; ++i) {
+        t5 = t1[i];
+        if (line < t5)
+          return i - 1;
+        if (line === t5) {
+          if (i >= t4)
+            return H.ioore(t3, i);
+          t5 = column < t3[i];
+        } else
+          t5 = false;
+        if (t5)
+          return i - 1;
+      }
+      return t2 - 1;
+    },
+    spanFor$4$files$uri: function(line, column, files, uri) {
+      var index, t1, t2, t3, _this = this;
+      type$.Map_String_SourceFile._check(files);
+      index = _this._indexFor$2(line, column);
+      t1 = _this._maps;
+      if (index < 0 || index >= t1.length)
+        return H.ioore(t1, index);
+      t1 = t1[index];
+      t2 = _this._lineStart;
+      if (index >= t2.length)
+        return H.ioore(t2, index);
+      t2 = t2[index];
+      t3 = _this._columnStart;
+      if (index >= t3.length)
+        return H.ioore(t3, index);
+      return t1.spanFor$3$files(line - t2, column - t3[index], files);
+    },
+    spanFor$3$uri: function(line, column, uri) {
+      return this.spanFor$4$files$uri(line, column, null, uri);
+    },
+    spanFor$3$files: function(line, column, files) {
+      return this.spanFor$4$files$uri(line, column, files, null);
+    },
+    toString$0: function(_) {
+      var t2, t3, t4, i, _this = this,
+        t1 = H.getRuntimeType(_this).toString$0(0) + " : [";
+      for (t2 = _this._lineStart, t3 = _this._columnStart, t4 = _this._maps, i = 0; i < t2.length; ++i) {
+        t1 = t1 + "(" + t2[i] + ",";
+        if (i >= t3.length)
+          return H.ioore(t3, i);
+        t1 = t1 + t3[i] + ":";
+        if (i >= t4.length)
+          return H.ioore(t4, i);
+        t1 = t1 + t4[i].toString$0(0) + ")";
+      }
+      t1 += "]";
+      return t1.charCodeAt(0) == 0 ? t1 : t1;
+    }
+  };
+  T.MappingBundle.prototype = {
+    MappingBundle$fromJson$2$mapUrl: function(json, mapUrl) {
+      var t1, t2, t3, t4, t5;
+      for (t1 = J.get$iterator$ax(json), t2 = type$.Map_dynamic_dynamic, t3 = type$.SingleMapping, t4 = this._mappings; t1.moveNext$0();) {
+        t5 = t3._as(T.parseJson(t2._check(t1.get$current()), mapUrl, null));
+        t4.$indexSet(0, t5.targetUrl, t5);
+      }
+    },
+    toString$0: function(_) {
+      var t1, t2;
+      for (t1 = this._mappings.get$values(), t1 = t1.get$iterator(t1), t2 = ""; t1.moveNext$0();)
+        t2 += J.toString$0$(t1.get$current());
+      return t2.charCodeAt(0) == 0 ? t2 : t2;
+    },
+    spanFor$4$files$uri: function(line, column, files, uri) {
+      var separatorCodeUnits, t1, t2, onBoundary, i, candidate, $location;
+      type$.Map_String_SourceFile._check(files);
+      if (uri == null)
+        throw H.wrapException(P.ArgumentError$notNull("uri"));
+      separatorCodeUnits = H.setRuntimeTypeInfo([47, 58], type$.JSArray_int);
+      for (t1 = uri.length, t2 = this._mappings, onBoundary = true, i = 0; i < t1; ++i) {
+        if (onBoundary) {
+          candidate = C.JSString_methods.substring$1(uri, i);
+          if (t2.containsKey$1(candidate))
+            return t2.$index(0, candidate).spanFor$4$files$uri(line, column, files, candidate);
+        }
+        onBoundary = C.JSArray_methods.contains$1(separatorCodeUnits, C.JSString_methods._codeUnitAt$1(uri, i));
+      }
+      $location = V.SourceLocation$(line * 1000000 + column, column, line, P.Uri_parse(uri));
+      t1 = new G.SourceMapSpan(false, $location, $location, "");
+      t1.SourceSpanBase$3($location, $location, "");
+      return t1;
+    },
+    spanFor$3$uri: function(line, column, uri) {
+      return this.spanFor$4$files$uri(line, column, null, uri);
+    }
+  };
+  T.SingleMapping.prototype = {
+    SingleMapping$fromJson$2$mapUrl: function(map, mapUrl) {
+      var t5, source, t6, t7, tokenizer, entries, line, column, srcUrlId, srcLine, srcColumn, srcNameId, _this = this,
+        _s14_ = "sourcesContent",
+        _null = null,
+        sourcesContent = map.$index(0, _s14_) == null ? C.List_empty0 : P.List_List$from(type$.Iterable_dynamic._check(map.$index(0, _s14_)), true, type$.String),
+        t1 = type$.Uri,
+        t2 = _this.files,
+        t3 = _this.urls,
+        t4 = type$.JSArray_int,
+        i = 0;
+      while (true) {
+        t5 = t3.length;
+        if (!(i < t5 && i < sourcesContent.length))
+          break;
+        c$0: {
+          if (i >= sourcesContent.length)
+            return H.ioore(sourcesContent, i);
+          source = sourcesContent[i];
+          if (source == null)
+            break c$0;
+          H._checkStringNullable(source);
+          if (i >= t5)
+            return H.ioore(t3, i);
+          t5 = t3[i];
+          t6 = new H.CodeUnits(source);
+          t7 = H.setRuntimeTypeInfo([0], t4);
+          t7 = new Y.SourceFile(t1._check(typeof t5 == "string" ? P.Uri_parse(t5) : t5), t7, new Uint32Array(H._ensureNativeList(t6.toList$0(t6))));
+          t7.SourceFile$decoded$2$url(t6, t5);
+          C.JSArray_methods.$indexSet(t2, i, t7);
+        }
+        ++i;
+      }
+      t1 = H._checkStringNullable(map.$index(0, "mappings"));
+      t2 = t1.length;
+      tokenizer = new T._MappingTokenizer(t1, t2);
+      t1 = type$.JSArray_TargetEntry;
+      entries = H.setRuntimeTypeInfo([], t1);
+      t4 = _this.names;
+      t5 = t2 - 1;
+      t2 = t2 > 0;
+      t6 = _this.lines;
+      line = 0;
+      column = 0;
+      srcUrlId = 0;
+      srcLine = 0;
+      srcColumn = 0;
+      srcNameId = 0;
+      while (true) {
+        if (!(tokenizer.index < t5 && t2))
+          break;
+        c$1: {
+          if (tokenizer.get$nextKind().isNewLine) {
+            if (entries.length !== 0) {
+              C.JSArray_methods.add$1(t6, new T.TargetLineEntry(line, entries));
+              entries = H.setRuntimeTypeInfo([], t1);
+            }
+            ++line;
+            ++tokenizer.index;
+            column = 0;
+            break c$1;
+          }
+          if (tokenizer.get$nextKind().isNewSegment)
+            throw H.wrapException(_this._segmentError$2(0, line));
+          column += L.decodeVlq(tokenizer);
+          t7 = tokenizer.get$nextKind();
+          if (!(!t7.isNewLine && !t7.isNewSegment && !t7.isEof))
+            C.JSArray_methods.add$1(entries, new T.TargetEntry(column, _null, _null, _null, _null));
+          else {
+            srcUrlId += L.decodeVlq(tokenizer);
+            if (srcUrlId >= t3.length)
+              throw H.wrapException(P.StateError$("Invalid source url id. " + H.S(_this.targetUrl) + ", " + line + ", " + srcUrlId));
+            t7 = tokenizer.get$nextKind();
+            if (!(!t7.isNewLine && !t7.isNewSegment && !t7.isEof))
+              throw H.wrapException(_this._segmentError$2(2, line));
+            srcLine += L.decodeVlq(tokenizer);
+            t7 = tokenizer.get$nextKind();
+            if (!(!t7.isNewLine && !t7.isNewSegment && !t7.isEof))
+              throw H.wrapException(_this._segmentError$2(3, line));
+            srcColumn += L.decodeVlq(tokenizer);
+            t7 = tokenizer.get$nextKind();
+            if (!(!t7.isNewLine && !t7.isNewSegment && !t7.isEof))
+              C.JSArray_methods.add$1(entries, new T.TargetEntry(column, srcUrlId, srcLine, srcColumn, _null));
+            else {
+              srcNameId += L.decodeVlq(tokenizer);
+              if (srcNameId >= t4.length)
+                throw H.wrapException(P.StateError$("Invalid name id: " + H.S(_this.targetUrl) + ", " + line + ", " + srcNameId));
+              C.JSArray_methods.add$1(entries, new T.TargetEntry(column, srcUrlId, srcLine, srcColumn, srcNameId));
+            }
+          }
+          if (tokenizer.get$nextKind().isNewSegment)
+            ++tokenizer.index;
+        }
+      }
+      if (entries.length !== 0)
+        C.JSArray_methods.add$1(t6, new T.TargetLineEntry(line, entries));
+      map.forEach$1(0, new T.SingleMapping$fromJson_closure(_this));
+    },
+    _segmentError$2: function(seen, line) {
+      return new P.StateError("Invalid entry in sourcemap, expected 1, 4, or 5 values, but got " + seen + ".\ntargeturl: " + H.S(this.targetUrl) + ", line: " + line);
+    },
+    _findLine$1: function(line) {
+      var t2,
+        t1 = this.lines,
+        index = O.binarySearch(t1, new T.SingleMapping__findLine_closure(line));
+      if (index <= 0)
+        t1 = null;
+      else {
+        t2 = index - 1;
+        if (t2 >= t1.length)
+          return H.ioore(t1, t2);
+        t2 = t1[t2];
+        t1 = t2;
+      }
+      return t1;
+    },
+    _findColumn$3: function(line, column, lineEntry) {
+      var entries, index, t1;
+      if (lineEntry == null || lineEntry.entries.length === 0)
+        return null;
+      if (lineEntry.line !== line)
+        return C.JSArray_methods.get$last(lineEntry.entries);
+      entries = lineEntry.entries;
+      index = O.binarySearch(entries, new T.SingleMapping__findColumn_closure(column));
+      if (index <= 0)
+        t1 = null;
+      else {
+        t1 = index - 1;
+        if (t1 >= entries.length)
+          return H.ioore(entries, t1);
+        t1 = entries[t1];
+      }
+      return t1;
+    },
+    spanFor$4$files$uri: function(line, column, files, uri) {
+      var entry, url, t1, t2, start, t3, _this = this;
+      type$.Map_String_SourceFile._check(files);
+      entry = _this._findColumn$3(line, column, _this._findLine$1(line));
+      if (entry == null || entry.sourceUrlId == null)
+        return null;
+      url = C.JSArray_methods.$index(_this.urls, entry.sourceUrlId);
+      t1 = _this.sourceRoot;
+      if (t1 != null)
+        url = t1 + H.S(url);
+      t1 = _this._parser$_mapUrl;
+      t1 = t1 == null ? url : t1.resolve$1(url);
+      t2 = entry.sourceLine;
+      start = V.SourceLocation$(0, entry.sourceColumn, t2, t1);
+      t1 = entry.sourceNameId;
+      if (t1 != null) {
+        t2 = _this.names;
+        if (t1 >>> 0 !== t1 || t1 >= t2.length)
+          return H.ioore(t2, t1);
+        t1 = t2[t1];
+        t2 = t1.length;
+        t2 = V.SourceLocation$(start.offset + t2, start.column + t2, start.line, start.sourceUrl);
+        t3 = new G.SourceMapSpan(true, start, t2, t1);
+        t3.SourceSpanBase$3(start, t2, t1);
+        return t3;
+      } else {
+        t1 = new G.SourceMapSpan(false, start, start, "");
+        t1.SourceSpanBase$3(start, start, "");
+        return t1;
+      }
+    },
+    spanFor$3$uri: function(line, column, uri) {
+      return this.spanFor$4$files$uri(line, column, null, uri);
+    },
+    spanFor$3$files: function(line, column, files) {
+      return this.spanFor$4$files$uri(line, column, files, null);
+    },
+    toString$0: function(_) {
+      var _this = this,
+        t1 = H.getRuntimeType(_this).toString$0(0);
+      t1 + " : [";
+      t1 = t1 + " : [targetUrl: " + H.S(_this.targetUrl) + ", sourceRoot: " + H.S(_this.sourceRoot) + ", urls: " + H.S(_this.urls) + ", names: " + H.S(_this.names) + ", lines: " + H.S(_this.lines) + "]";
+      return t1.charCodeAt(0) == 0 ? t1 : t1;
+    }
+  };
+  T.SingleMapping$fromJson_closure.prototype = {
+    call$2: function($name, value) {
+      if (J.startsWith$1$s($name, "x_"))
+        this.$this.extensions.$indexSet(0, H._checkStringNullable($name), value);
+    },
+    $signature: 6
+  };
+  T.SingleMapping__findLine_closure.prototype = {
+    call$1: function(e) {
+      return e.get$line() > this.line;
+    },
+    $signature: 9
+  };
+  T.SingleMapping__findColumn_closure.prototype = {
+    call$1: function(e) {
+      return e.get$column() > this.column;
+    },
+    $signature: 9
+  };
+  T.TargetLineEntry.prototype = {
+    toString$0: function(_) {
+      return H.getRuntimeType(this).toString$0(0) + ": " + this.line + " " + H.S(this.entries);
+    },
+    get$line: function() {
+      return this.line;
+    }
+  };
+  T.TargetEntry.prototype = {
+    toString$0: function(_) {
+      var _this = this;
+      return H.getRuntimeType(_this).toString$0(0) + ": (" + _this.column + ", " + H.S(_this.sourceUrlId) + ", " + H.S(_this.sourceLine) + ", " + H.S(_this.sourceColumn) + ", " + H.S(_this.sourceNameId) + ")";
+    },
+    get$column: function() {
+      return this.column;
+    }
+  };
+  T._MappingTokenizer.prototype = {
+    moveNext$0: function() {
+      return ++this.index < this._parser$_length;
+    },
+    get$current: function() {
+      var t2,
+        t1 = this.index;
+      if (t1 >= 0 && t1 < this._parser$_length) {
+        t2 = this._internal;
+        if (t1 < 0 || t1 >= t2.length)
+          return H.ioore(t2, t1);
+        t1 = t2[t1];
+      } else
+        t1 = null;
+      return t1;
+    },
+    get$hasTokens: function() {
+      var t1 = this._parser$_length;
+      return this.index < t1 - 1 && t1 > 0;
+    },
+    get$nextKind: function() {
+      var t1, t2, next;
+      if (!this.get$hasTokens())
+        return C._TokenKind_false_false_true;
+      t1 = this._internal;
+      t2 = this.index + 1;
+      if (t2 < 0 || t2 >= t1.length)
+        return H.ioore(t1, t2);
+      next = t1[t2];
+      if (next === ";")
+        return C._TokenKind_true_false_false;
+      if (next === ",")
+        return C._TokenKind_false_true_false;
+      return C._TokenKind_false_false_false;
+    },
+    toString$0: function(_) {
+      var t1, i, t2, t3, _this = this;
+      for (t1 = _this._internal, i = 0, t2 = ""; i < _this.index; ++i) {
+        if (i >= t1.length)
+          return H.ioore(t1, i);
+        t2 += t1[i];
+      }
+      t2 += "\x1b[31m";
+      t2 = t2 + H.S(_this.get$current() == null ? "" : _this.get$current()) + "\x1b[0m";
+      for (i = _this.index + 1, t3 = t1.length; i < t3; ++i) {
+        if (i < 0)
+          return H.ioore(t1, i);
+        t2 += t1[i];
+      }
+      t1 = t2 + (" (" + _this.index + ")");
+      return t1.charCodeAt(0) == 0 ? t1 : t1;
+    },
+    $isIterator: 1
+  };
+  T._TokenKind.prototype = {};
+  G.SourceMapSpan.prototype = {
+    get$isIdentifier: function() {
+      return this.isIdentifier;
+    }
+  };
+  L.closure.prototype = {
+    call$0: function() {
+      var i,
+        map = P.LinkedHashMap_LinkedHashMap$_empty(type$.String, type$.int);
+      for (i = 0; i < 64; ++i)
+        map.$indexSet(0, "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"[i], i);
+      return map;
+    },
+    $signature: 93
+  };
+  Y.SourceFile.prototype = {
+    get$length: function(_) {
+      return this._decodedChars.length;
+    },
+    get$lines: function() {
+      return this._lineStarts.length;
+    },
+    SourceFile$decoded$2$url: function(decodedChars, url) {
+      var t1, t2, t3, i, c, j, t4;
+      for (t1 = this._decodedChars, t2 = t1.length, t3 = this._lineStarts, i = 0; i < t2; ++i) {
+        c = t1[i];
+        if (c === 13) {
+          j = i + 1;
+          if (j < t2) {
+            if (j >= t2)
+              return H.ioore(t1, j);
+            t4 = t1[j] !== 10;
+          } else
+            t4 = true;
+          if (t4)
+            c = 10;
+        }
+        if (c === 10)
+          C.JSArray_methods.add$1(t3, i + 1);
+      }
+    },
+    span$2: function(start, end) {
+      return Y._FileSpan$(this, start, end);
+    },
+    getLine$1: function(offset) {
+      var t1, _this = this;
+      if (offset < 0)
+        throw H.wrapException(P.RangeError$("Offset may not be negative, was " + offset + "."));
+      else if (offset > _this._decodedChars.length)
+        throw H.wrapException(P.RangeError$("Offset " + offset + " must not be greater than the number of characters in the file, " + _this.get$length(_this) + "."));
+      t1 = _this._lineStarts;
+      if (offset < C.JSArray_methods.get$first(t1))
+        return -1;
+      if (offset >= C.JSArray_methods.get$last(t1))
+        return t1.length - 1;
+      if (_this._isNearCachedLine$1(offset))
+        return _this._cachedLine;
+      return _this._cachedLine = _this._binarySearch$1(offset) - 1;
+    },
+    _isNearCachedLine$1: function(offset) {
+      var t2, t3, t4, _this = this,
+        t1 = _this._cachedLine;
+      if (t1 == null)
+        return false;
+      t2 = _this._lineStarts;
+      if (t1 >>> 0 !== t1 || t1 >= t2.length)
+        return H.ioore(t2, t1);
+      if (offset < t2[t1])
+        return false;
+      t1 = _this._cachedLine;
+      t3 = t2.length;
+      if (typeof t1 !== "number")
+        return t1.$ge();
+      if (t1 < t3 - 1) {
+        t4 = t1 + 1;
+        if (t4 < 0 || t4 >= t3)
+          return H.ioore(t2, t4);
+        t4 = offset < t2[t4];
+      } else
+        t4 = true;
+      if (t4)
+        return true;
+      if (t1 < t3 - 2) {
+        t4 = t1 + 2;
+        if (t4 < 0 || t4 >= t3)
+          return H.ioore(t2, t4);
+        t4 = offset < t2[t4];
+        t2 = t4;
+      } else
+        t2 = true;
+      if (t2) {
+        _this._cachedLine = t1 + 1;
+        return true;
+      }
+      return false;
+    },
+    _binarySearch$1: function(offset) {
+      var min, half,
+        t1 = this._lineStarts,
+        t2 = t1.length,
+        max = t2 - 1;
+      for (min = 0; min < max;) {
+        half = min + C.JSInt_methods._tdivFast$1(max - min, 2);
+        if (half < 0 || half >= t2)
+          return H.ioore(t1, half);
+        if (t1[half] > offset)
+          max = half;
+        else
+          min = half + 1;
+      }
+      return max;
+    },
+    getColumn$1: function(offset) {
+      var line, lineStart, _this = this;
+      if (offset < 0)
+        throw H.wrapException(P.RangeError$("Offset may not be negative, was " + offset + "."));
+      else if (offset > _this._decodedChars.length)
+        throw H.wrapException(P.RangeError$("Offset " + offset + " must be not be greater than the number of characters in the file, " + _this.get$length(_this) + "."));
+      line = _this.getLine$1(offset);
+      lineStart = C.JSArray_methods.$index(_this._lineStarts, line);
+      if (lineStart > offset)
+        throw H.wrapException(P.RangeError$("Line " + H.S(line) + " comes after offset " + offset + "."));
+      return offset - lineStart;
+    },
+    getOffset$2: function(line, column) {
+      var t1, t2, result, t3;
+      if (typeof line !== "number")
+        return line.$lt();
+      if (line < 0)
+        throw H.wrapException(P.RangeError$("Line may not be negative, was " + line + "."));
+      else {
+        t1 = this._lineStarts;
+        t2 = t1.length;
+        if (line >= t2)
+          throw H.wrapException(P.RangeError$("Line " + line + " must be less than the number of lines in the file, " + this.get$lines() + "."));
+      }
+      result = t1[line];
+      if (result <= this._decodedChars.length) {
+        t3 = line + 1;
+        t1 = t3 < t2 && result >= t1[t3];
+      } else
+        t1 = true;
+      if (t1)
+        throw H.wrapException(P.RangeError$("Line " + line + " doesn't have 0 columns."));
+      return result;
+    },
+    getOffset$1: function(line) {
+      return this.getOffset$2(line, null);
+    }
+  };
+  Y.FileLocation.prototype = {
+    get$sourceUrl: function() {
+      return this.file.url;
+    },
+    get$line: function() {
+      return this.file.getLine$1(this.offset);
+    },
+    get$column: function() {
+      return this.file.getColumn$1(this.offset);
+    },
+    get$offset: function(receiver) {
+      return this.offset;
+    }
+  };
+  Y._FileSpan.prototype = {
+    get$sourceUrl: function() {
+      return this.file.url;
+    },
+    get$length: function(_) {
+      return this._file$_end - this._file$_start;
+    },
+    get$start: function() {
+      return Y.FileLocation$_(this.file, this._file$_start);
+    },
+    get$end: function() {
+      return Y.FileLocation$_(this.file, this._file$_end);
+    },
+    get$text: function() {
+      return P.String_String$fromCharCodes(C.NativeUint32List_methods.sublist$2(this.file._decodedChars, this._file$_start, this._file$_end), 0, null);
+    },
+    get$context: function() {
+      var t2, _this = this,
+        t1 = _this.file,
+        endOffset = _this._file$_end,
+        endLine = t1.getLine$1(endOffset);
+      if (t1.getColumn$1(endOffset) === 0 && endLine !== 0) {
+        if (endOffset - _this._file$_start === 0) {
+          if (endLine === t1._lineStarts.length - 1)
+            t1 = "";
+          else {
+            t2 = t1.getOffset$1(endLine);
+            if (typeof endLine !== "number")
+              return endLine.$add();
+            t1 = P.String_String$fromCharCodes(C.NativeUint32List_methods.sublist$2(t1._decodedChars, t2, t1.getOffset$1(endLine + 1)), 0, null);
+          }
+          return t1;
+        }
+      } else if (endLine === t1._lineStarts.length - 1)
+        endOffset = t1._decodedChars.length;
+      else {
+        if (typeof endLine !== "number")
+          return endLine.$add();
+        endOffset = t1.getOffset$1(endLine + 1);
+      }
+      return P.String_String$fromCharCodes(C.NativeUint32List_methods.sublist$2(t1._decodedChars, t1.getOffset$1(t1.getLine$1(_this._file$_start)), endOffset), 0, null);
+    },
+    $eq: function(_, other) {
+      var _this = this;
+      if (other == null)
+        return false;
+      if (!type$.FileSpan._is(other))
+        return _this.super$SourceSpanMixin$$eq(0, other);
+      if (!(other instanceof Y._FileSpan))
+        return _this.super$SourceSpanMixin$$eq(0, other) && J.$eq$(_this.file.url, other.get$sourceUrl());
+      return _this._file$_start === other._file$_start && _this._file$_end === other._file$_end && J.$eq$(_this.file.url, other.file.url);
+    },
+    get$hashCode: function(_) {
+      return Y.SourceSpanMixin.prototype.get$hashCode.call(this, this);
+    },
+    expand$1: function(_, other) {
+      var start, _this = this,
+        t1 = _this.file;
+      if (!J.$eq$(t1.url, other.file.url))
+        throw H.wrapException(P.ArgumentError$('Source URLs "' + H.S(_this.get$sourceUrl()) + '" and  "' + H.S(other.get$sourceUrl()) + "\" don't match."));
+      start = Math.min(_this._file$_start, other._file$_start);
+      return Y._FileSpan$(t1, start, Math.max(_this._file$_end, other._file$_end));
+    },
+    $isFileSpan: 1,
+    $isSourceSpanWithContext: 1
+  };
+  U.Highlighter.prototype = {
+    highlight$0: function() {
+      var t1, t2, lineStart, context, lines, t3, t4, lineNumber, _i, line, lastLineIndex, _this = this;
+      _this._writeSidebar$1$end($._glyphs.get$downEnd());
+      t1 = _this._highlighter$_buffer;
+      t1._contents += "\n";
+      t2 = _this._span;
+      lineStart = B.findLineStart(t2.get$context(), t2.get$text(), t2.get$start().get$column());
+      H.assertHelper(lineStart != null);
+      context = t2.get$context();
+      if (typeof lineStart !== "number")
+        return lineStart.$gt();
+      if (lineStart > 0) {
+        lines = C.JSString_methods.substring$2(context, 0, lineStart - 1).split("\n");
+        t3 = t2.get$start().get$line();
+        t4 = lines.length;
+        if (typeof t3 !== "number")
+          return t3.$sub();
+        lineNumber = t3 - t4;
+        for (t3 = _this._multiline, _i = 0; _i < t4; ++_i) {
+          line = lines[_i];
+          _this._writeSidebar$1$line(lineNumber);
+          t1._contents += C.JSString_methods.$mul(" ", t3 ? 3 : 1);
+          _this._writeText$1(line);
+          t1._contents += "\n";
+          ++lineNumber;
+        }
+        context = C.JSString_methods.substring$1(context, lineStart);
+      }
+      lines = H.setRuntimeTypeInfo(context.split("\n"), type$.JSArray_String);
+      t3 = t2.get$end().get$line();
+      t2 = t2.get$start().get$line();
+      if (typeof t3 !== "number")
+        return t3.$sub();
+      if (typeof t2 !== "number")
+        return H.iae(t2);
+      lastLineIndex = t3 - t2;
+      t2 = C.JSArray_methods.get$last(lines);
+      t2.toString;
+      if (J.get$length$asx(t2) === 0 && lines.length > lastLineIndex + 1) {
+        if (0 >= lines.length)
+          return H.ioore(lines, -1);
+        lines.pop();
+      }
+      _this._writeFirstLine$1(C.JSArray_methods.get$first(lines));
+      if (_this._multiline) {
+        _this._writeIntermediateLines$1(H.SubListIterable$(lines, 1, null, type$.String).take$1(0, lastLineIndex - 1));
+        if (lastLineIndex < 0 || lastLineIndex >= lines.length)
+          return H.ioore(lines, lastLineIndex);
+        _this._writeLastLine$1(lines[lastLineIndex]);
+      }
+      _this._writeTrailingLines$1(H.SubListIterable$(lines, lastLineIndex + 1, null, type$.String));
+      _this._writeSidebar$1$end($._glyphs.get$upEnd());
+      t1 = t1._contents;
+      return t1.charCodeAt(0) == 0 ? t1 : t1;
+    },
+    _writeFirstLine$1: function(line) {
+      var t3, t4, startColumn, endColumn, textBefore, textInside, tabsBefore, tabsInside, _this = this, t1 = {},
+        t2 = _this._span;
+      _this._writeSidebar$1$line(t2.get$start().get$line());
+      t3 = t2.get$start().get$column();
+      t4 = line.length;
+      startColumn = t1.startColumn = Math.min(t3, t4);
+      t3 = t2.get$end();
+      t3 = t3.get$offset(t3);
+      t2 = t2.get$start();
+      endColumn = t1.endColumn = Math.min(startColumn + t3 - t2.get$offset(t2), t4);
+      textBefore = J.substring$2$s(line, 0, startColumn);
+      t2 = _this._multiline;
+      if (t2 && _this._isOnlyWhitespace$1(textBefore)) {
+        t1 = _this._highlighter$_buffer;
+        t1._contents += " ";
+        _this._colorize$1(new U.Highlighter__writeFirstLine_closure(_this, line));
+        t1._contents += "\n";
+        return;
+      }
+      t3 = _this._highlighter$_buffer;
+      t3._contents += C.JSString_methods.$mul(" ", t2 ? 3 : 1);
+      _this._writeText$1(textBefore);
+      textInside = C.JSString_methods.substring$2(line, startColumn, endColumn);
+      _this._colorize$1(new U.Highlighter__writeFirstLine_closure0(_this, textInside));
+      _this._writeText$1(C.JSString_methods.substring$1(line, endColumn));
+      t3._contents += "\n";
+      tabsBefore = _this._countTabs$1(textBefore);
+      tabsInside = _this._countTabs$1(textInside);
+      startColumn += tabsBefore * 3;
+      t1.startColumn = startColumn;
+      t1.endColumn = endColumn + (tabsBefore + tabsInside) * 3;
+      _this._writeSidebar$0();
+      if (t2) {
+        t3._contents += " ";
+        _this._colorize$1(new U.Highlighter__writeFirstLine_closure1(t1, _this));
+      } else {
+        t3._contents += C.JSString_methods.$mul(" ", startColumn + 1);
+        _this._colorize$1(new U.Highlighter__writeFirstLine_closure2(t1, _this));
+      }
+      t3._contents += "\n";
+    },
+    _writeIntermediateLines$1: function(lines) {
+      var t1, lineNumber, t2, t3, _this = this;
+      type$.Iterable_String._check(lines);
+      H.assertHelper(_this._multiline);
+      t1 = _this._span.get$start().get$line();
+      if (typeof t1 !== "number")
+        return t1.$add();
+      lineNumber = t1 + 1;
+      for (t1 = new H.ListIterator(lines, lines.get$length(lines), lines.$ti._eval$1("ListIterator<ListIterable.E>")), t2 = _this._highlighter$_buffer; t1.moveNext$0();) {
+        t3 = t1.__internal$_current;
+        _this._writeSidebar$1$line(lineNumber);
+        t2._contents += " ";
+        _this._colorize$1(new U.Highlighter__writeIntermediateLines_closure(_this, t3));
+        t2._contents += "\n";
+        ++lineNumber;
+      }
+    },
+    _writeLastLine$1: function(line) {
+      var t3, t4, endColumn, textInside, _this = this, t1 = {},
+        t2 = _this._multiline;
+      H.assertHelper(t2);
+      t3 = _this._span;
+      _this._writeSidebar$1$line(t3.get$end().get$line());
+      t3 = t3.get$end().get$column();
+      t4 = line.length;
+      endColumn = t1.endColumn = Math.min(t3, t4);
+      if (t2 && endColumn === t4) {
+        t1 = _this._highlighter$_buffer;
+        t1._contents += " ";
+        _this._colorize$1(new U.Highlighter__writeLastLine_closure(_this, line));
+        t1._contents += "\n";
+        return;
+      }
+      t2 = _this._highlighter$_buffer;
+      t2._contents += " ";
+      textInside = J.substring$2$s(line, 0, endColumn);
+      _this._colorize$1(new U.Highlighter__writeLastLine_closure0(_this, textInside));
+      _this._writeText$1(C.JSString_methods.substring$1(line, endColumn));
+      t2._contents += "\n";
+      t1.endColumn = endColumn + _this._countTabs$1(textInside) * 3;
+      _this._writeSidebar$0();
+      t2._contents += " ";
+      _this._colorize$1(new U.Highlighter__writeLastLine_closure1(t1, _this));
+      t2._contents += "\n";
+    },
+    _writeTrailingLines$1: function(lines) {
+      var t1, lineNumber, t2, t3, t4, _this = this;
+      type$.Iterable_String._check(lines);
+      t1 = _this._span.get$end().get$line();
+      if (typeof t1 !== "number")
+        return t1.$add();
+      lineNumber = t1 + 1;
+      for (t1 = new H.ListIterator(lines, lines.get$length(lines), lines.$ti._eval$1("ListIterator<ListIterable.E>")), t2 = _this._highlighter$_buffer, t3 = _this._multiline; t1.moveNext$0();) {
+        t4 = t1.__internal$_current;
+        _this._writeSidebar$1$line(lineNumber);
+        t2._contents += C.JSString_methods.$mul(" ", t3 ? 3 : 1);
+        _this._writeText$1(t4);
+        t2._contents += "\n";
+        ++lineNumber;
+      }
+    },
+    _writeText$1: function(text) {
+      var t1, t2, t3;
+      text.toString;
+      t1 = new H.CodeUnits(text);
+      t1 = new H.ListIterator(t1, t1.get$length(t1), type$.CodeUnits._eval$1("ListIterator<ListMixin.E>"));
+      t2 = this._highlighter$_buffer;
+      for (; t1.moveNext$0();) {
+        t3 = t1.__internal$_current;
+        if (t3 === 9)
+          t2._contents += C.JSString_methods.$mul(" ", 4);
+        else
+          t2._contents += H.Primitives_stringFromCharCode(t3);
+      }
+    },
+    _writeSidebar$2$end$line: function(end, line) {
+      this._colorize$2$color(new U.Highlighter__writeSidebar_closure(this, line, end), "\x1b[34m");
+    },
+    _writeSidebar$1$end: function(end) {
+      return this._writeSidebar$2$end$line(end, null);
+    },
+    _writeSidebar$1$line: function(line) {
+      return this._writeSidebar$2$end$line(null, line);
+    },
+    _writeSidebar$0: function() {
+      return this._writeSidebar$2$end$line(null, null);
+    },
+    _countTabs$1: function(text) {
+      var t1, count;
+      for (t1 = new H.CodeUnits(text), t1 = new H.ListIterator(t1, t1.get$length(t1), type$.CodeUnits._eval$1("ListIterator<ListMixin.E>")), count = 0; t1.moveNext$0();)
+        if (t1.__internal$_current === 9)
+          ++count;
+      return count;
+    },
+    _isOnlyWhitespace$1: function(text) {
+      var t1, t2;
+      for (t1 = new H.CodeUnits(text), t1 = new H.ListIterator(t1, t1.get$length(t1), type$.CodeUnits._eval$1("ListIterator<ListMixin.E>")); t1.moveNext$0();) {
+        t2 = t1.__internal$_current;
+        if (t2 !== 32 && t2 !== 9)
+          return false;
+      }
+      return true;
+    },
+    _colorize$2$color: function(callback, color) {
+      var t1, t2;
+      type$.void_Function._check(callback);
+      t1 = this._color;
+      t2 = t1 != null;
+      if (t2) {
+        t1 = color == null ? t1 : color;
+        this._highlighter$_buffer._contents += t1;
+      }
+      callback.call$0();
+      if (t2)
+        this._highlighter$_buffer._contents += "\x1b[0m";
+    },
+    _colorize$1: function(callback) {
+      return this._colorize$2$color(callback, null);
+    }
+  };
+  U.Highlighter__writeFirstLine_closure.prototype = {
+    call$0: function() {
+      var t1 = this.$this,
+        t2 = t1._highlighter$_buffer,
+        t3 = t2._contents += $._glyphs.glyphOrAscii$2("\u250c", "/");
+      t2._contents = t3 + " ";
+      t1._writeText$1(this.line);
+    },
+    $signature: 0
+  };
+  U.Highlighter__writeFirstLine_closure0.prototype = {
+    call$0: function() {
+      return this.$this._writeText$1(this.textInside);
+    },
+    $signature: 1
+  };
+  U.Highlighter__writeFirstLine_closure1.prototype = {
+    call$0: function() {
+      var t2,
+        t1 = this.$this._highlighter$_buffer;
+      t1._contents += $._glyphs.get$topLeftCorner();
+      t2 = t1._contents += C.JSString_methods.$mul($._glyphs.get$horizontalLine(), this._box_0.startColumn + 1);
+      t1._contents = t2 + "^";
+    },
+    $signature: 0
+  };
+  U.Highlighter__writeFirstLine_closure2.prototype = {
+    call$0: function() {
+      var t1 = this._box_0;
+      this.$this._highlighter$_buffer._contents += C.JSString_methods.$mul("^", Math.max(t1.endColumn - t1.startColumn, 1));
+      return null;
+    },
+    $signature: 1
+  };
+  U.Highlighter__writeIntermediateLines_closure.prototype = {
+    call$0: function() {
+      var t1 = this.$this,
+        t2 = t1._highlighter$_buffer,
+        t3 = t2._contents += $._glyphs.get$verticalLine();
+      t2._contents = t3 + " ";
+      t1._writeText$1(this.line);
+    },
+    $signature: 0
+  };
+  U.Highlighter__writeLastLine_closure.prototype = {
+    call$0: function() {
+      var t1 = this.$this,
+        t2 = t1._highlighter$_buffer,
+        t3 = t2._contents += $._glyphs.glyphOrAscii$2("\u2514", "\\");
+      t2._contents = t3 + " ";
+      t1._writeText$1(this.line);
+    },
+    $signature: 0
+  };
+  U.Highlighter__writeLastLine_closure0.prototype = {
+    call$0: function() {
+      var t1 = this.$this,
+        t2 = t1._highlighter$_buffer,
+        t3 = t2._contents += $._glyphs.get$verticalLine();
+      t2._contents = t3 + " ";
+      t1._writeText$1(this.textInside);
+    },
+    $signature: 0
+  };
+  U.Highlighter__writeLastLine_closure1.prototype = {
+    call$0: function() {
+      var t2,
+        t1 = this.$this._highlighter$_buffer;
+      t1._contents += $._glyphs.get$bottomLeftCorner();
+      t2 = t1._contents += C.JSString_methods.$mul($._glyphs.get$horizontalLine(), this._box_0.endColumn);
+      t1._contents = t2 + "^";
+    },
+    $signature: 0
+  };
+  U.Highlighter__writeSidebar_closure.prototype = {
+    call$0: function() {
+      var t1 = this.line,
+        t2 = this.$this,
+        t3 = t2._highlighter$_buffer;
+      t2 = t2._paddingBeforeSidebar;
+      if (t1 != null)
+        t3._contents += C.JSString_methods.padRight$1(C.JSInt_methods.toString$0(t1 + 1), t2);
+      else
+        t3._contents += C.JSString_methods.$mul(" ", t2);
+      t1 = this.end;
+      t3._contents += t1 == null ? $._glyphs.get$verticalLine() : t1;
+    },
+    $signature: 0
+  };
+  V.SourceLocation.prototype = {
+    distance$1: function(other) {
+      var t1 = this.sourceUrl;
+      if (!J.$eq$(t1, other.get$sourceUrl()))
+        throw H.wrapException(P.ArgumentError$('Source URLs "' + H.S(t1) + '" and "' + H.S(other.get$sourceUrl()) + "\" don't match."));
+      return Math.abs(this.offset - other.get$offset(other));
+    },
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      return type$.SourceLocation._is(other) && J.$eq$(this.sourceUrl, other.get$sourceUrl()) && this.offset === other.get$offset(other);
+    },
+    get$hashCode: function(_) {
+      return J.get$hashCode$(this.sourceUrl) + this.offset;
+    },
+    toString$0: function(_) {
+      var _this = this,
+        t1 = "<" + H.getRuntimeType(_this).toString$0(0) + ": " + _this.offset + " ",
+        source = _this.sourceUrl;
+      return t1 + (H.S(source == null ? "unknown source" : source) + ":" + (_this.line + 1) + ":" + (_this.column + 1)) + ">";
+    },
+    get$sourceUrl: function() {
+      return this.sourceUrl;
+    },
+    get$offset: function(receiver) {
+      return this.offset;
+    },
+    get$line: function() {
+      return this.line;
+    },
+    get$column: function() {
+      return this.column;
+    }
+  };
+  D.SourceLocationMixin.prototype = {
+    distance$1: function(other) {
+      if (!J.$eq$(this.file.url, other.get$sourceUrl()))
+        throw H.wrapException(P.ArgumentError$('Source URLs "' + H.S(this.get$sourceUrl()) + '" and "' + H.S(other.get$sourceUrl()) + "\" don't match."));
+      return Math.abs(this.offset - other.get$offset(other));
+    },
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      return type$.SourceLocation._is(other) && J.$eq$(this.file.url, other.get$sourceUrl()) && this.offset === other.get$offset(other);
+    },
+    get$hashCode: function(_) {
+      return J.get$hashCode$(this.file.url) + this.offset;
+    },
+    toString$0: function(_) {
+      var t1 = this.offset,
+        t2 = "<" + H.getRuntimeType(this).toString$0(0) + ": " + t1 + " ",
+        t3 = this.file,
+        source = t3.url,
+        t4 = H.S(source == null ? "unknown source" : source) + ":",
+        t5 = t3.getLine$1(t1);
+      if (typeof t5 !== "number")
+        return t5.$add();
+      return t2 + (t4 + (t5 + 1) + ":" + (t3.getColumn$1(t1) + 1)) + ">";
+    },
+    $isSourceLocation: 1
+  };
+  V.SourceSpan.prototype = {};
+  V.SourceSpanBase.prototype = {
+    SourceSpanBase$3: function(start, end, text) {
+      var t3,
+        t1 = this.end,
+        t2 = this.start;
+      if (!J.$eq$(t1.get$sourceUrl(), t2.get$sourceUrl()))
+        throw H.wrapException(P.ArgumentError$('Source URLs "' + H.S(t2.get$sourceUrl()) + '" and  "' + H.S(t1.get$sourceUrl()) + "\" don't match."));
+      else if (t1.get$offset(t1) < t2.get$offset(t2))
+        throw H.wrapException(P.ArgumentError$("End " + t1.toString$0(0) + " must come after start " + t2.toString$0(0) + "."));
+      else {
+        t3 = this.text;
+        if (t3.length !== t2.distance$1(t1))
+          throw H.wrapException(P.ArgumentError$('Text "' + t3 + '" must be ' + t2.distance$1(t1) + " characters long."));
+      }
+    },
+    get$start: function() {
+      return this.start;
+    },
+    get$end: function() {
+      return this.end;
+    },
+    get$text: function() {
+      return this.text;
+    }
+  };
+  G.SourceSpanException.prototype = {
+    get$message: function(_) {
+      return this._span_exception$_message;
+    },
+    toString$1$color: function(_, color) {
+      var t1 = this._span_exception$_span;
+      if (t1 == null)
+        return this._span_exception$_message;
+      return "Error on " + t1.message$2$color(0, this._span_exception$_message, color);
+    },
+    toString$0: function($receiver) {
+      return this.toString$1$color($receiver, null);
+    },
+    $isException: 1
+  };
+  G.SourceSpanFormatException.prototype = {$isFormatException: 1};
+  Y.SourceSpanMixin.prototype = {
+    get$sourceUrl: function() {
+      return this.get$start().get$sourceUrl();
+    },
+    get$length: function(_) {
+      var t2,
+        t1 = this.get$end();
+      t1 = t1.get$offset(t1);
+      t2 = this.get$start();
+      return t1 - t2.get$offset(t2);
+    },
+    message$2$color: function(_, message, color) {
+      var t2, highlight, _this = this,
+        t1 = _this.get$start().get$line();
+      if (typeof t1 !== "number")
+        return t1.$add();
+      t1 = "line " + (t1 + 1) + ", column " + (_this.get$start().get$column() + 1);
+      if (_this.get$sourceUrl() != null) {
+        t2 = _this.get$sourceUrl();
+        t2 = t1 + (" of " + H.S($.$get$context().prettyUri$1(t2)));
+        t1 = t2;
+      }
+      t1 += ": " + H.S(message);
+      highlight = _this.highlight$1$color(color);
+      if (highlight.length !== 0)
+        t1 = t1 + "\n" + highlight;
+      return t1.charCodeAt(0) == 0 ? t1 : t1;
+    },
+    message$1: function($receiver, message) {
+      return this.message$2$color($receiver, message, null);
+    },
+    highlight$1$color: function(color) {
+      var t2, t3, t4, newSpan, _this = this,
+        t1 = type$.SourceSpanWithContext._is(_this);
+      if (!t1 && _this.get$length(_this) === 0)
+        return "";
+      if (t1 && B.findLineStart(_this.get$context(), _this.get$text(), _this.get$start().get$column()) != null)
+        t1 = _this;
+      else {
+        t1 = _this.get$start();
+        t1 = V.SourceLocation$(t1.get$offset(t1), 0, 0, _this.get$sourceUrl());
+        t2 = _this.get$end();
+        t2 = t2.get$offset(t2);
+        t3 = _this.get$sourceUrl();
+        t4 = B.countCodeUnits(_this.get$text(), 10);
+        t3 = X.SourceSpanWithContext$(t1, V.SourceLocation$(t2, U.Highlighter__lastLineLength(_this.get$text()), t4, t3), _this.get$text(), _this.get$text());
+        t1 = t3;
+      }
+      newSpan = U.Highlighter__normalizeEndOfLine(U.Highlighter__normalizeTrailingNewline(U.Highlighter__normalizeNewlines(t1)));
+      return new U.Highlighter(newSpan, color, newSpan.get$start().get$line() != newSpan.get$end().get$line(), J.toString$0$(newSpan.get$end().get$line()).length + 1, new P.StringBuffer("")).highlight$0();
+    },
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      return type$.SourceSpan._is(other) && this.get$start().$eq(0, other.get$start()) && this.get$end().$eq(0, other.get$end());
+    },
+    get$hashCode: function(_) {
+      var t2,
+        t1 = this.get$start();
+      t1 = t1.get$hashCode(t1);
+      t2 = this.get$end();
+      return t1 + 31 * t2.get$hashCode(t2);
+    },
+    toString$0: function(_) {
+      var _this = this;
+      return "<" + H.getRuntimeType(_this).toString$0(0) + ": from " + _this.get$start().toString$0(0) + " to " + _this.get$end().toString$0(0) + ' "' + _this.get$text() + '">';
+    },
+    $isSourceSpan: 1
+  };
+  X.SourceSpanWithContext.prototype = {
+    get$context: function() {
+      return this._context;
+    }
+  };
+  U.Chain.prototype = {
+    foldFrames$2$terse: function(predicate, terse) {
+      var t1 = this.traces,
+        t2 = H._arrayInstanceType(t1),
+        t3 = t2._eval$1("MappedListIterable<1,Trace>"),
+        foldedTraces = new H.MappedListIterable(t1, t2._eval$1("Trace(1)")._check(new U.Chain_foldFrames_closure(type$.bool_Function_Frame._check(predicate), true)), t3),
+        nonEmptyTraces = foldedTraces.super$Iterable$where(0, t3._eval$1("bool(ListIterable.E)")._check(new U.Chain_foldFrames_closure0(true)));
+      if (!nonEmptyTraces.get$iterator(nonEmptyTraces).moveNext$0() && !foldedTraces.get$isEmpty(foldedTraces))
+        return new U.Chain(P.List_List$unmodifiable(H.setRuntimeTypeInfo([foldedTraces.get$last(foldedTraces)], type$.JSArray_Trace), type$.Trace));
+      return new U.Chain(P.List_List$unmodifiable(nonEmptyTraces, type$.Trace));
+    },
+    toTrace$0: function() {
+      var t1 = this.traces,
+        t2 = H._arrayInstanceType(t1);
+      return new Y.Trace(P.List_List$unmodifiable(new H.ExpandIterable(t1, t2._eval$1("Iterable<Frame>(1)")._check(new U.Chain_toTrace_closure()), t2._eval$1("ExpandIterable<1,Frame>")), type$.Frame), new P._StringStackTrace(null));
+    },
+    toString$0: function(_) {
+      var t1 = this.traces,
+        t2 = H._arrayInstanceType(t1),
+        t3 = type$.int;
+      return new H.MappedListIterable(t1, t2._eval$1("String(1)")._check(new U.Chain_toString_closure(new H.MappedListIterable(t1, t2._eval$1("int(1)")._check(new U.Chain_toString_closure0()), t2._eval$1("MappedListIterable<1,int>")).fold$1$2(0, 0, H.instantiate1(P.math__max$closure(), t3), t3))), t2._eval$1("MappedListIterable<1,String>")).join$1(0, "===== asynchronous gap ===========================\n");
+    },
+    $isStackTrace: 1,
+    get$traces: function() {
+      return this.traces;
+    }
+  };
+  U.Chain_capture_closure.prototype = {
+    call$0: function() {
+      var error, stackTrace, t1, exception;
+      try {
+        t1 = this.callback.call$0();
+        return t1;
+      } catch (exception) {
+        error = H.unwrapException(exception);
+        stackTrace = H.getTraceFromException(exception);
+        $.Zone__current.handleUncaughtError$2(error, stackTrace);
+        return null;
+      }
+    },
+    $signature: function() {
+      return this.T._eval$1("0()");
+    }
+  };
+  U.Chain_Chain$current_closure.prototype = {
+    call$0: function() {
+      var t3,
+        t1 = this.chain,
+        t2 = C.JSArray_methods.get$first(t1.get$traces()).get$frames();
+      t2 = H.SubListIterable$(t2, this.level + 2, null, H._arrayInstanceType(t2)._precomputed1);
+      t3 = C.JSArray_methods.get$first(t1.get$traces()).get$original();
+      t3 = H.setRuntimeTypeInfo([new Y.Trace(P.List_List$unmodifiable(t2, type$.Frame), new P._StringStackTrace(t3._stackTrace))], type$.JSArray_Trace);
+      t1 = t1.get$traces();
+      C.JSArray_methods.addAll$1(t3, H.SubListIterable$(t1, 1, null, H._arrayInstanceType(t1)._precomputed1));
+      return new U.Chain(P.List_List$unmodifiable(t3, type$.Trace));
+    },
+    $signature: 16
+  };
+  U.Chain_Chain$forTrace_closure.prototype = {
+    call$0: function() {
+      return U.Chain_Chain$parse(J.toString$0$(this.trace));
+    },
+    $signature: 16
+  };
+  U.Chain_Chain$parse_closure.prototype = {
+    call$1: function(trace) {
+      H._checkStringNullable(trace);
+      return new Y.Trace(P.List_List$unmodifiable(Y.Trace__parseVM(trace), type$.Frame), new P._StringStackTrace(trace));
+    },
+    $signature: 42
+  };
+  U.Chain_Chain$parse_closure0.prototype = {
+    call$1: function(trace) {
+      return Y.Trace$parseFriendly(H._checkStringNullable(trace));
+    },
+    $signature: 42
+  };
+  U.Chain_foldFrames_closure.prototype = {
+    call$1: function(trace) {
+      return type$.Trace._check(trace).foldFrames$2$terse(this.predicate, this.terse);
+    },
+    $signature: 45
+  };
+  U.Chain_foldFrames_closure0.prototype = {
+    call$1: function(trace) {
+      type$.Trace._check(trace);
+      if (trace.get$frames().length > 1)
+        return true;
+      if (trace.get$frames().length === 0)
+        return false;
+      if (!this.terse)
+        return false;
+      return C.JSArray_methods.get$single(trace.get$frames()).get$line() != null;
+    },
+    $signature: 52
+  };
+  U.Chain_toTrace_closure.prototype = {
+    call$1: function(trace) {
+      return type$.Trace._check(trace).get$frames();
+    },
+    $signature: 53
+  };
+  U.Chain_toString_closure0.prototype = {
+    call$1: function(trace) {
+      var t1 = type$.Trace._check(trace).get$frames(),
+        t2 = H._arrayInstanceType(t1),
+        t3 = type$.int;
+      return new H.MappedListIterable(t1, t2._eval$1("int(1)")._check(new U.Chain_toString__closure0()), t2._eval$1("MappedListIterable<1,int>")).fold$1$2(0, 0, H.instantiate1(P.math__max$closure(), t3), t3);
+    },
+    $signature: 54
+  };
+  U.Chain_toString__closure0.prototype = {
+    call$1: function(frame) {
+      type$.Frame._check(frame);
+      return frame.get$location(frame).length;
+    },
+    $signature: 39
+  };
+  U.Chain_toString_closure.prototype = {
+    call$1: function(trace) {
+      var t1 = type$.Trace._check(trace).get$frames(),
+        t2 = H._arrayInstanceType(t1);
+      return new H.MappedListIterable(t1, t2._eval$1("String(1)")._check(new U.Chain_toString__closure(this.longest)), t2._eval$1("MappedListIterable<1,String>")).join$0(0);
+    },
+    $signature: 56
+  };
+  U.Chain_toString__closure.prototype = {
+    call$1: function(frame) {
+      type$.Frame._check(frame);
+      return J.padRight$1$s(frame.get$location(frame), this.longest) + "  " + H.S(frame.get$member()) + "\n";
+    },
+    $signature: 38
+  };
+  A.Frame.prototype = {
+    get$isCore: function() {
+      return this.uri.get$scheme() === "dart";
+    },
+    get$library: function() {
+      var t1 = this.uri;
+      if (t1.get$scheme() === "data")
+        return "data:...";
+      return $.$get$context().prettyUri$1(t1);
+    },
+    get$$package: function() {
+      var t1 = this.uri;
+      if (t1.get$scheme() !== "package")
+        return null;
+      return C.JSArray_methods.get$first(t1.get$path(t1).split("/"));
+    },
+    get$location: function(_) {
+      var t2, _this = this,
+        t1 = _this.line;
+      if (t1 == null)
+        return _this.get$library();
+      t2 = _this.column;
+      if (t2 == null)
+        return H.S(_this.get$library()) + " " + H.S(t1);
+      return H.S(_this.get$library()) + " " + H.S(t1) + ":" + H.S(t2);
+    },
+    toString$0: function(_) {
+      return H.S(this.get$location(this)) + " in " + H.S(this.member);
+    },
+    get$uri: function() {
+      return this.uri;
+    },
+    get$line: function() {
+      return this.line;
+    },
+    get$column: function() {
+      return this.column;
+    },
+    get$member: function() {
+      return this.member;
+    }
+  };
+  A.Frame_Frame$parseVM_closure.prototype = {
+    call$0: function() {
+      var match, t2, t3, member, uri, lineAndColumn, line, _null = null,
+        t1 = this.frame;
+      if (t1 === "...")
+        return new A.Frame(P._Uri__Uri(_null, _null, _null, _null), _null, _null, "...");
+      match = $.$get$_vmFrame().firstMatch$1(t1);
+      if (match == null)
+        return new N.UnparsedFrame(P._Uri__Uri(_null, "unparsed", _null, _null), t1);
+      t1 = match._match;
+      if (1 >= t1.length)
+        return H.ioore(t1, 1);
+      t2 = t1[1];
+      t3 = $.$get$_asyncBody();
+      t2.toString;
+      t2 = H.stringReplaceAllUnchecked(t2, t3, "<async>");
+      member = H.stringReplaceAllUnchecked(t2, "<anonymous closure>", "<fn>");
+      if (2 >= t1.length)
+        return H.ioore(t1, 2);
+      uri = P.Uri_parse(t1[2]);
+      if (3 >= t1.length)
+        return H.ioore(t1, 3);
+      lineAndColumn = t1[3].split(":");
+      t1 = lineAndColumn.length;
+      line = t1 > 1 ? P.int_parse(lineAndColumn[1], _null, _null) : _null;
+      return new A.Frame(uri, line, t1 > 2 ? P.int_parse(lineAndColumn[2], _null, _null) : _null, member);
+    },
+    $signature: 17
+  };
+  A.Frame_Frame$parseV8_closure.prototype = {
+    call$0: function() {
+      var t2, t3, t4, _s4_ = "<fn>",
+        t1 = this.frame,
+        match = $.$get$_v8Frame().firstMatch$1(t1);
+      if (match == null)
+        return new N.UnparsedFrame(P._Uri__Uri(null, "unparsed", null, null), t1);
+      t1 = new A.Frame_Frame$parseV8_closure_parseLocation(t1);
+      t2 = match._match;
+      t3 = t2.length;
+      if (2 >= t3)
+        return H.ioore(t2, 2);
+      t4 = t2[2];
+      if (t4 != null) {
+        t2 = t2[1];
+        t2.toString;
+        t2 = H.stringReplaceAllUnchecked(t2, "<anonymous>", _s4_);
+        t2 = H.stringReplaceAllUnchecked(t2, "Anonymous function", _s4_);
+        return t1.call$2(t4, H.stringReplaceAllUnchecked(t2, "(anonymous function)", _s4_));
+      } else {
+        if (3 >= t3)
+          return H.ioore(t2, 3);
+        return t1.call$2(t2[3], _s4_);
+      }
+    },
+    $signature: 17
+  };
+  A.Frame_Frame$parseV8_closure_parseLocation.prototype = {
+    call$2: function($location, member) {
+      var t2, urlMatch, t3, _null = null,
+        t1 = $.$get$_v8EvalLocation(),
+        evalMatch = t1.firstMatch$1($location);
+      for (; evalMatch != null;) {
+        t2 = evalMatch._match;
+        if (1 >= t2.length)
+          return H.ioore(t2, 1);
+        $location = t2[1];
+        evalMatch = t1.firstMatch$1($location);
+      }
+      if ($location === "native")
+        return new A.Frame(P.Uri_parse("native"), _null, _null, member);
+      urlMatch = $.$get$_v8UrlLocation().firstMatch$1($location);
+      if (urlMatch == null)
+        return new N.UnparsedFrame(P._Uri__Uri(_null, "unparsed", _null, _null), this.frame);
+      t1 = urlMatch._match;
+      if (1 >= t1.length)
+        return H.ioore(t1, 1);
+      t2 = A.Frame__uriOrPathToUri(t1[1]);
+      if (2 >= t1.length)
+        return H.ioore(t1, 2);
+      t3 = P.int_parse(t1[2], _null, _null);
+      if (3 >= t1.length)
+        return H.ioore(t1, 3);
+      return new A.Frame(t2, t3, P.int_parse(t1[3], _null, _null), member);
+    },
+    $signature: 59
+  };
+  A.Frame_Frame$parseFirefox_closure.prototype = {
+    call$0: function() {
+      var uri, t2, t3, member, line, _null = null,
+        t1 = this.frame,
+        match = $.$get$_firefoxSafariFrame().firstMatch$1(t1);
+      if (match == null)
+        return new N.UnparsedFrame(P._Uri__Uri(_null, "unparsed", _null, _null), t1);
+      t1 = match._match;
+      if (3 >= t1.length)
+        return H.ioore(t1, 3);
+      uri = A.Frame__uriOrPathToUri(t1[3]);
+      t2 = t1.length;
+      if (1 >= t2)
+        return H.ioore(t1, 1);
+      t3 = t1[1];
+      if (t3 != null) {
+        if (2 >= t2)
+          return H.ioore(t1, 2);
+        t2 = C.JSString_methods.allMatches$1("/", t1[2]);
+        member = J.$add$ansx(t3, C.JSArray_methods.join$0(P.List_List$filled(t2.get$length(t2), ".<fn>", type$.String)));
+        if (member === "")
+          member = "<fn>";
+        member = C.JSString_methods.replaceFirst$2(member, $.$get$_initialDot(), "");
+      } else
+        member = "<fn>";
+      if (4 >= t1.length)
+        return H.ioore(t1, 4);
+      t2 = t1[4];
+      line = t2 === "" ? _null : P.int_parse(t2, _null, _null);
+      if (5 >= t1.length)
+        return H.ioore(t1, 5);
+      t1 = t1[5];
+      return new A.Frame(uri, line, t1 == null || t1 === "" ? _null : P.int_parse(t1, _null, _null), member);
+    },
+    $signature: 17
+  };
+  A.Frame_Frame$parseFriendly_closure.prototype = {
+    call$0: function() {
+      var t2, buffer, indices, uri, line, column, _null = null,
+        t1 = this.frame,
+        match = $.$get$_friendlyFrame().firstMatch$1(t1);
+      if (match == null)
+        throw H.wrapException(P.FormatException$("Couldn't parse package:stack_trace stack trace line '" + H.S(t1) + "'.", _null, _null));
+      t1 = match._match;
+      if (1 >= t1.length)
+        return H.ioore(t1, 1);
+      t2 = t1[1];
+      if (t2 === "data:...") {
+        buffer = new P.StringBuffer("");
+        indices = H.setRuntimeTypeInfo([-1], type$.JSArray_int);
+        P.UriData__writeUri(_null, _null, _null, buffer, indices);
+        C.JSArray_methods.add$1(indices, buffer._contents.length);
+        buffer._contents += ",";
+        P.UriData__uriEncodeBytes(C.List_CVk, C.C_AsciiCodec.encode$1(""), buffer);
+        t2 = buffer._contents;
+        uri = new P.UriData(t2.charCodeAt(0) == 0 ? t2 : t2, indices, _null).get$uri();
+      } else
+        uri = P.Uri_parse(t2);
+      if (uri.get$scheme() === "") {
+        t2 = $.$get$context();
+        uri = t2.toUri$1(t2.absolute$7(0, t2.style.pathFromUri$1(M._parseUri(uri)), _null, _null, _null, _null, _null, _null));
+      }
+      if (2 >= t1.length)
+        return H.ioore(t1, 2);
+      t2 = t1[2];
+      line = t2 == null ? _null : P.int_parse(t2, _null, _null);
+      if (3 >= t1.length)
+        return H.ioore(t1, 3);
+      t2 = t1[3];
+      column = t2 == null ? _null : P.int_parse(t2, _null, _null);
+      if (4 >= t1.length)
+        return H.ioore(t1, 4);
+      return new A.Frame(uri, line, column, t1[4]);
+    },
+    $signature: 17
+  };
+  X.LazyChain.prototype = {
+    get$_chain: function() {
+      var _this = this;
+      if (_this._lazy_chain$_inner == null)
+        _this.set$_lazy_chain$_inner(_this._thunk.call$0());
+      return _this._lazy_chain$_inner;
+    },
+    get$traces: function() {
+      return this.get$_chain().get$traces();
+    },
+    foldFrames$2$terse: function(predicate, terse) {
+      return new X.LazyChain(new X.LazyChain_foldFrames_closure(this, type$.bool_Function_Frame._check(predicate), true));
+    },
+    toTrace$0: function() {
+      return new T.LazyTrace(new X.LazyChain_toTrace_closure(this));
+    },
+    toString$0: function(_) {
+      return J.toString$0$(this.get$_chain());
+    },
+    set$_lazy_chain$_inner: function(_inner) {
+      this._lazy_chain$_inner = type$.Chain._check(_inner);
+    },
+    $isStackTrace: 1,
+    $isChain: 1
+  };
+  X.LazyChain_foldFrames_closure.prototype = {
+    call$0: function() {
+      return this.$this.get$_chain().foldFrames$2$terse(this.predicate, this.terse);
+    },
+    $signature: 16
+  };
+  X.LazyChain_toTrace_closure.prototype = {
+    call$0: function() {
+      return this.$this.get$_chain().toTrace$0();
+    },
+    $signature: 8
+  };
+  T.LazyTrace.prototype = {
+    get$_lazy_trace$_trace: function() {
+      var _this = this;
+      if (_this._lazy_trace$_inner == null)
+        _this.set$_lazy_trace$_inner(_this._lazy_trace$_thunk.call$0());
+      return _this._lazy_trace$_inner;
+    },
+    get$frames: function() {
+      return this.get$_lazy_trace$_trace().get$frames();
+    },
+    get$original: function() {
+      return this.get$_lazy_trace$_trace().get$original();
+    },
+    foldFrames$2$terse: function(predicate, terse) {
+      return new T.LazyTrace(new T.LazyTrace_foldFrames_closure(this, type$.bool_Function_Frame._check(predicate), true));
+    },
+    toString$0: function(_) {
+      return J.toString$0$(this.get$_lazy_trace$_trace());
+    },
+    set$_lazy_trace$_inner: function(_inner) {
+      this._lazy_trace$_inner = type$.Trace._check(_inner);
+    },
+    $isStackTrace: 1,
+    $isTrace: 1
+  };
+  T.LazyTrace_foldFrames_closure.prototype = {
+    call$0: function() {
+      return this.$this.get$_lazy_trace$_trace().foldFrames$2$terse(this.predicate, this.terse);
+    },
+    $signature: 8
+  };
+  O.StackZoneSpecification.prototype = {
+    chainFor$1: function(trace) {
+      var t2, previous, t3, t1 = {};
+      t1.trace = trace;
+      if (type$.Chain._is(trace))
+        return trace;
+      if (trace == null) {
+        trace = P.StackTrace_current();
+        t1.trace = trace;
+        t2 = trace;
+      } else
+        t2 = trace;
+      previous = this._chains.$index(0, t2);
+      if (previous == null)
+        previous = this._currentNode;
+      if (previous == null) {
+        t3 = type$.Trace;
+        if (t3._is(t2))
+          return new U.Chain(P.List_List$unmodifiable(H.setRuntimeTypeInfo([t2], type$.JSArray_Trace), t3));
+        return new X.LazyChain(new O.StackZoneSpecification_chainFor_closure(t1));
+      } else
+        return new O._Node(Y.Trace_Trace$from(!type$.Trace._is(t2) ? t1.trace = new T.LazyTrace(new O.StackZoneSpecification_chainFor_closure0(this, t2)) : t2), previous).toChain$0();
+    },
+    _stack_zone_specification$_registerCallback$1$4: function($self, $parent, zone, f, $R) {
+      var t1, t2;
+      $R._eval$1("0()")._check(f);
+      if (f == null || J.$eq$($.Zone__current.$index(0, $.$get$StackZoneSpecification_disableKey()), true))
+        return $parent.registerCallback$1$2(zone, f, $R);
+      t1 = this._currentTrace$1(2);
+      t2 = this._currentNode;
+      return $parent.registerCallback$1$2(zone, new O.StackZoneSpecification__registerCallback_closure(this, f, new O._Node(Y.Trace_Trace$from(t1), t2), $R), $R);
+    },
+    _stack_zone_specification$_registerCallback$4: function($self, $parent, zone, f) {
+      return this._stack_zone_specification$_registerCallback$1$4($self, $parent, zone, f, type$.dynamic);
+    },
+    _stack_zone_specification$_registerUnaryCallback$2$4: function($self, $parent, zone, f, $R, $T) {
+      var t1, t2;
+      $R._eval$1("@<0>")._bind$1($T)._eval$1("1(2)")._check(f);
+      if (f == null || J.$eq$($.Zone__current.$index(0, $.$get$StackZoneSpecification_disableKey()), true))
+        return $parent.registerUnaryCallback$2$2(zone, f, $R, $T);
+      t1 = this._currentTrace$1(2);
+      t2 = this._currentNode;
+      return $parent.registerUnaryCallback$2$2(zone, new O.StackZoneSpecification__registerUnaryCallback_closure(this, f, new O._Node(Y.Trace_Trace$from(t1), t2), $T, $R), $R, $T);
+    },
+    _stack_zone_specification$_registerUnaryCallback$4: function($self, $parent, zone, f) {
+      return this._stack_zone_specification$_registerUnaryCallback$2$4($self, $parent, zone, f, type$.dynamic, type$.dynamic);
+    },
+    _stack_zone_specification$_registerBinaryCallback$3$4: function($self, $parent, zone, f, $R, T1, T2) {
+      var t1, t2;
+      type$.Function._check(f);
+      if (f == null || J.$eq$($.Zone__current.$index(0, $.$get$StackZoneSpecification_disableKey()), true))
+        return $parent.registerBinaryCallback$3$2(zone, $R._eval$1("@<0>")._bind$1(T1)._bind$1(T2)._eval$1("1(2,3)")._check(f), $R, T1, T2);
+      t1 = this._currentTrace$1(2);
+      t2 = this._currentNode;
+      return $parent.registerBinaryCallback$3$2(zone, new O.StackZoneSpecification__registerBinaryCallback_closure(this, f, new O._Node(Y.Trace_Trace$from(t1), t2), T1, T2, $R), $R, T1, T2);
+    },
+    _stack_zone_specification$_registerBinaryCallback$4: function($self, $parent, zone, f) {
+      return this._stack_zone_specification$_registerBinaryCallback$3$4($self, $parent, zone, f, type$.dynamic, type$.dynamic, type$.dynamic);
+    },
+    _stack_zone_specification$_errorCallback$5: function($self, $parent, zone, error, stackTrace) {
+      var t1, t2, t3, asyncError, _this = this;
+      type$.StackTrace._check(stackTrace);
+      if (J.$eq$($.Zone__current.$index(0, $.$get$StackZoneSpecification_disableKey()), true))
+        return $parent.errorCallback$3(zone, error, stackTrace);
+      if (stackTrace == null) {
+        t1 = _this._currentTrace$1(3);
+        t2 = _this._currentNode;
+        stackTrace = new O._Node(Y.Trace_Trace$from(t1), t2).toChain$0();
+      } else {
+        t1 = _this._chains;
+        if (t1.$index(0, stackTrace) == null) {
+          t2 = _this._currentTrace$1(3);
+          t3 = _this._currentNode;
+          t1.$indexSet(0, stackTrace, new O._Node(Y.Trace_Trace$from(t2), t3));
+        }
+      }
+      asyncError = $parent.errorCallback$3(zone, error, stackTrace);
+      return asyncError == null ? new P.AsyncError(error, stackTrace) : asyncError;
+    },
+    _stack_zone_specification$_run$1$2: function(f, node, $T) {
+      var previousNode, stackTrace, t1, exception, t2, _this = this;
+      $T._eval$1("0()")._check(f);
+      previousNode = _this._currentNode;
+      _this._currentNode = node;
+      try {
+        t1 = f.call$0();
+        return t1;
+      } catch (exception) {
+        H.unwrapException(exception);
+        stackTrace = H.getTraceFromException(exception);
+        t1 = _this._chains;
+        t2 = stackTrace;
+        if (t1.$index(0, t2) == null)
+          t1.$indexSet(0, t2, node);
+        throw exception;
+      } finally {
+        _this.set$_currentNode(previousNode);
+      }
+    },
+    _currentTrace$1: function(level) {
+      var t1 = {};
+      t1.level = level;
+      return new T.LazyTrace(new O.StackZoneSpecification__currentTrace_closure(t1, this, P.StackTrace_current()));
+    },
+    _trimVMChain$1: function(trace) {
+      var text = J.toString$0$(trace),
+        index = J.getInterceptor$s(text).indexOf$1(text, "<asynchronous suspension>\n");
+      return index === -1 ? text : C.JSString_methods.substring$2(text, 0, index);
+    },
+    set$_currentNode: function(_currentNode) {
+      this._currentNode = type$._Node._check(_currentNode);
+    }
+  };
+  O.StackZoneSpecification_chainFor_closure.prototype = {
+    call$0: function() {
+      return U.Chain_Chain$parse(J.toString$0$(this._box_0.trace));
+    },
+    $signature: 16
+  };
+  O.StackZoneSpecification_chainFor_closure0.prototype = {
+    call$0: function() {
+      return Y.Trace_Trace$parse(this.$this._trimVMChain$1(this.original));
+    },
+    $signature: 8
+  };
+  O.StackZoneSpecification__registerCallback_closure.prototype = {
+    call$0: function() {
+      var _this = this;
+      return _this.$this._stack_zone_specification$_run$1$2(_this.f, _this.node, _this.R);
+    },
+    $signature: function() {
+      return this.R._eval$1("0()");
+    }
+  };
+  O.StackZoneSpecification__registerUnaryCallback_closure.prototype = {
+    call$1: function(arg) {
+      var _this = this,
+        t1 = _this.R;
+      return _this.$this._stack_zone_specification$_run$1$2(new O.StackZoneSpecification__registerUnaryCallback__closure(_this.f, _this.T._check(arg), t1), _this.node, t1);
+    },
+    $signature: function() {
+      return this.R._eval$1("@<0>")._bind$1(this.T)._eval$1("1(2)");
+    }
+  };
+  O.StackZoneSpecification__registerUnaryCallback__closure.prototype = {
+    call$0: function() {
+      return this.f.call$1(this.arg);
+    },
+    $signature: function() {
+      return this.R._eval$1("0()");
+    }
+  };
+  O.StackZoneSpecification__registerBinaryCallback_closure.prototype = {
+    call$2: function(arg1, arg2) {
+      var _this = this,
+        t1 = _this.R;
+      return _this.$this._stack_zone_specification$_run$1$2(new O.StackZoneSpecification__registerBinaryCallback__closure(_this.f, _this.T1._check(arg1), _this.T2._check(arg2), t1), _this.node, t1);
+    },
+    $signature: function() {
+      return this.R._eval$1("@<0>")._bind$1(this.T1)._bind$1(this.T2)._eval$1("1(2,3)");
+    }
+  };
+  O.StackZoneSpecification__registerBinaryCallback__closure.prototype = {
+    call$0: function() {
+      var _this = this;
+      return _this.R._check(_this.f.call$2(_this.arg1, _this.arg2));
+    },
+    $signature: function() {
+      return this.R._eval$1("0()");
+    }
+  };
+  O.StackZoneSpecification__currentTrace_closure.prototype = {
+    call$0: function() {
+      var text = this.$this._trimVMChain$1(this.stackTrace),
+        t1 = Y.Trace_Trace$parse(text).frames,
+        t2 = this._box_0.level;
+      if (typeof t2 !== "number")
+        return t2.$add();
+      return new Y.Trace(P.List_List$unmodifiable(H.SubListIterable$(t1, t2 + 2, null, H._arrayInstanceType(t1)._precomputed1), type$.Frame), new P._StringStackTrace(text));
+    },
+    $signature: 8
+  };
+  O._Node.prototype = {
+    toChain$0: function() {
+      var node,
+        nodes = H.setRuntimeTypeInfo([], type$.JSArray_Trace);
+      for (node = this; node != null;) {
+        C.JSArray_methods.add$1(nodes, node.trace);
+        node = node.previous;
+      }
+      return new U.Chain(P.List_List$unmodifiable(nodes, type$.Trace));
+    }
+  };
+  Y.Trace.prototype = {
+    foldFrames$2$terse: function(predicate, terse) {
+      var newFrames, t1, t2, _box_0 = {};
+      _box_0.predicate = predicate;
+      _box_0.predicate = new Y.Trace_foldFrames_closure(type$.bool_Function_Frame._check(predicate));
+      newFrames = H.setRuntimeTypeInfo([], type$.JSArray_Frame);
+      for (t1 = this.frames, t2 = H._arrayInstanceType(t1)._eval$1("ReversedListIterable<1>"), t1 = new H.ReversedListIterable(t1, t2), t2 = new H.ListIterator(t1, t1.get$length(t1), t2._eval$1("ListIterator<ListIterable.E>")); t2.moveNext$0();) {
+        t1 = t2.__internal$_current;
+        if (t1 instanceof N.UnparsedFrame || !H.boolConversionCheck(_box_0.predicate.call$1(t1)))
+          C.JSArray_methods.add$1(newFrames, t1);
+        else if (newFrames.length === 0 || !H.boolConversionCheck(_box_0.predicate.call$1(C.JSArray_methods.get$last(newFrames))))
+          C.JSArray_methods.add$1(newFrames, new A.Frame(t1.get$uri(), t1.get$line(), t1.get$column(), t1.get$member()));
+      }
+      newFrames = new H.MappedListIterable(newFrames, type$.Frame_Function_Frame._check(new Y.Trace_foldFrames_closure0(_box_0)), type$.MappedListIterable_Frame_Frame).toList$0(0);
+      if (newFrames.length > 1 && H.boolConversionCheck(_box_0.predicate.call$1(C.JSArray_methods.get$first(newFrames))))
+        C.JSArray_methods.removeAt$1(newFrames, 0);
+      return new Y.Trace(P.List_List$unmodifiable(new H.ReversedListIterable(newFrames, H._arrayInstanceType(newFrames)._eval$1("ReversedListIterable<1>")), type$.Frame), new P._StringStackTrace(this.original._stackTrace));
+    },
+    toString$0: function(_) {
+      var t1 = this.frames,
+        t2 = H._arrayInstanceType(t1),
+        t3 = type$.int;
+      return new H.MappedListIterable(t1, t2._eval$1("String(1)")._check(new Y.Trace_toString_closure(new H.MappedListIterable(t1, t2._eval$1("int(1)")._check(new Y.Trace_toString_closure0()), t2._eval$1("MappedListIterable<1,int>")).fold$1$2(0, 0, H.instantiate1(P.math__max$closure(), t3), t3))), t2._eval$1("MappedListIterable<1,String>")).join$0(0);
+    },
+    $isStackTrace: 1,
+    get$frames: function() {
+      return this.frames;
+    },
+    get$original: function() {
+      return this.original;
+    }
+  };
+  Y.Trace_Trace$current_closure.prototype = {
+    call$0: function() {
+      var t1 = this.trace,
+        t2 = t1.get$frames();
+      t2 = H.SubListIterable$(t2, this.level + 2, null, H._arrayInstanceType(t2)._precomputed1);
+      t1 = t1.get$original();
+      return new Y.Trace(P.List_List$unmodifiable(t2, type$.Frame), new P._StringStackTrace(t1._stackTrace));
+    },
+    $signature: 8
+  };
+  Y.Trace_Trace$from_closure.prototype = {
+    call$0: function() {
+      return Y.Trace_Trace$parse(this.trace.toString$0(0));
+    },
+    $signature: 8
+  };
+  Y.Trace__parseVM_closure.prototype = {
+    call$1: function(line) {
+      return A.Frame_Frame$parseVM(H._checkStringNullable(line));
+    },
+    $signature: 10
+  };
+  Y.Trace$parseV8_closure.prototype = {
+    call$1: function(line) {
+      return !J.startsWith$1$s(H._checkStringNullable(line), $.$get$_v8TraceLine());
+    },
+    $signature: 4
+  };
+  Y.Trace$parseV8_closure0.prototype = {
+    call$1: function(line) {
+      return A.Frame_Frame$parseV8(H._checkStringNullable(line));
+    },
+    $signature: 10
+  };
+  Y.Trace$parseJSCore_closure.prototype = {
+    call$1: function(line) {
+      return H._checkStringNullable(line) !== "\tat ";
+    },
+    $signature: 4
+  };
+  Y.Trace$parseJSCore_closure0.prototype = {
+    call$1: function(line) {
+      return A.Frame_Frame$parseV8(H._checkStringNullable(line));
+    },
+    $signature: 10
+  };
+  Y.Trace$parseFirefox_closure.prototype = {
+    call$1: function(line) {
+      H._checkStringNullable(line);
+      return line.length !== 0 && line !== "[native code]";
+    },
+    $signature: 4
+  };
+  Y.Trace$parseFirefox_closure0.prototype = {
+    call$1: function(line) {
+      return A.Frame_Frame$parseFirefox(H._checkStringNullable(line));
+    },
+    $signature: 10
+  };
+  Y.Trace$parseFriendly_closure.prototype = {
+    call$1: function(line) {
+      return !J.startsWith$1$s(H._checkStringNullable(line), "=====");
+    },
+    $signature: 4
+  };
+  Y.Trace$parseFriendly_closure0.prototype = {
+    call$1: function(line) {
+      return A.Frame_Frame$parseFriendly(H._checkStringNullable(line));
+    },
+    $signature: 10
+  };
+  Y.Trace_foldFrames_closure.prototype = {
+    call$1: function(frame) {
+      if (H.boolConversionCheck(this.oldPredicate.call$1(frame)))
+        return true;
+      if (frame.get$isCore())
+        return true;
+      if (frame.get$$package() === "stack_trace")
+        return true;
+      if (!J.contains$1$asx(frame.get$member(), "<async>"))
+        return false;
+      return frame.get$line() == null;
+    },
+    $signature: 21
+  };
+  Y.Trace_foldFrames_closure0.prototype = {
+    call$1: function(frame) {
+      var t1, t2;
+      type$.Frame._check(frame);
+      if (frame instanceof N.UnparsedFrame || !H.boolConversionCheck(this._box_0.predicate.call$1(frame)))
+        return frame;
+      t1 = frame.get$library();
+      t2 = $.$get$_terseRegExp();
+      t1.toString;
+      return new A.Frame(P.Uri_parse(H.stringReplaceAllUnchecked(t1, t2, "")), null, null, frame.get$member());
+    },
+    $signature: 46
+  };
+  Y.Trace_toString_closure0.prototype = {
+    call$1: function(frame) {
+      type$.Frame._check(frame);
+      return frame.get$location(frame).length;
+    },
+    $signature: 39
+  };
+  Y.Trace_toString_closure.prototype = {
+    call$1: function(frame) {
+      type$.Frame._check(frame);
+      if (frame instanceof N.UnparsedFrame)
+        return frame.toString$0(0) + "\n";
+      return J.padRight$1$s(frame.get$location(frame), this.longest) + "  " + H.S(frame.get$member()) + "\n";
+    },
+    $signature: 38
+  };
+  N.UnparsedFrame.prototype = {
+    toString$0: function(_) {
+      return this.member;
+    },
+    $isFrame: 1,
+    get$uri: function() {
+      return this.uri;
+    },
+    get$line: function() {
+      return null;
+    },
+    get$column: function() {
+      return null;
+    },
+    get$isCore: function() {
+      return false;
+    },
+    get$library: function() {
+      return "unparsed";
+    },
+    get$$package: function() {
+      return null;
+    },
+    get$location: function() {
+      return "unparsed";
+    },
+    get$member: function() {
+      return this.member;
+    }
+  };
+  K.GuaranteeChannel.prototype = {
+    get$stream: function(_) {
+      var t1 = this._streamController;
+      t1.toString;
+      return new P._ControllerStream(t1, H._instanceType(t1)._eval$1("_ControllerStream<1>"));
+    },
+    get$sink: function() {
+      return this._sink;
+    },
+    GuaranteeChannel$3$allowSinkErrors: function(innerSink, allowSinkErrors, _box_0, $T) {
+      var _this = this;
+      _this.set$_sink(new K._GuaranteeSink(innerSink, _this, new P._AsyncCompleter(new P._Future($.Zone__current, type$._Future_dynamic), type$._AsyncCompleter_dynamic), allowSinkErrors, $T._eval$1("_GuaranteeSink<0>")));
+      _this.set$_streamController(P.StreamController_StreamController(null, new K.GuaranteeChannel_closure(_box_0, _this), true, $T));
+    },
+    _onSinkDisconnected$0: function() {
+      this._disconnected = true;
+      var t1 = this._subscription;
+      if (t1 != null)
+        t1.cancel$0();
+      this._streamController.close$0(0);
+    },
+    set$_sink: function(_sink) {
+      this._sink = this.$ti._eval$1("_GuaranteeSink<1>")._check(_sink);
+    },
+    set$_streamController: function(_streamController) {
+      this._streamController = this.$ti._eval$1("StreamController<1>")._check(_streamController);
+    },
+    set$_subscription: function(_subscription) {
+      this._subscription = this.$ti._eval$1("StreamSubscription<1>")._check(_subscription);
+    }
+  };
+  K.GuaranteeChannel_closure.prototype = {
+    call$0: function() {
+      var t2, t3,
+        t1 = this.$this;
+      if (t1._disconnected)
+        return;
+      t2 = this._box_0.innerStream;
+      t3 = t1._streamController;
+      t1.set$_subscription(t2.listen$3$onDone$onError(t3.get$add(t3), new K.GuaranteeChannel__closure(t1), t3.get$addError()));
+    },
+    $signature: 0
+  };
+  K.GuaranteeChannel__closure.prototype = {
+    call$0: function() {
+      var t1 = this.$this;
+      t1._sink._onStreamDisconnected$0();
+      t1._streamController.close$0(0);
+    },
+    $signature: 0
+  };
+  K._GuaranteeSink.prototype = {
+    get$done: function() {
+      return this._doneCompleter.future;
+    },
+    add$1: function(_, data) {
+      var t1, _this = this;
+      _this.$ti._precomputed1._check(data);
+      if (_this._closed)
+        throw H.wrapException(P.StateError$("Cannot add event after closing."));
+      if (_this._addStreamSubscription != null)
+        throw H.wrapException(P.StateError$("Cannot add event while adding stream."));
+      if (_this._disconnected)
+        return;
+      t1 = _this._inner;
+      t1._async$_target.add$1(0, t1.$ti._precomputed1._check(data));
+    },
+    addError$2: function(error, stackTrace) {
+      var _this = this;
+      type$.StackTrace._check(stackTrace);
+      if (_this._closed)
+        throw H.wrapException(P.StateError$("Cannot add event after closing."));
+      if (_this._addStreamSubscription != null)
+        throw H.wrapException(P.StateError$("Cannot add event while adding stream."));
+      if (_this._disconnected)
+        return;
+      _this._addError$2(error, stackTrace);
+    },
+    addError$1: function(error) {
+      return this.addError$2(error, null);
+    },
+    _addError$2: function(error, stackTrace) {
+      var _this = this;
+      type$.StackTrace._check(stackTrace);
+      if (_this._allowErrors) {
+        _this._inner._async$_target.addError$2(error, stackTrace);
+        return;
+      }
+      _this._doneCompleter.completeError$2(error, stackTrace);
+      _this._onStreamDisconnected$0();
+      _this._channel._onSinkDisconnected$0();
+      _this._inner._async$_target.close$0(0).catchError$1(new K._GuaranteeSink__addError_closure());
+    },
+    _addError$1: function(error) {
+      return this._addError$2(error, null);
+    },
+    addStream$1: function(stream) {
+      var t1, t2, _this = this;
+      _this.$ti._eval$1("Stream<1>")._check(stream);
+      if (_this._closed)
+        throw H.wrapException(P.StateError$("Cannot add stream after closing."));
+      if (_this._addStreamSubscription != null)
+        throw H.wrapException(P.StateError$("Cannot add stream while adding stream."));
+      if (_this._disconnected) {
+        t1 = new P._Future($.Zone__current, type$._Future_void);
+        t1._asyncComplete$1(null);
+        return t1;
+      }
+      t1 = new P._SyncCompleter(new P._Future($.Zone__current, type$._Future_dynamic), type$._SyncCompleter_dynamic);
+      _this._addStreamCompleter = t1;
+      t2 = _this._inner;
+      _this.set$_addStreamSubscription(stream.listen$3$onDone$onError(t2.get$add(t2), t1.get$complete(), _this.get$_addError()));
+      return _this._addStreamCompleter.future.then$1$1(new K._GuaranteeSink_addStream_closure(_this), type$.void);
+    },
+    close$0: function(_) {
+      var _this = this;
+      if (_this._addStreamSubscription != null)
+        throw H.wrapException(P.StateError$("Cannot close sink while adding stream."));
+      if (_this._closed)
+        return _this._doneCompleter.future;
+      _this._closed = true;
+      if (!_this._disconnected) {
+        _this._channel._onSinkDisconnected$0();
+        _this._doneCompleter.complete$1(_this._inner._async$_target.close$0(0));
+      }
+      return _this._doneCompleter.future;
+    },
+    _onStreamDisconnected$0: function() {
+      var t1, _this = this;
+      _this._disconnected = true;
+      t1 = _this._doneCompleter;
+      if (t1.future._state === 0)
+        t1.complete$0();
+      t1 = _this._addStreamSubscription;
+      if (t1 == null)
+        return;
+      _this._addStreamCompleter.complete$1(t1.cancel$0());
+      _this._addStreamCompleter = null;
+      _this.set$_addStreamSubscription(null);
+    },
+    set$_addStreamSubscription: function(_addStreamSubscription) {
+      this._addStreamSubscription = this.$ti._eval$1("StreamSubscription<1>")._check(_addStreamSubscription);
+    },
+    $isEventSink: 1,
+    $isStreamConsumer: 1,
+    $isStreamSink: 1,
+    $isSink: 1
+  };
+  K._GuaranteeSink__addError_closure.prototype = {
+    call$1: function(_) {
+    },
+    $signature: 3
+  };
+  K._GuaranteeSink_addStream_closure.prototype = {
+    call$1: function(_) {
+      var t1 = this.$this;
+      t1._addStreamCompleter = null;
+      t1.set$_addStreamSubscription(null);
+    },
+    $signature: 3
+  };
+  D._MultiChannel.prototype = {
+    _MultiChannel$1: function(_inner, $T) {
+      var t2, _this = this,
+        t1 = _this._mainController;
+      _this._controllers.$indexSet(0, 0, t1);
+      t2 = t1._local._streamController;
+      t2.toString;
+      new P._ControllerStream(t2, H._instanceType(t2)._eval$1("_ControllerStream<1>")).listen$2$onDone(new D._MultiChannel_closure(_this, $T), new D._MultiChannel_closure0(_this));
+      t2 = _this._multi_channel$_inner._streamController;
+      t2.toString;
+      _this._innerStreamSubscription = new P._ControllerStream(t2, H._instanceType(t2)._eval$1("_ControllerStream<1>")).listen$3$onDone$onError(new D._MultiChannel_closure1(_this, $T), _this.get$_closeInnerChannel(), t1._local._sink.get$addError());
+    },
+    virtualChannel$1: function(id) {
+      var t2, t3, controller, _this = this, t1 = {};
+      t1.outputId = t1.inputId = null;
+      if (id != null) {
+        t1.inputId = id;
+        t1.outputId = id + 1;
+        t2 = id;
+      } else {
+        t2 = _this._nextId;
+        t3 = t1.inputId = t2 + 1;
+        t1.outputId = t2;
+        _this._nextId = t2 + 2;
+        t2 = t3;
+      }
+      if (_this._multi_channel$_inner == null) {
+        t1 = _this.$ti;
+        t3 = new P._Future($.Zone__current, type$._Future_dynamic);
+        t3._asyncComplete$1(null);
+        return new D.VirtualChannel(_this, t2, new P._EmptyStream(t1._eval$1("_EmptyStream<1>")), new S.NullStreamSink(t3, t1._eval$1("NullStreamSink<1>")), t1._eval$1("VirtualChannel<1>"));
+      }
+      if (_this._pendingIds.remove$1(0, t2))
+        controller = _this._controllers.$index(0, t2);
+      else {
+        t3 = _this._controllers;
+        if (t3.containsKey$1(t2) || _this._closedIds.contains$1(0, t2))
+          throw H.wrapException(P.ArgumentError$("A virtual channel with id " + H.S(id) + " already exists."));
+        else {
+          controller = B.StreamChannelController$(true, true, _this.$ti._precomputed1);
+          t3.$indexSet(0, t2, controller);
+        }
+      }
+      t2 = controller._local._streamController;
+      t2.toString;
+      new P._ControllerStream(t2, H._instanceType(t2)._eval$1("_ControllerStream<1>")).listen$2$onDone(new D._MultiChannel_virtualChannel_closure(t1, _this), new D._MultiChannel_virtualChannel_closure0(t1, _this));
+      t1 = t1.outputId;
+      t2 = controller._foreign;
+      t3 = t2._streamController;
+      t3.toString;
+      return new D.VirtualChannel(_this, t1, new P._ControllerStream(t3, H._instanceType(t3)._eval$1("_ControllerStream<1>")), t2._sink, _this.$ti._eval$1("VirtualChannel<1>"));
+    },
+    virtualChannel$0: function() {
+      return this.virtualChannel$1(null);
+    },
+    _closeChannel$2: function(inputId, outputId) {
+      var t1, t2, _this = this;
+      _this._closedIds.add$1(0, inputId);
+      t1 = _this._controllers;
+      t1.remove$1(0, inputId)._local._sink.close$0(0);
+      t2 = _this._multi_channel$_inner;
+      if (t2 == null)
+        return;
+      t2._sink.add$1(0, H.setRuntimeTypeInfo([outputId], type$.JSArray_int));
+      if (t1.get$isEmpty(t1))
+        _this._closeInnerChannel$0();
+    },
+    _closeInnerChannel$0: function() {
+      var t1, t2, t3, _i, _this = this;
+      _this._multi_channel$_inner._sink.close$0(0);
+      _this._innerStreamSubscription.cancel$0();
+      _this._multi_channel$_inner = null;
+      for (t1 = _this._controllers, t2 = P.List_List$from(t1.get$values(), true, type$.dynamic), t3 = t2.length, _i = 0; _i < t2.length; t2.length === t3 || (0, H.throwConcurrentModificationError)(t2), ++_i)
+        t2[_i].get$local()._sink.close$0(0);
+      t1.clear$0(0);
+    },
+    $isMultiChannel: 1
+  };
+  D._MultiChannel_closure.prototype = {
+    call$1: function(message) {
+      this.T._check(message);
+      return this.$this._multi_channel$_inner._sink.add$1(0, [0, message]);
+    },
+    $signature: function() {
+      return this.T._eval$1("~(0)");
+    }
+  };
+  D._MultiChannel_closure0.prototype = {
+    call$0: function() {
+      return this.$this._closeChannel$2(0, 0);
+    },
+    $signature: 1
+  };
+  D._MultiChannel_closure1.prototype = {
+    call$1: function(message) {
+      var t3, controller,
+        t1 = J.getInterceptor$asx(message),
+        id = t1.$index(message, 0),
+        t2 = this.$this;
+      if (t2._closedIds.contains$1(0, id))
+        return;
+      H._checkIntNullable(id);
+      t3 = this.T;
+      controller = t2._controllers.putIfAbsent$2(id, new D._MultiChannel__closure(t2, id, t3));
+      t2 = t1.get$length(message);
+      if (typeof t2 !== "number")
+        return t2.$gt();
+      if (t2 > 1)
+        controller._local._sink.add$1(0, t3._check(t1.$index(message, 1)));
+      else
+        controller._local._sink.close$0(0);
+    },
+    $signature: 3
+  };
+  D._MultiChannel__closure.prototype = {
+    call$0: function() {
+      this.$this._pendingIds.add$1(0, H._checkIntNullable(this.id));
+      return B.StreamChannelController$(true, true, this.T);
+    },
+    $signature: function() {
+      return this.T._eval$1("StreamChannelController<0>()");
+    }
+  };
+  D._MultiChannel_virtualChannel_closure.prototype = {
+    call$1: function(message) {
+      var t1 = this.$this;
+      t1.$ti._precomputed1._check(message);
+      return t1._multi_channel$_inner._sink.add$1(0, [this._box_0.outputId, message]);
+    },
+    $signature: function() {
+      return this.$this.$ti._eval$1("~(1)");
+    }
+  };
+  D._MultiChannel_virtualChannel_closure0.prototype = {
+    call$0: function() {
+      var t1 = this._box_0;
+      return this.$this._closeChannel$2(t1.inputId, t1.outputId);
+    },
+    $signature: 1
+  };
+  D.VirtualChannel.prototype = {$isMultiChannel: 1,
+    get$stream: function(receiver) {
+      return this.stream;
+    }
+  };
+  N.StreamChannelCompleter.prototype = {
+    set$_stream_channel_completer$_channel: function(_channel) {
+      this._stream_channel_completer$_channel = this.$ti._eval$1("StreamChannel<1>")._check(_channel);
+    }
+  };
+  B.StreamChannelController.prototype = {
+    get$local: function() {
+      return this._local;
+    },
+    set$_local: function(_local) {
+      this._local = this.$ti._eval$1("StreamChannel<1>")._check(_local);
+    },
+    set$_foreign: function(_foreign) {
+      this._foreign = this.$ti._eval$1("StreamChannel<1>")._check(_foreign);
+    }
+  };
+  R.StreamChannel.prototype = {};
+  R._StreamChannel.prototype = {
+    get$stream: function(receiver) {
+      return this.stream;
+    }
+  };
+  R.StreamChannelMixin.prototype = {$isStreamChannel: 1};
+  E.StringScannerException.prototype = {};
+  S.SpanScanner.prototype = {
+    spanFrom$1: function(startState) {
+      var endPosition = this._string_scanner$_position;
+      return this._sourceFile.span$2(startState.position, endPosition);
+    },
+    matches$1: function(_, pattern) {
+      var _this = this;
+      if (!_this.super$StringScanner$matches(0, pattern)) {
+        _this._lastSpan = null;
+        return false;
+      }
+      _this._lastSpan = _this._sourceFile.span$2(_this._string_scanner$_position, _this.get$lastMatch().get$end());
+      return true;
+    },
+    error$3$length$position: function(_, message, $length, position) {
+      var t1 = this.string;
+      B.validateErrorArgs(t1, null, position, $length);
+      throw H.wrapException(E.StringScannerException$(message, this._sourceFile.span$2(position, position + $length), t1));
+    }
+  };
+  S._SpanScannerState.prototype = {$isLineScannerState: 1};
+  X.StringScanner.prototype = {
+    get$lastMatch: function() {
+      var _this = this;
+      if (_this._string_scanner$_position !== _this._lastMatchPosition)
+        _this._lastMatch = null;
+      return _this._lastMatch;
+    },
+    peekChar$0: function() {
+      var index = this._string_scanner$_position;
+      if (index < 0 || index >= this.string.length)
+        return null;
+      return J.codeUnitAt$1$s(this.string, index);
+    },
+    scan$1: function(pattern) {
+      var _this = this,
+        success = _this.matches$1(0, pattern);
+      if (success)
+        _this._lastMatchPosition = _this._string_scanner$_position = _this._lastMatch.get$end();
+      return success;
+    },
+    expect$2$name: function(pattern, $name) {
+      var t1;
+      if (this.scan$1(pattern))
+        return;
+      if ($name == null)
+        if (type$.RegExp._is(pattern))
+          $name = "/" + pattern.pattern + "/";
+        else {
+          t1 = J.toString$0$(pattern);
+          t1 = H.stringReplaceAllUnchecked(t1, "\\", "\\\\");
+          $name = '"' + H.stringReplaceAllUnchecked(t1, '"', '\\"') + '"';
+        }
+      this.error$3$length$position(0, "expected " + $name + ".", 0, this._string_scanner$_position);
+    },
+    expect$1: function(pattern) {
+      return this.expect$2$name(pattern, null);
+    },
+    matches$1: function(_, pattern) {
+      var _this = this,
+        t1 = J.matchAsPrefix$2$s(pattern, _this.string, _this._string_scanner$_position);
+      _this._lastMatch = t1;
+      _this._lastMatchPosition = _this._string_scanner$_position;
+      return t1 != null;
+    }
+  };
+  A.AsciiGlyphSet.prototype = {
+    glyphOrAscii$2: function(glyph, alternative) {
+      return alternative;
+    },
+    get$horizontalLine: function() {
+      return "-";
+    },
+    get$verticalLine: function() {
+      return "|";
+    },
+    get$topLeftCorner: function() {
+      return ",";
+    },
+    get$bottomLeftCorner: function() {
+      return "'";
+    },
+    get$upEnd: function() {
+      return "'";
+    },
+    get$downEnd: function() {
+      return ",";
+    }
+  };
+  K.UnicodeGlyphSet.prototype = {
+    glyphOrAscii$2: function(glyph, alternative) {
+      return glyph;
+    },
+    get$horizontalLine: function() {
+      return "\u2500";
+    },
+    get$verticalLine: function() {
+      return "\u2502";
+    },
+    get$topLeftCorner: function() {
+      return "\u250c";
+    },
+    get$bottomLeftCorner: function() {
+      return "\u2514";
+    },
+    get$upEnd: function() {
+      return "\u2575";
+    },
+    get$downEnd: function() {
+      return "\u2577";
+    }
+  };
+  L.internalBootstrapBrowserTest_closure.prototype = {
+    call$0: function() {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter(type$.Null),
+        $async$returnValue, t1, serialized, formatter, manager, $async$temp1;
+      var $async$call$0 = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1)
+          return P._asyncRethrow($async$result, $async$completer);
+        while (true)
+          switch ($async$goto) {
+            case 0:
+              // Function start
+              manager = type$.SuiteChannelManager._as($.Zone__current.$index(0, $.$get$_currentKey()));
+              if (manager == null)
+                H.throwExpression(P.StateError$("suiteChannel() may only be called within a test worker."));
+              t1 = manager.connectOut$1("test.browser.mapper");
+              t1 = t1.get$stream(t1);
+              $async$temp1 = type$.Map_dynamic_dynamic;
+              $async$goto = 3;
+              return P._asyncAwait(t1.get$first(t1), $async$call$0);
+            case 3:
+              // returning from await.
+              serialized = $async$temp1._as($async$result);
+              if (serialized == null) {
+                // goto return
+                $async$goto = 1;
+                break;
+              }
+              t1 = E.JSStackTraceMapper_deserialize(serialized);
+              formatter = type$.StackTraceFormatter._as($.Zone__current.$index(0, $.$get$_currentKey0()));
+              if (formatter == null)
+                H.throwExpression(P.StateError$("setStackTraceMapper() may only be called within a test worker."));
+              formatter.configure$1$mapper(t1);
+            case 1:
+              // return
+              return P._asyncReturn($async$returnValue, $async$completer);
+          }
+      });
+      return P._asyncStartSync($async$call$0, $async$completer);
+    },
+    $signature: 2
+  };
+  N.postMessageChannel_closure.prototype = {
+    call$1: function(message) {
+      var t1, t2;
+      type$.MessageEvent._check(message);
+      t1 = message.origin;
+      t2 = window.location;
+      return t1 === (t2 && C.Location_methods).get$origin(t2) && J.$eq$(new P._AcceptStructuredCloneDart2Js([], []).convertNativeToDart_AcceptStructuredClone$2$mustCopy(message.data, true), "port");
+    },
+    $signature: 69
+  };
+  N.postMessageChannel_closure0.prototype = {
+    call$1: function(message) {
+      var t2, t3, portSubscription,
+        t1 = type$.MessageEvent,
+        port = J.get$first$ax(t1._check(message).ports);
+      port.toString;
+      t2 = this.controller;
+      t3 = type$.void_Function_MessageEvent._check(new N.postMessageChannel__closure(t2));
+      type$.void_Function._check(null);
+      portSubscription = W._EventStreamSubscription$(port, "message", t3, false, t1);
+      t2 = t2._local._streamController;
+      t2.toString;
+      new P._ControllerStream(t2, H._instanceType(t2)._eval$1("_ControllerStream<1>")).listen$2$onDone(new N.postMessageChannel__closure0(port), new N.postMessageChannel__closure1(port, portSubscription));
+    },
+    $signature: 29
+  };
+  N.postMessageChannel__closure.prototype = {
+    call$1: function(message) {
+      type$.MessageEvent._check(message);
+      this.controller._local._sink.add$1(0, new P._AcceptStructuredCloneDart2Js([], []).convertNativeToDart_AcceptStructuredClone$2$mustCopy(message.data, true));
+    },
+    $signature: 29
+  };
+  N.postMessageChannel__closure0.prototype = {
+    call$1: function(data) {
+      C.MessagePort_methods.postMessage$1(this.port, P.LinkedHashMap_LinkedHashMap$_literal(["data", data], type$.String, type$.dynamic));
+    },
+    $signature: 3
+  };
+  N.postMessageChannel__closure1.prototype = {
+    call$0: function() {
+      var t1 = type$.String;
+      C.MessagePort_methods.postMessage$1(this.port, P.LinkedHashMap_LinkedHashMap$_literal(["event", "done"], t1, t1));
+      this.portSubscription.cancel$0();
+    },
+    $signature: 0
+  };
+  K.ClosedException.prototype = {
+    toString$0: function(_) {
+      return "This test has been closed.";
+    },
+    $isException: 1
+  };
+  X.Declarer.prototype = {
+    test$9$onPlatform$retry$skip$solo$tags$testOn$timeout: function($name, body, onPlatform, retry, skip, solo, tags, testOn, timeout) {
+      var newMetadata, metadata, t1, t2, _this = this;
+      type$.dynamic_Function._check(body);
+      type$.Map_String_dynamic._check(onPlatform);
+      _this._checkNotBuilt$1("test");
+      newMetadata = O.Metadata$parse(onPlatform, H.boolConversionCheck(_this._noRetry) ? 0 : retry, skip, tags, testOn, timeout);
+      newMetadata.validatePlatformSelectors$1(_this._platformVariables);
+      metadata = _this._metadata.merge$1(newMetadata);
+      t1 = _this._declarer$_name;
+      t1 = t1 == null ? $name : t1 + " " + $name;
+      t2 = H.boolConversionCheck(_this._collectTraces) ? Y.Trace_Trace$current(2) : null;
+      C.JSArray_methods.add$1(_this._entries, new U.LocalTest(t1, metadata, t2, false, new X.Declarer_test_closure(_this, body), false));
+    },
+    group$9$onPlatform$retry$skip$solo$tags$testOn$timeout: function($name, body, onPlatform, retry, skip, solo, tags, testOn, timeout) {
+      var t2, newMetadata, t3, metadata, t4, trace, t5, t6, t7, t8, t9, t10, t11, t12, declarer, _this = this, _null = null,
+        t1 = type$.void_Function;
+      t1._check(body);
+      type$.Map_String_dynamic._check(onPlatform);
+      _this._checkNotBuilt$1("group");
+      t2 = H.boolConversionCheck(_this._noRetry);
+      newMetadata = O.Metadata$parse(onPlatform, t2 ? 0 : retry, skip, tags, testOn, timeout);
+      t3 = _this._platformVariables;
+      newMetadata.validatePlatformSelectors$1(t3);
+      metadata = _this._metadata.merge$1(newMetadata);
+      t4 = H.boolConversionCheck(_this._collectTraces);
+      trace = t4 ? Y.Trace_Trace$current(2) : _null;
+      t5 = _this._declarer$_name;
+      t5 = t5 == null ? $name : t5 + " " + $name;
+      t6 = type$.JSArray_of_dynamic_Function;
+      t7 = H.setRuntimeTypeInfo([], t6);
+      t8 = H.setRuntimeTypeInfo([], t6);
+      t9 = H.setRuntimeTypeInfo([], t6);
+      t10 = P.Duration$(0, 12);
+      t6 = H.setRuntimeTypeInfo([], t6);
+      t11 = type$.JSArray_GroupEntry;
+      t12 = H.setRuntimeTypeInfo([], t11);
+      t11 = H.setRuntimeTypeInfo([], t11);
+      declarer = new X.Declarer(_this, t5, metadata, t3, trace, t4, t2, t7, t8, t9, new R.Timeout(t10, _null), t6, t12, t11);
+      t12 = type$.dynamic;
+      P.runZoned(t1._check(new X.Declarer_group_closure(body)), _null, _null, P.LinkedHashMap_LinkedHashMap$_literal([C.Symbol_Drw, declarer], t12, t12), type$.void);
+      t12 = _this._entries;
+      C.JSArray_methods.add$1(t12, declarer.build$0());
+      t1 = t11.length;
+      if (t1 !== 0)
+        C.JSArray_methods.add$1(_this._soloEntries, C.JSArray_methods.get$last(t12));
+    },
+    build$0: function() {
+      var t1, t2, _this = this;
+      _this._checkNotBuilt$1("build");
+      _this._built = true;
+      t1 = _this._entries;
+      t2 = H._arrayInstanceType(t1);
+      return O.Group$(_this._declarer$_name, new H.MappedListIterable(t1, t2._eval$1("GroupEntry(1)")._check(new X.Declarer_build_closure(_this)), t2._eval$1("MappedListIterable<1,GroupEntry>")).toList$0(0), _this._metadata, _this.get$_setUpAll(), _this.get$_tearDownAll(), _this._declarer$_trace);
+    },
+    _checkNotBuilt$1: function($name) {
+      if (!this._built)
+        return;
+      throw H.wrapException(P.StateError$("Can't call " + $name + "() once tests have begun running."));
+    },
+    _runSetUps$0: function() {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter(type$.dynamic),
+        $async$self = this, t1;
+      var $async$_runSetUps$0 = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1)
+          return P._asyncRethrow($async$result, $async$completer);
+        while (true)
+          switch ($async$goto) {
+            case 0:
+              // Function start
+              t1 = $async$self._declarer$_parent;
+              $async$goto = t1 != null ? 2 : 3;
+              break;
+            case 2:
+              // then
+              $async$goto = 4;
+              return P._asyncAwait(t1._runSetUps$0(), $async$_runSetUps$0);
+            case 4:
+              // returning from await.
+            case 3:
+              // join
+              $async$goto = 5;
+              return P._asyncAwait(P.Future_forEach($async$self._setUps, new X.Declarer__runSetUps_closure(), type$.dynamic_Function), $async$_runSetUps$0);
+            case 5:
+              // returning from await.
+              // implicit return
+              return P._asyncReturn(null, $async$completer);
+          }
+      });
+      return P._asyncStartSync($async$_runSetUps$0, $async$completer);
+    },
+    get$_setUpAll: function() {
+      return null;
+    },
+    get$_tearDownAll: function() {
+      var _this = this,
+        t1 = _this._tearDownAlls.length;
+      if (t1 === 0)
+        return null;
+      t1 = _this._declarer$_name;
+      t1 = t1 == null ? "(tearDownAll)" : t1 + " (tearDownAll)";
+      return new U.LocalTest(t1, _this._metadata.change$1$timeout(_this._timeout), null, true, new X.Declarer__tearDownAll_closure(_this), false);
+    }
+  };
+  X.Declarer_test_closure.prototype = {
+    call$0: function() {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter(type$.Null),
+        $async$returnValue, $async$self = this, declarer, declarer0, t1, t2, t3, t4, t5, _i, tearDown, t6, parents;
+      var $async$call$0 = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1)
+          return P._asyncRethrow($async$result, $async$completer);
+        while (true)
+          $async$outer:
+            switch ($async$goto) {
+              case 0:
+                // Function start
+                parents = H.setRuntimeTypeInfo([], type$.JSArray_Declarer);
+                for (declarer = $async$self.$this, declarer0 = declarer; declarer0 != null; declarer0 = declarer0._declarer$_parent)
+                  C.JSArray_methods.add$1(parents, declarer0);
+                for (t1 = type$.ReversedListIterable_Declarer, t2 = new H.ReversedListIterable(parents, t1), t1 = new H.ListIterator(t2, t2.get$length(t2), t1._eval$1("ListIterator<ListIterable.E>")), t2 = type$.Invoker, t3 = type$.dynamic_Function, t4 = type$.Declarer; t1.moveNext$0();)
+                  for (t5 = t1.__internal$_current._tearDowns, _i = 0; false; ++_i) {
+                    if (_i >= 0) {
+                      $async$returnValue = H.ioore(t5, _i);
+                      // goto return
+                      $async$goto = 1;
+                      break $async$outer;
+                    }
+                    tearDown = t5[_i];
+                    t6 = t2._as($.Zone__current.$index(0, C.Symbol_cQL));
+                    t6.toString;
+                    t3._check(tearDown);
+                    if (H.boolConversionCheck(H._asBoolNullable($.Zone__current.$index(0, t6._closableKey))) && t6._onCloseCompleter.future._state !== 0)
+                      H.throwExpression(K.ClosedException$());
+                    if (t6._invoker$_controller._liveTest._live_test_controller$_controller._test.isScaffoldAll)
+                      C.JSArray_methods.add$1(t4._as($.Zone__current.$index(0, C.Symbol_Drw))._tearDownAlls, tearDown);
+                    else
+                      C.JSArray_methods.add$1(t6._invoker$_tearDowns, tearDown);
+                  }
+                t1 = type$.dynamic;
+                $async$goto = 3;
+                return P._asyncAwait(P.runZoned(new X.Declarer_test__closure(declarer, $async$self.body), null, null, P.LinkedHashMap_LinkedHashMap$_literal([C.Symbol_Drw, declarer], t1, t1), type$.Future_void), $async$call$0);
+              case 3:
+                // returning from await.
+              case 1:
+                // return
+                return P._asyncReturn($async$returnValue, $async$completer);
+            }
+      });
+      return P._asyncStartSync($async$call$0, $async$completer);
+    },
+    $signature: 2
+  };
+  X.Declarer_test__closure.prototype = {
+    call$0: function() {
+      return type$.Invoker._as($.Zone__current.$index(0, C.Symbol_cQL)).waitForOutstandingCallbacks$1(new X.Declarer_test___closure(this.$this, this.body));
+    },
+    $signature: 13
+  };
+  X.Declarer_test___closure.prototype = {
+    call$0: function() {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter(type$.Null),
+        $async$self = this;
+      var $async$call$0 = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1)
+          return P._asyncRethrow($async$result, $async$completer);
+        while (true)
+          switch ($async$goto) {
+            case 0:
+              // Function start
+              $async$goto = 2;
+              return P._asyncAwait($async$self.$this._runSetUps$0(), $async$call$0);
+            case 2:
+              // returning from await.
+              $async$goto = 3;
+              return P._asyncAwait($async$self.body.call$0(), $async$call$0);
+            case 3:
+              // returning from await.
+              // implicit return
+              return P._asyncReturn(null, $async$completer);
+          }
+      });
+      return P._asyncStartSync($async$call$0, $async$completer);
+    },
+    $signature: 2
+  };
+  X.Declarer_group_closure.prototype = {
+    call$0: function() {
+      if (!type$.Future_dynamic._is(this.body.call$0()))
+        return;
+      throw H.wrapException(P.ArgumentError$("Groups may not be async."));
+    },
+    $signature: 0
+  };
+  X.Declarer_build_closure.prototype = {
+    call$1: function(entry) {
+      var t1;
+      type$.GroupEntry._check(entry);
+      t1 = this.$this._soloEntries;
+      return t1.length !== 0 && !C.JSArray_methods.contains$1(t1, entry) ? new U.LocalTest(entry.get$name(entry), entry.get$metadata().change$2$skip$skipReason(true, 'does not have "solo"'), null, false, null, true) : entry;
+    },
+    $signature: 22
+  };
+  X.Declarer__runSetUps_closure.prototype = {
+    call$1: function(setUp) {
+      return setUp.call$0();
+    },
+    $signature: 18
+  };
+  X.Declarer__tearDownAll_closure.prototype = {
+    call$0: function() {
+      var t1 = this.$this,
+        t2 = type$.dynamic;
+      return P.runZoned(new X.Declarer__tearDownAll__closure(t1), null, null, P.LinkedHashMap_LinkedHashMap$_literal([C.Symbol_Drw, t1], t2, t2), type$.Future_Null);
+    },
+    $signature: 2
+  };
+  X.Declarer__tearDownAll__closure.prototype = {
+    call$0: function() {
+      return type$.Invoker._as($.Zone__current.$index(0, C.Symbol_cQL)).unclosable$1$1(new X.Declarer__tearDownAll___closure(this.$this), type$.Future_Null);
+    },
+    $signature: 2
+  };
+  X.Declarer__tearDownAll___closure.prototype = {
+    call$0: function() {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter(type$.Null),
+        $async$returnValue, $async$self = this, t1, t2;
+      var $async$call$0 = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1)
+          return P._asyncRethrow($async$result, $async$completer);
+        while (true)
+          switch ($async$goto) {
+            case 0:
+              // Function start
+              t1 = $async$self.$this._tearDownAlls;
+            case 3:
+              // for condition
+              if (!(t2 = t1.length, t2 !== 0)) {
+                // goto after for
+                $async$goto = 4;
+                break;
+              }
+              if (0 >= t2) {
+                $async$returnValue = H.ioore(t1, -1);
+                // goto return
+                $async$goto = 1;
+                break;
+              }
+              $async$goto = 5;
+              return P._asyncAwait(V.errorsDontStopTest(t1.pop()), $async$call$0);
+            case 5:
+              // returning from await.
+              // goto for condition
+              $async$goto = 3;
+              break;
+            case 4:
+              // after for
+            case 1:
+              // return
+              return P._asyncReturn($async$returnValue, $async$completer);
+          }
+      });
+      return P._asyncStartSync($async$call$0, $async$completer);
+    },
+    $signature: 2
+  };
+  O.Group.prototype = {
+    forPlatform$1: function(platform) {
+      var newMetadata, filtered, _this = this,
+        t1 = _this.metadata;
+      if (!H.boolConversionCheck(t1.testOn.evaluate$1(platform)))
+        return null;
+      newMetadata = t1.forPlatform$1(platform);
+      filtered = _this._group$_map$1(new O.Group_forPlatform_closure(platform));
+      if (filtered.length === 0 && _this.entries.length !== 0)
+        return null;
+      return O.Group$(_this.name, filtered, newMetadata, _this.setUpAll, _this.tearDownAll, _this.trace);
+    },
+    _group$_map$1: function(callback) {
+      var t1 = this.entries,
+        t2 = H._arrayInstanceType(t1),
+        t3 = t2._eval$1("MappedListIterable<1,GroupEntry>");
+      t3 = new H.MappedListIterable(t1, t2._eval$1("GroupEntry(1)")._check(new O.Group__map_closure(type$.GroupEntry_Function_GroupEntry._check(callback))), t3).super$Iterable$where(0, t3._eval$1("bool(ListIterable.E)")._check(new O.Group__map_closure0()));
+      return P.List_List$from(t3, true, t3.$ti._eval$1("Iterable.E"));
+    },
+    $isGroupEntry: 1,
+    get$name: function(receiver) {
+      return this.name;
+    },
+    get$metadata: function() {
+      return this.metadata;
+    }
+  };
+  O.Group_forPlatform_closure.prototype = {
+    call$1: function(entry) {
+      return entry.forPlatform$1(this.platform);
+    },
+    $signature: 22
+  };
+  O.Group__map_closure.prototype = {
+    call$1: function(entry) {
+      return this.callback.call$1(type$.GroupEntry._check(entry));
+    },
+    $signature: 22
+  };
+  O.Group__map_closure0.prototype = {
+    call$1: function(entry) {
+      return type$.GroupEntry._check(entry) != null;
+    },
+    $signature: 72
+  };
+  V.GroupEntry.prototype = {};
+  U.LocalTest.prototype = {
+    load$2$groups: function(suite, groups) {
+      var t1, invoker;
+      type$.Iterable_Group._check(groups);
+      t1 = new P._AsyncCompleter(new P._Future($.Zone__current, type$._Future_void), type$._AsyncCompleter_void);
+      invoker = new U.Invoker(this._guarded, new P.Object(), t1, H.setRuntimeTypeInfo([], type$.JSArray_Zone), new P.Object(), H.setRuntimeTypeInfo([], type$.JSArray_of_dynamic_Function), H.setRuntimeTypeInfo([], type$.JSArray_String));
+      t1 = V.LiveTestController$(suite, this, invoker.get$_invoker$_onRun(), t1.get$complete(), groups);
+      invoker._invoker$_controller = t1;
+      return t1._liveTest;
+    },
+    forPlatform$1: function(platform) {
+      var _this = this,
+        t1 = _this.metadata;
+      if (!H.boolConversionCheck(t1.testOn.evaluate$1(platform)))
+        return null;
+      return new U.LocalTest(_this.name, t1.forPlatform$1(platform), _this.trace, _this.isScaffoldAll, _this._body, _this._guarded);
+    },
+    get$name: function(receiver) {
+      return this.name;
+    },
+    get$metadata: function() {
+      return this.metadata;
+    }
+  };
+  U.Invoker.prototype = {
+    get$_outstandingCallbacks: function() {
+      var counter = type$._AsyncCounter._as($.Zone__current.$index(0, this._counterKey));
+      if (counter != null)
+        return counter;
+      throw H.wrapException(P.StateError$("Can't add or remove outstanding callbacks outside of a test body."));
+    },
+    addOutstandingCallback$0: function() {
+      if (H.boolConversionCheck(H._asBoolNullable($.Zone__current.$index(0, this._closableKey))) && this._onCloseCompleter.future._state !== 0)
+        throw H.wrapException(K.ClosedException$());
+      ++this.get$_outstandingCallbacks()._count;
+    },
+    waitForOutstandingCallbacks$1: function(fn) {
+      var t2, counter, t3, _this = this, t1 = {};
+      type$.FutureOr_void_Function._check(fn);
+      _this.heartbeat$0();
+      t1.zone = null;
+      t2 = new P._Future($.Zone__current, type$._Future_void);
+      counter = new U._AsyncCounter(new P._AsyncCompleter(t2, type$._AsyncCompleter_void));
+      t3 = type$.dynamic;
+      P.runZoned(new U.Invoker_waitForOutstandingCallbacks_closure(t1, _this, fn, counter), null, null, P.LinkedHashMap_LinkedHashMap$_literal([_this._counterKey, counter], t3, t3), type$.Future_Null);
+      return t2.whenComplete$1(new U.Invoker_waitForOutstandingCallbacks_closure0(t1, _this));
+    },
+    unclosable$1$1: function(fn, $T) {
+      var t1;
+      $T._eval$1("0()")._check(fn);
+      this.heartbeat$0();
+      t1 = type$.dynamic;
+      return P.runZoned(fn, null, null, P.LinkedHashMap_LinkedHashMap$_literal([this._closableKey, false], t1, t1), $T);
+    },
+    heartbeat$0: function() {
+      var t1, timeout, _this = this;
+      if (_this._invoker$_controller._liveTest._live_test_controller$_controller._live_test_controller$_state.status === C.Status_complete)
+        return;
+      t1 = _this._timeoutTimer;
+      if (t1 != null)
+        t1.cancel$0();
+      timeout = _this._invoker$_controller._liveTest._live_test_controller$_controller._test.metadata.timeout.apply$1(C.Duration_30000000);
+      if (timeout == null)
+        return;
+      _this._timeoutTimer = _this._invokerZone.createTimer$2(timeout, new U.Invoker_heartbeat_closure(_this, new U.Invoker_heartbeat_message(timeout), timeout));
+    },
+    _handleError$3: function(zone, error, stackTrace) {
+      var t2, t3, t4, shouldBeDone, _this = this, t1 = {};
+      t1.stackTrace = stackTrace;
+      if (_this._runCount !== zone.$index(0, C.Symbol_runCount))
+        return;
+      zone.run$1$1(new U.Invoker__handleError_closure(t1), type$.Null);
+      t2 = _this._invoker$_controller;
+      t3 = t2._liveTest._live_test_controller$_controller._live_test_controller$_state;
+      if (t3.status === C.Status_complete) {
+        t4 = t3.result;
+        shouldBeDone = t4 === C.Result_success || t4 === C.Result_skipped;
+      } else
+        shouldBeDone = false;
+      if (!(error instanceof G.TestFailure))
+        t2.setState$1(C.State_Status_complete_Result_error);
+      else if (t3.result !== C.Result_error)
+        t2.setState$1(C.State_Status_complete_Result_failure);
+      _this._invoker$_controller.addError$2(error, t1.stackTrace);
+      zone.run$1$1(new U.Invoker__handleError_closure0(_this), type$.void);
+      t2 = _this._invoker$_controller._liveTest._live_test_controller$_controller;
+      if (t2._test.metadata._chainStackTraces === false)
+        C.JSArray_methods.add$1(_this._printsOnFailure, "Consider enabling the flag chain-stack-traces to receive more detailed exceptions.\nFor example, 'pub run test --chain-stack-traces'.");
+      t2 = _this._printsOnFailure;
+      if (t2.length !== 0) {
+        P.print(C.JSArray_methods.join$1(t2, "\n\n"));
+        C.JSArray_methods.set$length(t2, 0);
+      }
+      if (!shouldBeDone)
+        return;
+      _this._invoker$_controller._liveTest._live_test_controller$_controller._live_test_controller$_suite.toString;
+      _this._handleError$3(zone, "This test failed after it had already completed. Make sure to use [expectAsync]\nor the [completes] matcher when testing async code.", t1.stackTrace);
+    },
+    _handleError$2: function(zone, error) {
+      return this._handleError$3(zone, error, null);
+    },
+    _invoker$_onRun$0: function() {
+      var t1, t2, _this = this;
+      _this._invoker$_controller.setState$1(C.State_Status_running_Result_success);
+      t1 = $.Zone__current;
+      ++_this._runCount;
+      t2 = _this._invoker$_controller._liveTest._live_test_controller$_controller;
+      U.Chain_capture(new U.Invoker__onRun_closure(_this, new U._AsyncCounter(new P._AsyncCompleter(new P._Future(t1, type$._Future_void), type$._AsyncCompleter_void))), false, t2._test.metadata._chainStackTraces !== false, type$.Null);
+    },
+    _runTearDowns$0: function() {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter(type$.void),
+        $async$returnValue, $async$self = this, t1, t2;
+      var $async$_runTearDowns$0 = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1)
+          return P._asyncRethrow($async$result, $async$completer);
+        while (true)
+          switch ($async$goto) {
+            case 0:
+              // Function start
+              t1 = $async$self._invoker$_tearDowns;
+            case 3:
+              // for condition
+              if (!(t2 = t1.length, t2 !== 0)) {
+                // goto after for
+                $async$goto = 4;
+                break;
+              }
+              if (0 >= t2) {
+                $async$returnValue = H.ioore(t1, -1);
+                // goto return
+                $async$goto = 1;
+                break;
+              }
+              $async$goto = 5;
+              return P._asyncAwait(V.errorsDontStopTest(t1.pop()), $async$_runTearDowns$0);
+            case 5:
+              // returning from await.
+              // goto for condition
+              $async$goto = 3;
+              break;
+            case 4:
+              // after for
+            case 1:
+              // return
+              return P._asyncReturn($async$returnValue, $async$completer);
+          }
+      });
+      return P._asyncStartSync($async$_runTearDowns$0, $async$completer);
+    }
+  };
+  U.Invoker_guard_closure.prototype = {
+    call$5: function($self, _, zone, error, stackTrace) {
+      var invoker;
+      type$.StackTrace._check(stackTrace);
+      invoker = zone.$index(0, C.Symbol_cQL);
+      if (invoker != null)
+        $self.get$parent($self).run$1$1(new U.Invoker_guard__closure(invoker, zone, error, stackTrace), type$.dynamic);
+      else
+        $self.get$parent($self).handleUncaughtError$2(error, stackTrace);
+    },
+    $signature: 28
+  };
+  U.Invoker_guard__closure.prototype = {
+    call$0: function() {
+      var _this = this;
+      return _this.invoker._handleError$3(_this.zone, _this.error, _this.stackTrace);
+    },
+    $signature: 34
+  };
+  U.Invoker_waitForOutstandingCallbacks_closure.prototype = {
+    call$0: function() {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter(type$.Null),
+        $async$self = this, zone;
+      var $async$call$0 = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1)
+          return P._asyncRethrow($async$result, $async$completer);
+        while (true)
+          switch ($async$goto) {
+            case 0:
+              // Function start
+              zone = $.Zone__current;
+              $async$self._box_0.zone = zone;
+              C.JSArray_methods.add$1($async$self.$this._outstandingCallbackZones, zone);
+              $async$goto = 2;
+              return P._asyncAwait($async$self.fn.call$0(), $async$call$0);
+            case 2:
+              // returning from await.
+              $async$self.counter.decrement$0();
+              // implicit return
+              return P._asyncReturn(null, $async$completer);
+          }
+      });
+      return P._asyncStartSync($async$call$0, $async$completer);
+    },
+    $signature: 2
+  };
+  U.Invoker_waitForOutstandingCallbacks_closure0.prototype = {
+    call$0: function() {
+      C.JSArray_methods.remove$1(this.$this._outstandingCallbackZones, this._box_0.zone);
+    },
+    $signature: 0
+  };
+  U.Invoker_heartbeat_message.prototype = {
+    call$0: function() {
+      var message,
+        t1 = this.timeout._duration,
+        minutes = C.JSInt_methods._tdivFast$1(t1, 60000000),
+        seconds = C.JSInt_methods.$mod(C.JSInt_methods._tdivFast$1(t1, 1000000), 60),
+        decaseconds = C.JSInt_methods._tdivFast$1(C.JSInt_methods.$mod(C.JSInt_methods._tdivFast$1(t1, 1000), 1000), 100),
+        t2 = minutes !== 0,
+        t3 = t2 ? "" + minutes + " minutes" : "";
+      if (!t2 || seconds !== 0) {
+        t2 = t2 ? t3 + ", " : t3;
+        t2 += seconds;
+        t2 = (decaseconds !== 0 ? t2 + ("." + decaseconds) : t2) + " seconds";
+      } else
+        t2 = t3;
+      message = "Test timed out after " + (t2.charCodeAt(0) == 0 ? t2 : t2) + ".";
+      return t1 === 30000000 ? message + " See https://pub.dev/packages/test#timeouts" : message;
+    },
+    $signature: 74
+  };
+  U.Invoker_heartbeat_closure.prototype = {
+    call$0: function() {
+      var t1 = this.$this;
+      C.JSArray_methods.get$last(t1._outstandingCallbackZones).run$1$1(new U.Invoker_heartbeat__closure(t1, this.message, this.timeout), type$.Null);
+    },
+    $signature: 0
+  };
+  U.Invoker_heartbeat__closure.prototype = {
+    call$0: function() {
+      var t1 = this.$this;
+      if (t1._invoker$_controller._liveTest._live_test_controller$_controller._live_test_controller$_state.status === C.Status_complete)
+        return;
+      t1._handleError$2($.Zone__current, new P.TimeoutException(this.message.call$0(), this.timeout));
+    },
+    $signature: 0
+  };
+  U.Invoker__handleError_closure.prototype = {
+    call$0: function() {
+      var t1 = this._box_0,
+        t2 = t1.stackTrace;
+      if (t2 == null)
+        t1.stackTrace = U.Chain_Chain$current();
+      else
+        t1.stackTrace = U.Chain_Chain$forTrace(t2);
+    },
+    $signature: 0
+  };
+  U.Invoker__handleError_closure0.prototype = {
+    call$0: function() {
+      var t1 = this.$this.get$_outstandingCallbacks()._invoker$_completer;
+      if (t1.future._state === 0)
+        t1.complete$0();
+      return null;
+    },
+    $signature: 1
+  };
+  U.Invoker__onRun_closure.prototype = {
+    call$0: function() {
+      var t1 = this.$this,
+        t2 = type$.void_Function._check(new U.Invoker__onRun__closure(t1, this.outstandingCallbacksForBody));
+      if (t1._guarded)
+        U.Invoker_guard(t2, type$.void);
+      else
+        t2.call$0();
+    },
+    $signature: 0
+  };
+  U.Invoker__onRun__closure.prototype = {
+    call$0: function() {
+      var _null = null,
+        t1 = this.$this,
+        t2 = type$.dynamic;
+      t2 = P.LinkedHashMap_LinkedHashMap$_literal([C.Symbol_cQL, t1, t1._counterKey, this.outstandingCallbacksForBody, t1._closableKey, true, C.Symbol_runCount, t1._runCount], t2, t2);
+      P.runZoned(new U.Invoker__onRun___closure(t1), _null, P._ZoneSpecification$(_null, _null, _null, _null, _null, new U.Invoker__onRun___closure0(t1), _null, _null, _null, _null, _null, _null, _null), t2, type$.Future_Null);
+    },
+    $signature: 0
+  };
+  U.Invoker__onRun___closure.prototype = {
+    call$0: function() {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter(type$.Null),
+        $async$returnValue, $async$self = this, t3, t4, t5, t6, t1, t2;
+      var $async$call$0 = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1)
+          return P._asyncRethrow($async$result, $async$completer);
+        while (true)
+          switch ($async$goto) {
+            case 0:
+              // Function start
+              t1 = $async$self.$this;
+              t2 = $.Zone__current;
+              t1._invokerZone = t2;
+              C.JSArray_methods.add$1(t1._outstandingCallbackZones, t2);
+              P.Future_Future(new U.Invoker__onRun____closure(t1), type$.void);
+              $async$goto = 3;
+              return P._asyncAwait(t1.get$_outstandingCallbacks()._invoker$_completer.future, $async$call$0);
+            case 3:
+              // returning from await.
+              t2 = t1._timeoutTimer;
+              if (t2 != null)
+                t2.cancel$0();
+              t2 = t1._invoker$_controller;
+              t3 = t2._liveTest._live_test_controller$_controller;
+              t4 = t3._live_test_controller$_state.result;
+              if (t4 !== C.Result_success) {
+                t5 = t1._runCount;
+                t6 = t3._test.metadata._retry;
+                t5 = t5 < (t6 == null ? 0 : t6) + 1;
+              } else
+                t5 = false;
+              if (t5) {
+                t2.message$1(0, new D.Message(C.MessageType_print, "Retry: " + H.S(t3._test.name)));
+                t1._invoker$_onRun$0();
+                // goto return
+                $async$goto = 1;
+                break;
+              }
+              t2.setState$1(new G.State(C.Status_complete, t4));
+              t1._invoker$_controller.completer.complete$0();
+            case 1:
+              // return
+              return P._asyncReturn($async$returnValue, $async$completer);
+          }
+      });
+      return P._asyncStartSync($async$call$0, $async$completer);
+    },
+    $signature: 2
+  };
+  U.Invoker__onRun____closure.prototype = {
+    call$0: function() {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter(type$.Null),
+        $async$self = this, t1;
+      var $async$call$0 = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1)
+          return P._asyncRethrow($async$result, $async$completer);
+        while (true)
+          switch ($async$goto) {
+            case 0:
+              // Function start
+              t1 = $async$self.$this;
+              $async$goto = 2;
+              return P._asyncAwait(t1._invoker$_controller._liveTest._live_test_controller$_controller._test._body.call$0(), $async$call$0);
+            case 2:
+              // returning from await.
+              $async$goto = 3;
+              return P._asyncAwait(t1.unclosable$1$1(t1.get$_runTearDowns(), type$.Future_void), $async$call$0);
+            case 3:
+              // returning from await.
+              t1.heartbeat$0();
+              t1.get$_outstandingCallbacks().decrement$0();
+              // implicit return
+              return P._asyncReturn(null, $async$completer);
+          }
+      });
+      return P._asyncStartSync($async$call$0, $async$completer);
+    },
+    $signature: 2
+  };
+  U.Invoker__onRun___closure0.prototype = {
+    call$4: function(_, __, ___, line) {
+      H._checkStringNullable(line);
+      return this.$this._invoker$_controller.message$1(0, new D.Message(C.MessageType_print, line));
+    },
+    $signature: 37
+  };
+  U._AsyncCounter.prototype = {
+    decrement$0: function() {
+      if (--this._count !== 0)
+        return;
+      var t1 = this._invoker$_completer;
+      if (t1.future._state !== 0)
+        return;
+      t1.complete$0();
+    }
+  };
+  Z.LiveTest.prototype = {};
+  V._LiveTest.prototype = {
+    run$0: function() {
+      var t1 = this._live_test_controller$_controller;
+      if (t1._runCalled)
+        H.throwExpression(P.StateError$("LiveTest.run() may not be called more than once."));
+      else if ((t1._onErrorController._state & 4) !== 0)
+        H.throwExpression(P.StateError$("LiveTest.run() may not be called for a closed test."));
+      t1._runCalled = true;
+      t1._onRun.call$0();
+      return t1._liveTest._live_test_controller$_controller.completer.future;
+    }
+  };
+  V.LiveTestController.prototype = {
+    addError$2: function(error, stackTrace) {
+      var asyncError,
+        t1 = this._onErrorController;
+      if ((t1._state & 4) !== 0)
+        return;
+      asyncError = new P.AsyncError(error, U.Chain_Chain$forTrace(stackTrace));
+      C.JSArray_methods.add$1(this._errors, asyncError);
+      t1.add$1(0, asyncError);
+    },
+    setState$1: function(newState) {
+      var _this = this;
+      if ((_this._onErrorController._state & 4) !== 0)
+        return;
+      if (_this._live_test_controller$_state.$eq(0, newState))
+        return;
+      _this._live_test_controller$_state = newState;
+      _this._onStateChangeController.add$1(0, newState);
+    },
+    message$1: function(_, message) {
+      var t1 = this._onMessageController;
+      if (t1._firstSubscription != null)
+        t1.add$1(0, message);
+      else
+        H.printString(message.text);
+    },
+    _live_test_controller$_run$0: function() {
+      var _this = this;
+      if (_this._runCalled)
+        throw H.wrapException(P.StateError$("LiveTest.run() may not be called more than once."));
+      else if ((_this._onErrorController._state & 4) !== 0)
+        throw H.wrapException(P.StateError$("LiveTest.run() may not be called for a closed test."));
+      _this._runCalled = true;
+      _this._onRun.call$0();
+      return _this._liveTest._live_test_controller$_controller.completer.future;
+    },
+    _live_test_controller$_close$0: function() {
+      var _this = this,
+        t1 = _this._onErrorController;
+      if ((t1._state & 4) !== 0)
+        return _this.completer.future;
+      _this._onStateChangeController.close$0(0);
+      t1.close$0(0);
+      if (_this._runCalled)
+        _this._onClose.call$0();
+      else
+        _this.completer.complete$0();
+      return _this.completer.future;
+    }
+  };
+  D.Message.prototype = {};
+  D.MessageType.prototype = {
+    toString$0: function(_) {
+      return this.name;
+    }
+  };
+  O.Metadata.prototype = {
+    _validateTags$0: function() {
+      var t1 = this.tags.where$1(0, new O.Metadata__validateTags_closure()),
+        t2 = t1.$ti,
+        t3 = t2._eval$1("MappedIterable<1,String>"),
+        invalidTags = P.List_List$from(new H.MappedIterable(t1, t2._eval$1("String(1)")._check(new O.Metadata__validateTags_closure0()), t3), true, t3._eval$1("Iterable.E"));
+      t1 = invalidTags.length;
+      if (t1 === 0)
+        return;
+      throw H.wrapException(P.ArgumentError$("Invalid " + B.pluralize("tag", t1) + " " + H.S(B.toSentence(invalidTags)) + ". Tags must be (optionally hyphenated) Dart identifiers."));
+    },
+    validatePlatformSelectors$1: function(validVariables) {
+      type$.Set_String._check(validVariables);
+      this.testOn.validate$1(validVariables);
+      this.onPlatform.forEach$1(0, new O.Metadata_validatePlatformSelectors_closure(validVariables));
+    },
+    merge$1: function(other) {
+      var t4, t5, t6, t7, t8, t9, t10, _this = this,
+        t1 = _this.testOn.intersection$1(other.testOn),
+        t2 = _this.timeout.merge$1(other.timeout),
+        t3 = other._skip;
+      if (t3 == null)
+        t3 = _this._skip;
+      t4 = other.skipReason;
+      if (t4 == null)
+        t4 = _this.skipReason;
+      t5 = other._verboseTrace;
+      if (t5 == null)
+        t5 = _this._verboseTrace;
+      t6 = other._chainStackTraces;
+      if (t6 == null)
+        t6 = _this._chainStackTraces;
+      t7 = other._retry;
+      if (t7 == null)
+        t7 = _this._retry;
+      t8 = _this.tags.union$1(other.tags);
+      t9 = type$.Metadata;
+      t10 = Y.mergeMaps(_this.onPlatform, other.onPlatform, new O.Metadata_merge_closure(), type$.PlatformSelector, t9);
+      return O.Metadata_Metadata(t6, Y.mergeMaps(_this.forTag, other.forTag, new O.Metadata_merge_closure0(), type$.BooleanSelector, t9), t10, t7, t3, t4, t8, t1, t2, t5);
+    },
+    change$4$onPlatform$skip$skipReason$timeout: function(onPlatform, skip, skipReason, timeout) {
+      var _this = this;
+      type$.Map_PlatformSelector_Metadata._check(onPlatform);
+      type$.Set_String._check(null);
+      type$.Map_BooleanSelector_Metadata._check(null);
+      if (timeout == null)
+        timeout = _this.timeout;
+      if (skip == null)
+        skip = _this._skip;
+      if (skipReason == null)
+        skipReason = _this.skipReason;
+      if (onPlatform == null)
+        onPlatform = _this.onPlatform;
+      return O.Metadata_Metadata(_this._chainStackTraces, _this.forTag, onPlatform, _this._retry, skip, skipReason, _this.tags, _this.testOn, timeout, _this._verboseTrace);
+    },
+    change$1$onPlatform: function(onPlatform) {
+      return this.change$4$onPlatform$skip$skipReason$timeout(onPlatform, null, null, null);
+    },
+    change$1$timeout: function(timeout) {
+      return this.change$4$onPlatform$skip$skipReason$timeout(null, null, null, timeout);
+    },
+    change$2$skip$skipReason: function(skip, skipReason) {
+      return this.change$4$onPlatform$skip$skipReason$timeout(null, skip, skipReason, null);
+    },
+    forPlatform$1: function(platform) {
+      var t1 = {},
+        t2 = this.onPlatform;
+      if (t2.get$isEmpty(t2))
+        return this;
+      t1.metadata = this;
+      t2.forEach$1(0, new O.Metadata_forPlatform_closure(t1, platform));
+      return t1.metadata.change$1$onPlatform(P.LinkedHashMap_LinkedHashMap$_empty(type$.PlatformSelector, type$.Metadata));
+    },
+    serialize$0: function() {
+      var t1, t2, t3, _this = this, serializedOnPlatform = [];
+      _this.onPlatform.forEach$1(0, new O.Metadata_serialize_closure(serializedOnPlatform));
+      t1 = _this.testOn._platform_selector$_inner;
+      t2 = J.getInterceptor$(t1);
+      t3 = t2.$eq(t1, C.C_All);
+      t1 = t3 ? null : t2.toString$0(t1);
+      t2 = type$.String;
+      return P.LinkedHashMap_LinkedHashMap$_literal(["testOn", t1, "timeout", _this._serializeTimeout$1(_this.timeout), "skip", _this._skip, "skipReason", _this.skipReason, "verboseTrace", _this._verboseTrace, "chainStackTraces", _this._chainStackTraces, "retry", _this._retry, "tags", _this.tags.toList$0(0), "onPlatform", serializedOnPlatform, "forTag", _this.forTag.map$2$1(0, new O.Metadata_serialize_closure0(), t2, type$.Map_String_dynamic)], t2, type$.dynamic);
+    },
+    _serializeTimeout$1: function(timeout) {
+      var t1;
+      if (timeout.$eq(0, C.Timeout_null_null))
+        return "none";
+      t1 = timeout.duration;
+      t1 = t1 == null ? null : t1._duration;
+      return P.LinkedHashMap_LinkedHashMap$_literal(["duration", t1, "scaleFactor", timeout.scaleFactor], type$.String, type$.num);
+    }
+  };
+  O.Metadata_Metadata__unresolved.prototype = {
+    call$0: function() {
+      var _this = this,
+        t1 = _this._box_0,
+        t2 = t1.tags;
+      return O.Metadata$_(_this.chainStackTraces, t1.forTag, _this.onPlatform, _this.retry, _this.skip, _this.skipReason, t2, _this.testOn, _this.timeout, _this.verboseTrace);
+    },
+    $signature: 77
+  };
+  O.Metadata_Metadata_closure.prototype = {
+    call$2: function(merged, selector) {
+      var t1, t2;
+      type$.Metadata._check(merged);
+      type$.BooleanSelector._check(selector);
+      t1 = this._box_0;
+      t2 = t1.tags;
+      if (!H.boolConversionCheck(selector.evaluate$1(t2.get$contains(t2))))
+        return merged;
+      return merged.merge$1(t1.forTag.remove$1(0, selector));
+    },
+    $signature: 78
+  };
+  O.Metadata$deserialize_closure.prototype = {
+    call$2: function(key, nested) {
+      return new P.MapEntry(new Y.BooleanSelectorImpl(new G.Parser(new O.Scanner(S.SpanScanner$(H._asStringNullable(key)))).parse$0()), O.Metadata$deserialize(nested), type$.MapEntry_BooleanSelector_Metadata);
+    },
+    $signature: 79
+  };
+  O.Metadata__validateTags_closure.prototype = {
+    call$1: function(tag) {
+      return !J.contains$1$asx(H._checkStringNullable(tag), $.$get$anchoredHyphenatedIdentifier());
+    },
+    $signature: 4
+  };
+  O.Metadata__validateTags_closure0.prototype = {
+    call$1: function(tag) {
+      return '"' + H.S(H._checkStringNullable(tag)) + '"';
+    },
+    $signature: 7
+  };
+  O.Metadata_validatePlatformSelectors_closure.prototype = {
+    call$2: function(selector, metadata) {
+      var t1;
+      type$.PlatformSelector._check(selector);
+      type$.Metadata._check(metadata);
+      t1 = this.validVariables;
+      selector.validate$1(t1);
+      metadata.validatePlatformSelectors$1(t1);
+    },
+    $signature: 19
+  };
+  O.Metadata_merge_closure.prototype = {
+    call$2: function(metadata1, metadata2) {
+      var t1 = type$.Metadata;
+      return t1._check(metadata1).merge$1(t1._check(metadata2));
+    },
+    $signature: 44
+  };
+  O.Metadata_merge_closure0.prototype = {
+    call$2: function(metadata1, metadata2) {
+      var t1 = type$.Metadata;
+      return t1._check(metadata1).merge$1(t1._check(metadata2));
+    },
+    $signature: 44
+  };
+  O.Metadata_forPlatform_closure.prototype = {
+    call$2: function(platformSelector, platformMetadata) {
+      var t1;
+      type$.PlatformSelector._check(platformSelector);
+      type$.Metadata._check(platformMetadata);
+      if (!H.boolConversionCheck(platformSelector.evaluate$1(this.platform)))
+        return;
+      t1 = this._box_0;
+      t1.metadata = t1.metadata.merge$1(platformMetadata);
+    },
+    $signature: 19
+  };
+  O.Metadata_serialize_closure.prototype = {
+    call$2: function(key, value) {
+      type$.PlatformSelector._check(key);
+      type$.Metadata._check(value);
+      C.JSArray_methods.add$1(this.serializedOnPlatform, [J.toString$0$(key), value.serialize$0()]);
+    },
+    $signature: 19
+  };
+  O.Metadata_serialize_closure0.prototype = {
+    call$2: function(selector, metadata) {
+      type$.BooleanSelector._check(selector);
+      type$.Metadata._check(metadata);
+      return new P.MapEntry(J.toString$0$(selector), metadata.serialize$0(), type$.MapEntry_of_String_and_Map_String_dynamic);
+    },
+    $signature: 82
+  };
+  N.OperatingSystem.prototype = {
+    toString$0: function(_) {
+      return this.name;
+    }
+  };
+  N.OperatingSystem_find_closure.prototype = {
+    call$1: function(platform) {
+      return type$.OperatingSystem._check(platform).identifier === this.identifier;
+    },
+    $signature: 83
+  };
+  N.OperatingSystem_find_closure0.prototype = {
+    call$0: function() {
+      return null;
+    },
+    $signature: 0
+  };
+  E.PlatformSelector.prototype = {
+    validate$1: function(validVariables) {
+      type$.Set_String._check(validVariables);
+      if (this === C.PlatformSelector_All)
+        return;
+      E.PlatformSelector__wrapFormatException(new E.PlatformSelector_validate_closure(this, validVariables), null, type$.void);
+    },
+    evaluate$1: function(platform) {
+      return this._platform_selector$_inner.evaluate$1(new E.PlatformSelector_evaluate_closure(platform));
+    },
+    intersection$1: function(other) {
+      var t1 = other._platform_selector$_inner,
+        t2 = J.$eq$(t1, C.C_All);
+      if (t2)
+        return this;
+      return new E.PlatformSelector(this._platform_selector$_inner.intersection$1(t1));
+    },
+    toString$0: function(_) {
+      return J.toString$0$(this._platform_selector$_inner);
+    },
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      return other instanceof E.PlatformSelector && J.$eq$(this._platform_selector$_inner, other._platform_selector$_inner);
+    },
+    get$hashCode: function(_) {
+      return J.get$hashCode$(this._platform_selector$_inner);
+    }
+  };
+  E.PlatformSelector$parse_closure.prototype = {
+    call$0: function() {
+      return new Y.BooleanSelectorImpl(new G.Parser(new O.Scanner(S.SpanScanner$(this.selector))).parse$0());
+    },
+    $signature: 84
+  };
+  E.PlatformSelector_validate_closure.prototype = {
+    call$0: function() {
+      return this.$this._platform_selector$_inner.validate$1(new E.PlatformSelector_validate__closure(this.validVariables));
+    },
+    $signature: 1
+  };
+  E.PlatformSelector_validate__closure.prototype = {
+    call$1: function($name) {
+      return $.$get$_universalValidVariables().contains$1(0, $name) || this.validVariables.contains$1(0, $name);
+    },
+    $signature: 4
+  };
+  E.PlatformSelector_evaluate_closure.prototype = {
+    call$1: function(variable) {
+      var t1, t2, t3;
+      H._checkStringNullable(variable);
+      t1 = this.platform;
+      t2 = t1.runtime;
+      if (variable == t2.identifier)
+        return true;
+      t3 = t2.parent;
+      if (variable == (t3 == null ? null : t3.identifier))
+        return true;
+      t3 = t1.os;
+      if (variable === t3.identifier)
+        return true;
+      switch (variable) {
+        case "dart-vm":
+          return t2.isDartVM;
+        case "browser":
+          return t2.isBrowser;
+        case "js":
+          return t2.isJS;
+        case "blink":
+          return t2.isBlink;
+        case "posix":
+          return t3 !== C.OperatingSystem_Windows_windows && t3 !== C.OperatingSystem_none_none;
+        case "google":
+          return t1.inGoogle;
+        default:
+          return false;
+      }
+    },
+    $signature: 4
+  };
+  B.Runtime.prototype = {
+    toString$0: function(_) {
+      return this.name;
+    }
+  };
+  B.Runtime_Runtime$deserialize_closure.prototype = {
+    call$1: function(platform) {
+      return type$.Runtime._check(platform).identifier === this.serialized;
+    },
+    $signature: 85
+  };
+  U.StackTraceFormatter.prototype = {
+    configure$3$except$mapper$only: function(except, mapper, only) {
+      var t1 = type$.Set_String;
+      t1._check(except);
+      t1._check(only);
+      if (mapper != null)
+        this._mapper = mapper;
+      if (except != null)
+        this.set$_except(except);
+      if (only != null)
+        this.set$_only(only);
+    },
+    configure$2$except$only: function(except, only) {
+      return this.configure$3$except$mapper$only(except, null, only);
+    },
+    configure$1$mapper: function(mapper) {
+      return this.configure$3$except$mapper$only(null, mapper, null);
+    },
+    formatStackTrace$2$verbose: function(stackTrace, verbose) {
+      var t2, t3, chain,
+        t1 = this._mapper;
+      if (t1 == null)
+        t1 = null;
+      else {
+        t2 = t1._mapping;
+        if (t2 == null) {
+          t2 = t1._mapContents;
+          t3 = t1._mapUrl;
+          t3 = t1._mapping = T.parseJsonExtended(C.C_JsonCodec.decode$2$reviver(t2, null), t3, null);
+          t2 = t3;
+        }
+        t1 = O.mapStackTrace(t2, stackTrace, false, t1._packageResolver, t1._sdkRoot);
+      }
+      chain = U.Chain_Chain$forTrace(t1 == null ? stackTrace : t1);
+      if (verbose)
+        return chain;
+      return chain.foldFrames$2$terse(new U.StackTraceFormatter_formatStackTrace_closure(this), true);
+    },
+    set$_except: function(_except) {
+      this._except = type$.Set_String._check(_except);
+    },
+    set$_only: function(_only) {
+      this._only = type$.Set_String._check(_only);
+    }
+  };
+  U.StackTraceFormatter_formatStackTrace_closure.prototype = {
+    call$1: function(frame) {
+      var t1 = this.$this,
+        t2 = t1._only;
+      if (t2._collection$_length !== 0)
+        return !t2.contains$1(0, frame.get$$package());
+      return t1._except.contains$1(0, frame.get$$package());
+    },
+    $signature: 21
+  };
+  G.State.prototype = {
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      return other instanceof G.State && this.status === other.status && this.result === other.result;
+    },
+    get$hashCode: function(_) {
+      return (H.Primitives_objectHashCode(this.status) ^ 7 * H.Primitives_objectHashCode(this.result)) >>> 0;
+    },
+    toString$0: function(_) {
+      var t1 = this.status;
+      if (t1 === C.Status_pending)
+        return "pending";
+      if (t1 === C.Status_complete)
+        return this.result.name;
+      t1 = this.result;
+      if (t1 === C.Result_success)
+        return "running";
+      return "running with " + t1.toString$0(0);
+    }
+  };
+  G.Status.prototype = {
+    toString$0: function(_) {
+      return this.name;
+    }
+  };
+  G.Result0.prototype = {
+    toString$0: function(_) {
+      return this.name;
+    }
+  };
+  U.Suite.prototype = {};
+  E.SuitePlatform.prototype = {};
+  V.Test.prototype = {$isGroupEntry: 1};
+  G.TestFailure.prototype = {
+    toString$0: function(_) {
+      return this.message;
+    },
+    get$message: function(receiver) {
+      return this.message;
+    }
+  };
+  G._expect_closure0.prototype = {
+    call$5: function(actual, matcher, reason, matchState, verbose) {
+      var t1 = new P.StringBuffer("");
+      matcher.describeMismatch$4(true, new E.StringDescription(t1), matchState, false);
+      t1 = t1._contents;
+      return G.formatFailure(matcher, true, t1.charCodeAt(0) == 0 ? t1 : t1, reason);
+    },
+    $signature: 86
+  };
+  G._expect_closure.prototype = {
+    call$0: function() {
+    },
+    $signature: 0
+  };
+  R.Timeout.prototype = {
+    merge$1: function(other) {
+      var t1, t2;
+      if (this.$eq(0, C.Timeout_null_null) || other.$eq(0, C.Timeout_null_null))
+        return C.Timeout_null_null;
+      t1 = other.duration;
+      if (t1 != null)
+        return new R.Timeout(t1, null);
+      t1 = this.duration;
+      if (t1 != null) {
+        t2 = other.scaleFactor;
+        t1 = t1._duration;
+        if (typeof t2 !== "number")
+          return H.iae(t2);
+        return new R.Timeout(new P.Duration(C.JSNumber_methods.round$0(t1 * t2)), null);
+      }
+      t1 = this.scaleFactor;
+      t2 = other.scaleFactor;
+      if (typeof t1 !== "number")
+        return t1.$mul();
+      if (typeof t2 !== "number")
+        return H.iae(t2);
+      return new R.Timeout(null, t1 * t2);
+    },
+    apply$1: function(base) {
+      var t1;
+      if (this.$eq(0, C.Timeout_null_null))
+        return null;
+      t1 = this.duration;
+      if (t1 == null) {
+        t1 = this.scaleFactor;
+        if (typeof t1 !== "number")
+          return H.iae(t1);
+        t1 = new P.Duration(C.JSNumber_methods.round$0(base._duration * t1));
+      }
+      return t1;
+    },
+    get$hashCode: function(_) {
+      return (J.get$hashCode$(this.duration) ^ 5 * J.get$hashCode$(this.scaleFactor)) >>> 0;
+    },
+    $eq: function(_, other) {
+      if (other == null)
+        return false;
+      return other instanceof R.Timeout && J.$eq$(other.duration, this.duration) && other.scaleFactor == this.scaleFactor;
+    },
+    toString$0: function(_) {
+      var t1 = this.duration;
+      if (t1 != null)
+        return t1.toString$0(0);
+      t1 = this.scaleFactor;
+      if (t1 != null)
+        return H.S(t1) + "x";
+      return "none";
+    }
+  };
+  S.RemoteListener.prototype = {
+    _serializeGroup$3: function(channel, group, parents) {
+      var t2, t3, t4, t5, t6, t1 = {};
+      t1.parents = parents;
+      type$.Iterable_Group._check(parents);
+      parents = H.setRuntimeTypeInfo(parents.slice(0), H._arrayInstanceType(parents));
+      C.JSArray_methods.add$1(parents, group);
+      t1.parents = parents;
+      t2 = group.metadata.serialize$0();
+      t3 = group.trace;
+      t3 = t3 == null ? null : J.toString$0$(t3.get$_lazy_trace$_trace());
+      t4 = group.entries;
+      t5 = H._arrayInstanceType(t4);
+      t6 = type$.dynamic;
+      return P.LinkedHashMap_LinkedHashMap$_literal(["type", "group", "name", group.name, "metadata", t2, "trace", t3, "setUpAll", this._serializeTest$3(channel, group.setUpAll, parents), "tearDownAll", this._serializeTest$3(channel, group.tearDownAll, parents), "entries", new H.MappedListIterable(t4, t5._eval$1("Map<@,@>(1)")._check(new S.RemoteListener__serializeGroup_closure(t1, this, channel)), t5._eval$1("MappedListIterable<1,Map<@,@>>")).toList$0(0)], t6, t6);
+    },
+    _serializeTest$3: function(channel, test, groups) {
+      var testChannel, t1, t2, t3, t4;
+      type$.Iterable_Group._check(groups);
+      if (test == null)
+        return null;
+      testChannel = channel.virtualChannel$0();
+      testChannel.stream.listen$1(new S.RemoteListener__serializeTest_closure(this, test, groups, channel));
+      t1 = test.name;
+      t2 = test.metadata.serialize$0();
+      t3 = test.trace;
+      t3 = t3 == null ? null : J.toString$0$(t3.get$_lazy_trace$_trace());
+      t4 = type$.dynamic;
+      return P.LinkedHashMap_LinkedHashMap$_literal(["type", "test", "name", t1, "metadata", t2, "trace", t3, "channel", testChannel.id], t4, t4);
+    },
+    _runLiveTest$2: function(liveTest, channel) {
+      var t1, t2;
+      channel.stream.listen$1(new S.RemoteListener__runLiveTest_closure(liveTest));
+      t1 = liveTest._live_test_controller$_controller;
+      t2 = t1._onStateChangeController;
+      new P._BroadcastStream(t2, H._instanceType(t2)._eval$1("_BroadcastStream<1>")).listen$1(new S.RemoteListener__runLiveTest_closure0(channel));
+      t2 = t1._onErrorController;
+      new P._BroadcastStream(t2, H._instanceType(t2)._eval$1("_BroadcastStream<1>")).listen$1(new S.RemoteListener__runLiveTest_closure1(channel, liveTest));
+      t1 = t1._onMessageController;
+      new P._BroadcastStream(t1, H._instanceType(t1)._eval$1("_BroadcastStream<1>")).listen$1(new S.RemoteListener__runLiveTest_closure2(this, channel));
+      t1 = type$.dynamic;
+      P.runZoned(new S.RemoteListener__runLiveTest_closure3(liveTest, channel), null, null, P.LinkedHashMap_LinkedHashMap$_literal([C.Symbol_MAi, channel], t1, t1), type$.Null);
+    }
+  };
+  S.RemoteListener_start_closure.prototype = {
+    call$4: function(_, __, ___, line) {
+      var t1;
+      H._checkStringNullable(line);
+      t1 = this.printZone;
+      if (t1 != null)
+        t1.print$1(0, line);
+      t1 = type$.String;
+      this.channel._mainController._foreign._sink.add$1(0, P.LinkedHashMap_LinkedHashMap$_literal(["type", "print", "line", line], t1, t1));
+    },
+    $signature: 87
+  };
+  S.RemoteListener_start_closure0.prototype = {
+    call$1: function(_) {
+    },
+    $signature: 3
+  };
+  S.RemoteListener_start_closure1.prototype = {
+    call$0: function() {
+      var _this = this,
+        t1 = type$.String,
+        t2 = P.LinkedHashSet_LinkedHashSet$_literal(["test", "stream_channel", "test_api"], t1),
+        t3 = type$.dynamic;
+      P.runZoned(type$.Null_Function._check(new S.RemoteListener_start__closure(_this._box_0, _this.getMain, _this.channel, _this.controller, _this.beforeLoad, _this.printZone, _this.spec)), null, null, P.LinkedHashMap_LinkedHashMap$_literal([$.$get$_currentKey0(), new U.StackTraceFormatter(t2, P.LinkedHashSet_LinkedHashSet$_empty(t1))], t3, t3), type$.Null);
+    },
+    $signature: 0
+  };
+  S.RemoteListener_start__closure.prototype = {
+    call$0: function() {
+      var _this = this,
+        t1 = _this._box_0,
+        t2 = _this.channel;
+      P.runZoned(new S.RemoteListener_start___closure(t1, _this.getMain, t2, _this.controller, _this.beforeLoad, _this.printZone), new S.RemoteListener_start___closure0(t1, t2), _this.spec, null, type$.Future_Null);
+    },
+    $signature: 0
+  };
+  S.RemoteListener_start___closure.prototype = {
+    call$0: function() {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter(type$.Null),
+        $async$returnValue, $async$next = [], $async$self = this, error, stackTrace, exception, t1, t2, queue, message, t3, metadata, declarer, t4, map, t5, t6, main;
+      var $async$call$0 = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1)
+          return P._asyncRethrow($async$result, $async$completer);
+        while (true)
+          switch ($async$goto) {
+            case 0:
+              // Function start
+              main = null;
+              try {
+                main = $async$self.getMain.call$0();
+              } catch (exception) {
+                t1 = H.unwrapException(exception);
+                if (type$.NoSuchMethodError._is(t1)) {
+                  S.RemoteListener__sendLoadException($async$self.channel, "No top-level main() function defined.");
+                  // goto return
+                  $async$goto = 1;
+                  break;
+                } else {
+                  error = t1;
+                  stackTrace = H.getTraceFromException(exception);
+                  S.RemoteListener__sendError($async$self.channel, error, stackTrace, $async$self._box_0.verboseChain);
+                  // goto return
+                  $async$goto = 1;
+                  break;
+                }
+              }
+              if (!type$.Function._is(main)) {
+                S.RemoteListener__sendLoadException($async$self.channel, "Top-level main getter is not a function.");
+                // goto return
+                $async$goto = 1;
+                break;
+              } else if (!type$.dynamic_Function._is(main)) {
+                S.RemoteListener__sendLoadException($async$self.channel, "Top-level main() function takes arguments.");
+                // goto return
+                $async$goto = 1;
+                break;
+              }
+              t1 = $async$self.channel;
+              t2 = t1._mainController._foreign._streamController;
+              t2.toString;
+              queue = new G.StreamQueue(new P._ControllerStream(t2, H._instanceType(t2)._eval$1("_ControllerStream<1>")), Q.QueueList$(type$.Result_dynamic), P.ListQueue$(type$._EventRequest_dynamic), type$.StreamQueue_dynamic);
+              $async$goto = 3;
+              return P._asyncAwait(queue.get$next(), $async$call$0);
+            case 3:
+              // returning from await.
+              message = $async$result;
+              t2 = J.getInterceptor$asx(message);
+              H.assertHelper(J.$eq$(t2.$index(message, "type"), "initial"));
+              if (queue._isClosed)
+                H.throwExpression(queue._failClosed$0());
+              t3 = new Y._CompleterStream(type$._CompleterStream_dynamic);
+              queue._isClosed = true;
+              queue._addRequest$1(new G._RestRequest(new Y.StreamCompleter(t3, type$.StreamCompleter_dynamic), queue, type$._RestRequest_dynamic));
+              t3.listen$1(new S.RemoteListener_start____closure($async$self.controller, t1));
+              t3 = H._asBoolNullable(t2.$index(message, "asciiGlyphs"));
+              if (t3 === true)
+                $._glyphs = C.C_AsciiGlyphSet;
+              metadata = O.Metadata$deserialize(t2.$index(message, "metadata"));
+              $async$self._box_0.verboseChain = metadata._verboseTrace === true;
+              t3 = P.LinkedHashSet_LinkedHashSet$from(type$.Iterable_dynamic._as(t2.$index(message, "platformVariables")), type$.String);
+              declarer = X.Declarer$(H._asBoolNullable(t2.$index(message, "collectTraces")), metadata, H._asBoolNullable(t2.$index(message, "noRetry")), t3);
+              t3 = type$.List_dynamic;
+              type$.StackTraceFormatter._as($.Zone__current.$index(0, $.$get$_currentKey0())).configure$2$except$only(S.RemoteListener__deserializeSet(t3._as(t2.$index(message, "foldTraceExcept"))), S.RemoteListener__deserializeSet(t3._as(t2.$index(message, "foldTraceOnly"))));
+              $async$goto = 4;
+              return P._asyncAwait($async$self.beforeLoad.call$0(), $async$call$0);
+            case 4:
+              // returning from await.
+              t3 = type$.dynamic;
+              $async$goto = 5;
+              return P._asyncAwait(P.runZoned(type$.void_Function._check(main), null, null, P.LinkedHashMap_LinkedHashMap$_literal([C.Symbol_Drw, declarer], t3, t3), type$.void), $async$call$0);
+            case 5:
+              // returning from await.
+              t4 = declarer.build$0();
+              map = type$.Map_dynamic_dynamic._as(t2.$index(message, "platform"));
+              t5 = B.Runtime_Runtime$deserialize(map.$index(0, "runtime"));
+              t6 = N.OperatingSystem_find(H._asStringNullable(map.$index(0, "os")));
+              t6 = E.SuitePlatform$(t5, H._asBoolNullable(map.$index(0, "inGoogle")), t6);
+              P.runZoned(new S.RemoteListener_start____closure0(new U.Suite(t6, H._asStringNullable(t2.$index(message, "path")), U.Suite__filterGroup(t4, t6)), $async$self.printZone, t1), null, null, P.LinkedHashMap_LinkedHashMap$_literal([C.Symbol_Drw, declarer], t3, t3), type$.Null);
+            case 1:
+              // return
+              return P._asyncReturn($async$returnValue, $async$completer);
+          }
+      });
+      return P._asyncStartSync($async$call$0, $async$completer);
+    },
+    $signature: 2
+  };
+  S.RemoteListener_start____closure.prototype = {
+    call$1: function(message) {
+      var t2, t3, t4,
+        t1 = J.getInterceptor$asx(message);
+      if (J.$eq$(t1.$index(message, "type"), "close")) {
+        this.controller._local._sink.close$0(0);
+        return;
+      }
+      H.assertHelper(J.$eq$(t1.$index(message, "type"), "suiteChannel"));
+      t2 = type$.SuiteChannelManager._as($.Zone__current.$index(0, $.$get$_currentKey()));
+      t3 = H._asStringNullable(t1.$index(message, "name"));
+      t1 = this.channel.virtualChannel$1(H._asIntNullable(t1.$index(message, "id")));
+      t4 = t2._outgoingConnections;
+      if (t4.containsKey$1(t3)) {
+        t2 = t4.remove$1(0, t3);
+        t2.toString;
+        H.instanceType(t2)._eval$1("StreamChannel<1>")._check(t1);
+        if (t2._stream_channel_completer$_set)
+          H.throwExpression(P.StateError$("The channel has already been set."));
+        t2._stream_channel_completer$_set = true;
+        t2._streamCompleter.setSourceStream$1(t1.stream);
+        t2 = t2._sinkCompleter;
+        t3 = t2.$ti;
+        t1 = t3._eval$1("StreamSink<1>")._check(t1.sink);
+        t2 = t3._eval$1("_CompleterSink<1>")._check(t2.sink);
+        if (t2._destinationSink != null)
+          H.throwExpression(P.StateError$("Destination sink already set"));
+        t2._setDestinationSink$1(t1);
+      } else {
+        t2 = t2._incomingConnections;
+        if (t2.containsKey$1(t3))
+          H.throwExpression(P.StateError$('Duplicate RunnerSuite.channel() connection "' + H.S(t3) + '".'));
+        else
+          t2.$indexSet(0, t3, t1);
+      }
+    },
+    $signature: 3
+  };
+  S.RemoteListener_start____closure0.prototype = {
+    call$0: function() {
+      U.Invoker_guard(new S.RemoteListener_start_____closure(this.suite, this.printZone, this.channel), type$.void);
+    },
+    $signature: 0
+  };
+  S.RemoteListener_start_____closure.prototype = {
+    call$0: function() {
+      var t1 = this.suite,
+        t2 = this.channel;
+      t2._mainController._foreign._sink.add$1(0, P.LinkedHashMap_LinkedHashMap$_literal(["type", "success", "root", new S.RemoteListener(t1, this.printZone)._serializeGroup$3(t2, t1.group, H.setRuntimeTypeInfo([], type$.JSArray_Group))], type$.String, type$.Object));
+      return null;
+    },
+    $signature: 1
+  };
+  S.RemoteListener_start___closure0.prototype = {
+    call$2: function(error, stackTrace) {
+      S.RemoteListener__sendError(this.channel, error, type$.StackTrace._check(stackTrace), this._box_0.verboseChain);
+    },
+    $signature: 5
+  };
+  S.RemoteListener__serializeGroup_closure.prototype = {
+    call$1: function(entry) {
+      var t1, t2, t3;
+      type$.GroupEntry._check(entry);
+      t1 = this.$this;
+      t2 = this.channel;
+      t3 = this._box_0.parents;
+      return entry instanceof O.Group ? t1._serializeGroup$3(t2, entry, t3) : t1._serializeTest$3(t2, type$.Test._as(entry), t3);
+    },
+    $signature: 88
+  };
+  S.RemoteListener__serializeTest_closure.prototype = {
+    call$1: function(message) {
+      var t2, _this = this,
+        t1 = J.getInterceptor$asx(message);
+      H.assertHelper(J.$eq$(t1.$index(message, "command"), "run"));
+      t2 = _this.$this;
+      t2._runLiveTest$2(_this.test.load$2$groups(t2._suite, _this.groups), _this.channel.virtualChannel$1(H._asIntNullable(t1.$index(message, "channel"))));
+    },
+    $signature: 3
+  };
+  S.RemoteListener__runLiveTest_closure.prototype = {
+    call$1: function(message) {
+      H.assertHelper(J.$eq$(J.$index$asx(message, "command"), "close"));
+      this.liveTest._live_test_controller$_controller._live_test_controller$_close$0();
+    },
+    $signature: 3
+  };
+  S.RemoteListener__runLiveTest_closure0.prototype = {
+    call$1: function(state) {
+      var t1;
+      type$.State._check(state);
+      t1 = type$.String;
+      this.channel.sink.add$1(0, P.LinkedHashMap_LinkedHashMap$_literal(["type", "state-change", "status", state.status.name, "result", state.result.name], t1, t1));
+    },
+    $signature: 23
+  };
+  S.RemoteListener__runLiveTest_closure1.prototype = {
+    call$1: function(asyncError) {
+      var t1, t2, t3, t4;
+      type$.AsyncError._check(asyncError);
+      t1 = asyncError.error;
+      t2 = type$.StackTraceFormatter._as($.Zone__current.$index(0, $.$get$_currentKey0()));
+      t3 = asyncError.stackTrace;
+      t4 = this.liveTest._live_test_controller$_controller;
+      this.channel.sink.add$1(0, P.LinkedHashMap_LinkedHashMap$_literal(["type", "error", "error", U.RemoteException_serialize(t1, t2.formatStackTrace$2$verbose(t3, t4._test.metadata._verboseTrace === true))], type$.String, type$.Object));
+    },
+    $signature: 90
+  };
+  S.RemoteListener__runLiveTest_closure2.prototype = {
+    call$1: function(message) {
+      var t1;
+      type$.Message._check(message);
+      t1 = this.$this._printZone;
+      if (t1 != null)
+        t1.print$1(0, message.text);
+      t1 = type$.String;
+      this.channel.sink.add$1(0, P.LinkedHashMap_LinkedHashMap$_literal(["type", "message", "message-type", message.type.name, "text", message.text], t1, t1));
+    },
+    $signature: 27
+  };
+  S.RemoteListener__runLiveTest_closure3.prototype = {
+    call$0: function() {
+      this.liveTest._live_test_controller$_controller._live_test_controller$_run$0().then$1$1(new S.RemoteListener__runLiveTest__closure(this.channel), type$.void);
+    },
+    $signature: 0
+  };
+  S.RemoteListener__runLiveTest__closure.prototype = {
+    call$1: function(_) {
+      var t1 = type$.String;
+      return this.channel.sink.add$1(0, P.LinkedHashMap_LinkedHashMap$_literal(["type", "complete"], t1, t1));
+    },
+    $signature: 15
+  };
+  N.SuiteChannelManager.prototype = {
+    connectOut$1: function($name) {
+      var t2, completer,
+        t1 = this._incomingConnections;
+      if (t1.containsKey$1($name))
+        return t1.$index(0, $name);
+      else {
+        t1 = this._names;
+        if (t1.contains$1(0, $name))
+          throw H.wrapException(P.StateError$('Duplicate suiteChannel() connection "' + $name + '".'));
+        else {
+          t1.add$1(0, $name);
+          t1 = new Y._CompleterStream(type$._CompleterStream_dynamic);
+          t2 = new T._CompleterSink(type$._CompleterSink_dynamic);
+          completer = new N.StreamChannelCompleter(new Y.StreamCompleter(t1, type$.StreamCompleter_dynamic), new T.StreamSinkCompleter(t2, type$.StreamSinkCompleter_dynamic), type$.StreamChannelCompleter_dynamic);
+          completer.set$_stream_channel_completer$_channel(new R._StreamChannel(t1, t2, type$._StreamChannel_dynamic));
+          this._outgoingConnections.$indexSet(0, $name, completer);
+          return completer._stream_channel_completer$_channel;
+        }
+      }
+    }
+  };
+  O.IterableSet.prototype = {
+    get$length: function(_) {
+      var t1 = this._iterable_set$_base._collection$_source;
+      return t1.get$length(t1);
+    },
+    get$iterator: function(_) {
+      var t1 = this._iterable_set$_base;
+      return new H.ListIterator(t1, t1.get$length(t1), t1.$ti._eval$1("ListIterator<ListMixin.E>"));
+    },
+    toSet$0: function(_) {
+      var t1 = this._iterable_set$_base;
+      return t1.toSet$0(t1);
+    }
+  };
+  O._IterableSet_SetMixin_UnmodifiableSetMixin.prototype = {};
+  E.StackTraceMapper.prototype = {};
+  V.errorsDontStopTest_closure.prototype = {
+    call$0: function() {
+      P.Future_Future$sync(this.body, type$.dynamic).whenComplete$1(this.completer.get$complete());
+    },
+    $signature: 0
+  };
+  V.errorsDontStopTest_closure0.prototype = {
+    call$1: function(_) {
+      var t1 = type$.Invoker._as($.Zone__current.$index(0, C.Symbol_cQL));
+      t1.heartbeat$0();
+      t1.get$_outstandingCallbacks().decrement$0();
+      return null;
+    },
+    $signature: 92
+  };
+  B.closure0.prototype = {
+    call$0: function() {
+      var t1 = $.$get$context().style;
+      if (t1 == $.$get$Style_url())
+        return C.OperatingSystem_none_none;
+      if (t1 == $.$get$Style_windows())
+        return C.OperatingSystem_Windows_windows;
+      if ($._macOSDirectories.any$1(0, J.get$startsWith$s(D.current())))
+        return C.OperatingSystem_RkP;
+      return C.OperatingSystem_Linux_linux;
+    },
+    $signature: 115
+  };
+  O.Engine.prototype = {
+    get$_onUnpaused: function() {
+      var t1 = new P._Future($.Zone__current, type$._Future_dynamic);
+      t1._asyncComplete$1(null);
+      return t1;
+    },
+    get$success: function() {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter(type$.bool),
+        $async$returnValue, $async$self = this;
+      var $async$get$success = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1)
+          return P._asyncRethrow($async$result, $async$completer);
+        while (true)
+          switch ($async$goto) {
+            case 0:
+              // Function start
+              $async$goto = 3;
+              return P._asyncAwait(P.Future_wait(H.setRuntimeTypeInfo([$async$self._group._future_group$_completer.future, $async$self._loadPool._pool$_closeMemo._async_memoizer$_completer.future], type$.JSArray_Future_dynamic), true, type$.dynamic), $async$get$success);
+            case 3:
+              // returning from await.
+              if (H.boolConversionCheck($async$self._closedBeforeDone)) {
+                $async$returnValue = null;
+                // goto return
+                $async$goto = 1;
+                break;
+              }
+              $async$returnValue = $async$self.get$liveTests().every$1(0, new O.Engine_success_closure());
+              // goto return
+              $async$goto = 1;
+              break;
+            case 1:
+              // return
+              return P._asyncReturn($async$returnValue, $async$completer);
+          }
+      });
+      return P._asyncStartSync($async$get$success, $async$completer);
+    },
+    get$liveTests: function() {
+      var _this = this;
+      return new M.UnionSet(P.LinkedHashSet_LinkedHashSet$from(H.setRuntimeTypeInfo([_this._passedGroup._union_set_controller$_set, _this._skippedGroup._union_set_controller$_set, _this._failedGroup._union_set_controller$_set, new O.IterableSet(new P.UnmodifiableListView(_this._active, type$.UnmodifiableListView_LiveTest), type$.IterableSet_LiveTest)], type$.JSArray_Set_LiveTest), type$.Set_LiveTest), true, type$.UnionSet_LiveTest);
+    },
+    Engine$3$concurrency$coverage$maxSuites: function(concurrency, coverage, maxSuites) {
+      this._group._future_group$_completer.future.then$1$1(new O.Engine_closure(this), type$.Null).catchError$1(new O.Engine_closure0());
+    },
+    run$0: function() {
+      var t2, subscription, _this = this, t1 = {};
+      if (_this._engine$_runCalled)
+        throw H.wrapException(P.StateError$("Engine.run() may not be called more than once."));
+      _this._engine$_runCalled = true;
+      t1.subscription = null;
+      t2 = _this._suiteController;
+      subscription = new P._ControllerStream(t2, H._instanceType(t2)._eval$1("_ControllerStream<1>")).listen$2$onDone(new O.Engine_run_closure(_this), new O.Engine_run_closure0(t1, _this));
+      t1.subscription = subscription;
+      _this._engine$_subscriptions.add$1(0, subscription);
+      return _this.get$success();
+    },
+    _runGroup$3: function(suiteController, group, parents) {
+      type$.List_Group._check(parents);
+      return this._runGroup$body$Engine(suiteController, group, parents);
+    },
+    _runGroup$body$Engine: function(suiteController, group, parents) {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter(type$.dynamic),
+        $async$returnValue, $async$handler = 2, $async$currentError, $async$next = [], $async$self = this, suiteConfig, skipGroup, setUpAllSucceeded, liveTest, entries, entry, test, liveTest0, t1, skipGroup0, t2, t3, t4, t5, t6, t7, t8, t9, t10, t11, t12, t13, t14, t15, _i, t16, t17, t18, invoker, t19, t20, result, t21;
+      var $async$_runGroup$3 = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1) {
+          $async$currentError = $async$result;
+          $async$goto = $async$handler;
+        }
+        while (true)
+          switch ($async$goto) {
+            case 0:
+              // Function start
+              C.JSArray_methods.add$1(parents, group);
+              $async$handler = 3;
+              t1 = suiteController._liveSuite._live_suite_controller$_controller._live_suite_controller$_suite;
+              suiteConfig = t1._runner_suite$_controller._config;
+              suiteConfig.toString;
+              skipGroup0 = group.metadata._skip === true;
+              skipGroup = skipGroup0;
+              setUpAllSucceeded = true;
+              $async$goto = !H.boolConversionCheck(skipGroup) && group.setUpAll != null ? 6 : 7;
+              break;
+            case 6:
+              // then
+              liveTest = group.setUpAll.load$2$groups(t1, parents);
+              $async$goto = 8;
+              return P._asyncAwait($async$self._engine$_runLiveTest$3$countSuccess(suiteController, liveTest, false), $async$_runGroup$3);
+            case 8:
+              // returning from await.
+              t1 = liveTest._live_test_controller$_controller._live_test_controller$_state.result;
+              setUpAllSucceeded = t1 === C.Result_success || t1 === C.Result_skipped;
+            case 7:
+              // join
+              $async$goto = !$async$self._engine$_closed && H.boolConversionCheck(setUpAllSucceeded) ? 9 : 10;
+              break;
+            case 9:
+              // then
+              t1 = group.entries;
+              t1 = H.setRuntimeTypeInfo(t1.slice(0), H._arrayInstanceType(t1)._eval$1("JSArray<1>"));
+              entries = t1;
+              suiteConfig.toString;
+              t1 = entries, t2 = t1.length, t3 = type$.Group, t4 = type$.List_Group, t5 = type$._Future_void, t6 = type$._AsyncCompleter_void, t7 = type$._SyncBroadcastStreamController_Message, t8 = type$._SyncBroadcastStreamController_AsyncError, t9 = type$._SyncBroadcastStreamController_State, t10 = type$.Test, t11 = type$.Iterable_Group, t12 = type$.JSArray_Zone, t13 = type$.JSArray_of_dynamic_Function, t14 = type$.JSArray_String, t15 = type$.JSArray_AsyncError, _i = 0;
+            case 11:
+              // for condition
+              if (!(_i < t1.length)) {
+                // goto after for
+                $async$goto = 13;
+                break;
+              }
+              entry = t1[_i];
+              if ($async$self._engine$_closed) {
+                $async$next = [1];
+                // goto finally
+                $async$goto = 4;
+                break;
+              }
+              $async$goto = entry instanceof O.Group ? 14 : 16;
+              break;
+            case 14:
+              // then
+              $async$goto = 17;
+              return P._asyncAwait($async$self._runGroup$3(suiteController, entry, parents), $async$_runGroup$3);
+            case 17:
+              // returning from await.
+              // goto join
+              $async$goto = 15;
+              break;
+            case 16:
+              // else
+              suiteConfig.toString;
+              t16 = entry.get$metadata();
+              t16 = t16._skip === true;
+              $async$goto = t16 ? 18 : 20;
+              break;
+            case 18:
+              // then
+              $async$goto = 21;
+              return P._asyncAwait($async$self._runSkippedTest$3(suiteController, t10._as(entry), parents), $async$_runGroup$3);
+            case 21:
+              // returning from await.
+              // goto join
+              $async$goto = 19;
+              break;
+            case 20:
+              // else
+              test = t10._as(entry);
+              t16 = test;
+              t17 = suiteController._liveSuite._live_suite_controller$_controller;
+              t16.toString;
+              t11._check(parents);
+              t18 = new P._AsyncCompleter(new P._Future($.Zone__current, t5), t6);
+              invoker = new U.Invoker(t16._guarded, new P.Object(), t18, H.setRuntimeTypeInfo([], t12), new P.Object(), H.setRuntimeTypeInfo([], t13), H.setRuntimeTypeInfo([], t14));
+              t19 = H.setRuntimeTypeInfo([], t15);
+              t20 = $.Zone__current;
+              result = P.List_List$from(parents, false, t3);
+              result.fixed$length = Array;
+              result.immutable$list = Array;
+              t21 = t4._check(result);
+              t16 = new V.LiveTestController(t17._live_suite_controller$_suite, t21, t16, invoker.get$_invoker$_onRun(), t18.get$complete(), t19, C.State_Status_pending_Result_success, new P._SyncBroadcastStreamController(null, null, t9), new P._SyncBroadcastStreamController(null, null, t8), new P._SyncBroadcastStreamController(null, null, t7), new P._AsyncCompleter(new P._Future(t20, t5), t6));
+              t17 = new V._LiveTest(t16);
+              t16._liveTest = t17;
+              invoker._invoker$_controller = t16;
+              $async$goto = 22;
+              return P._asyncAwait($async$self._engine$_runLiveTest$2(suiteController, t17), $async$_runGroup$3);
+            case 22:
+              // returning from await.
+            case 19:
+              // join
+            case 15:
+              // join
+            case 12:
+              // for update
+              t1.length === t2 || (0, H.throwConcurrentModificationError)(t1), ++_i;
+              // goto for condition
+              $async$goto = 11;
+              break;
+            case 13:
+              // after for
+            case 10:
+              // join
+              $async$goto = !H.boolConversionCheck(skipGroup) && group.tearDownAll != null ? 23 : 24;
+              break;
+            case 23:
+              // then
+              liveTest0 = group.tearDownAll.load$2$groups(suiteController._liveSuite._live_suite_controller$_controller._live_suite_controller$_suite, parents);
+              $async$goto = 25;
+              return P._asyncAwait($async$self._engine$_runLiveTest$3$countSuccess(suiteController, liveTest0, false), $async$_runGroup$3);
+            case 25:
+              // returning from await.
+              $async$goto = $async$self._engine$_closed ? 26 : 27;
+              break;
+            case 26:
+              // then
+              $async$goto = 28;
+              return P._asyncAwait(liveTest0._live_test_controller$_controller._live_test_controller$_close$0(), $async$_runGroup$3);
+            case 28:
+              // returning from await.
+            case 27:
+              // join
+            case 24:
+              // join
+              $async$next.push(5);
+              // goto finally
+              $async$goto = 4;
+              break;
+            case 3:
+              // uncaught
+              $async$next = [2];
+            case 4:
+              // finally
+              $async$handler = 2;
+              C.JSArray_methods.remove$1(parents, group);
+              // goto the next finally handler
+              $async$goto = $async$next.pop();
+              break;
+            case 5:
+              // after finally
+            case 1:
+              // return
+              return P._asyncReturn($async$returnValue, $async$completer);
+            case 2:
+              // rethrow
+              return P._asyncRethrow($async$currentError, $async$completer);
+          }
+      });
+      return P._asyncStartSync($async$_runGroup$3, $async$completer);
+    },
+    _engine$_runLiveTest$3$countSuccess: function(suiteController, liveTest, countSuccess) {
+      return this._runLiveTest$body$Engine(suiteController, liveTest, countSuccess);
+    },
+    _engine$_runLiveTest$2: function(suiteController, liveTest) {
+      return this._engine$_runLiveTest$3$countSuccess(suiteController, liveTest, true);
+    },
+    _runLiveTest$body$Engine: function(suiteController, liveTest, countSuccess) {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter(type$.dynamic),
+        $async$returnValue, $async$self = this, t2, t3, subscription, t1;
+      var $async$_engine$_runLiveTest$3$countSuccess = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1)
+          return P._asyncRethrow($async$result, $async$completer);
+        while (true)
+          switch ($async$goto) {
+            case 0:
+              // Function start
+              t1 = {};
+              $async$goto = 3;
+              return P._asyncAwait($async$self.get$_onUnpaused(), $async$_engine$_runLiveTest$3$countSuccess);
+            case 3:
+              // returning from await.
+              t2 = $async$self._active;
+              t2._queue_list$_add$1(t2.$ti._precomputed1._check(liveTest));
+              t2.get$first(t2).toString;
+              t1.subscription = null;
+              t2 = liveTest._live_test_controller$_controller;
+              t3 = t2._onStateChangeController;
+              subscription = new P._BroadcastStream(t3, H._instanceType(t3)._eval$1("_BroadcastStream<1>")).listen$2$onDone(new O.Engine__runLiveTest_closure($async$self, liveTest), new O.Engine__runLiveTest_closure0(t1, $async$self));
+              t1.subscription = subscription;
+              $async$self._engine$_subscriptions.add$1(0, subscription);
+              suiteController.reportLiveTest$2$countSuccess(liveTest, countSuccess);
+              $async$goto = 4;
+              return P._asyncAwait(P.Future_Future$microtask(liveTest.get$run(), type$.dynamic), $async$_engine$_runLiveTest$3$countSuccess);
+            case 4:
+              // returning from await.
+              $async$goto = 5;
+              return P._asyncAwait(P.Future_Future(new O.Engine__runLiveTest_closure1(), type$.Null), $async$_engine$_runLiveTest$3$countSuccess);
+            case 5:
+              // returning from await.
+              t1 = $async$self._restarted;
+              if (!t1.contains$1(0, liveTest)) {
+                // goto return
+                $async$goto = 1;
+                break;
+              }
+              $async$goto = 6;
+              return P._asyncAwait($async$self._engine$_runLiveTest$3$countSuccess(suiteController, t2._test.load$2$groups(t2._live_test_controller$_suite, t2._groups), countSuccess), $async$_engine$_runLiveTest$3$countSuccess);
+            case 6:
+              // returning from await.
+              t1.remove$1(0, liveTest);
+            case 1:
+              // return
+              return P._asyncReturn($async$returnValue, $async$completer);
+          }
+      });
+      return P._asyncStartSync($async$_engine$_runLiveTest$3$countSuccess, $async$completer);
+    },
+    _runSkippedTest$3: function(suiteController, test, parents) {
+      return this._runSkippedTest$body$Engine(suiteController, test, type$.List_Group._check(parents));
+    },
+    _runSkippedTest$body$Engine: function(suiteController, test, parents) {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter(type$.dynamic),
+        $async$returnValue, $async$self = this, skipped, controller, t1;
+      var $async$_runSkippedTest$3 = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1)
+          return P._asyncRethrow($async$result, $async$completer);
+        while (true)
+          switch ($async$goto) {
+            case 0:
+              // Function start
+              t1 = {};
+              $async$goto = 3;
+              return P._asyncAwait($async$self.get$_onUnpaused(), $async$_runSkippedTest$3);
+            case 3:
+              // returning from await.
+              skipped = new U.LocalTest(test.name, test.metadata, test.trace, false, new O.Engine__runSkippedTest_closure(), true);
+              t1.controller = null;
+              controller = V.LiveTestController$(suiteController._liveSuite._live_suite_controller$_controller._live_suite_controller$_suite, skipped, new O.Engine__runSkippedTest_closure0(t1, skipped), new O.Engine__runSkippedTest_closure1(), parents);
+              t1.controller = controller;
+              $async$goto = 4;
+              return P._asyncAwait($async$self._engine$_runLiveTest$2(suiteController, controller._liveTest), $async$_runSkippedTest$3);
+            case 4:
+              // returning from await.
+              $async$returnValue = $async$result;
+              // goto return
+              $async$goto = 1;
+              break;
+            case 1:
+              // return
+              return P._asyncReturn($async$returnValue, $async$completer);
+          }
+      });
+      return P._asyncStartSync($async$_runSkippedTest$3, $async$completer);
+    },
+    _addLiveSuite$1: function(liveSuite) {
+      var t1, t2, t3, _this = this;
+      _this._liveSuites.add$1(0, liveSuite);
+      _this._onSuiteStartedController.add$1(0, liveSuite);
+      t1 = liveSuite._live_suite_controller$_controller;
+      t2 = t1._onTestStartedController;
+      _this._onTestStartedGroup.add$1(0, new P._BroadcastStream(t2, H._instanceType(t2)._eval$1("_BroadcastStream<1>")));
+      t2 = _this._passedGroup;
+      t3 = type$.UnmodifiableSetView_LiveTest;
+      t2._union_set_controller$_sets.add$1(0, t2.$ti._eval$1("Set<1>")._check(new L.UnmodifiableSetView(t1._passed, t3)));
+      t2 = _this._skippedGroup;
+      t2._union_set_controller$_sets.add$1(0, t2.$ti._eval$1("Set<1>")._check(new L.UnmodifiableSetView(t1._skipped, t3)));
+      t2 = _this._failedGroup;
+      t2._union_set_controller$_sets.add$1(0, t2.$ti._eval$1("Set<1>")._check(new L.UnmodifiableSetView(t1._failed, t3)));
+    }
+  };
+  O.Engine_success_closure.prototype = {
+    call$1: function(liveTest) {
+      var t1 = type$.LiveTest._check(liveTest)._live_test_controller$_controller._live_test_controller$_state,
+        t2 = t1.result;
+      return (t2 === C.Result_success || t2 === C.Result_skipped) && t1.status === C.Status_complete;
+    },
+    $signature: 95
+  };
+  O.Engine_closure.prototype = {
+    call$1: function(_) {
+      var t1;
+      type$.List_dynamic._check(_);
+      t1 = this.$this;
+      t1._onTestStartedGroup.close$0(0);
+      t1._onSuiteStartedController.close$0(0);
+      if (t1._closedBeforeDone == null)
+        t1._closedBeforeDone = false;
+    },
+    $signature: 48
+  };
+  O.Engine_closure0.prototype = {
+    call$1: function(_) {
+    },
+    $signature: 3
+  };
+  O.Engine_run_closure.prototype = {
+    call$1: function(suite) {
+      var t1;
+      type$.RunnerSuite._check(suite);
+      t1 = this.$this;
+      t1._addedSuites.add$1(0, suite);
+      t1._onSuiteAddedController.add$1(0, suite);
+      t1._group.add$1(0, new O.Engine_run__closure(t1, suite).call$0());
+    },
+    $signature: 97
+  };
+  O.Engine_run__closure.prototype = {
+    call$0: function() {
+      return this.$call$body$Engine_run__closure();
+    },
+    $call$body$Engine_run__closure: function() {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter(type$.Null),
+        $async$self = this, controller, t1, t2, loadResource;
+      var $async$call$0 = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1)
+          return P._asyncRethrow($async$result, $async$completer);
+        while (true)
+          switch ($async$goto) {
+            case 0:
+              // Function start
+              t1 = {};
+              t2 = $async$self.$this;
+              $async$goto = 2;
+              return P._asyncAwait(t2._loadPool.request$0(0), $async$call$0);
+            case 2:
+              // returning from await.
+              loadResource = $async$result;
+              t1.controller = null;
+              controller = B.LiveSuiteController$($async$self.suite);
+              t1.controller = controller;
+              t2._addLiveSuite$1(controller._liveSuite);
+              $async$goto = 3;
+              return P._asyncAwait(t2._runPool.withResource$1$1(new O.Engine_run___closure(t1, t2, loadResource), type$.Null), $async$call$0);
+            case 3:
+              // returning from await.
+              // implicit return
+              return P._asyncReturn(null, $async$completer);
+          }
+      });
+      return P._asyncStartSync($async$call$0, $async$completer);
+    },
+    $signature: 2
+  };
+  O.Engine_run___closure.prototype = {
+    call$0: function() {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter(type$.Null),
+        $async$returnValue, $async$self = this, t2, t3, t1;
+      var $async$call$0 = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1)
+          return P._asyncRethrow($async$result, $async$completer);
+        while (true)
+          switch ($async$goto) {
+            case 0:
+              // Function start
+              t1 = $async$self.$this;
+              if (t1._engine$_closed) {
+                // goto return
+                $async$goto = 1;
+                break;
+              }
+              t2 = $async$self._box_0;
+              t3 = t2.controller;
+              $async$goto = 3;
+              return P._asyncAwait(t1._runGroup$3(t3, t3._liveSuite._live_suite_controller$_controller._live_suite_controller$_suite.group, H.setRuntimeTypeInfo([], type$.JSArray_Group)), $async$call$0);
+            case 3:
+              // returning from await.
+              t3 = t2.controller;
+              t3._onTestStartedController.close$0(0);
+              t3._onCompleteGroup.close$0(0);
+              t1 = $async$self.loadResource;
+              t1.toString;
+              t2 = type$.dynamic_Function._check(new O.Engine_run____closure(t2));
+              if (t1._released)
+                H.throwExpression(P.StateError$("A PoolResource may only be released once."));
+              t1._released = true;
+              t1._pool._onResourceReleaseAllowed$1(t2);
+            case 1:
+              // return
+              return P._asyncReturn($async$returnValue, $async$completer);
+          }
+      });
+      return P._asyncStartSync($async$call$0, $async$completer);
+    },
+    $signature: 2
+  };
+  O.Engine_run____closure.prototype = {
+    call$0: function() {
+      return this._box_0.controller.close$0(0);
+    },
+    $signature: 14
+  };
+  O.Engine_run_closure0.prototype = {
+    call$0: function() {
+      var t1 = this.$this;
+      t1._engine$_subscriptions.remove$1(0, this._box_1.subscription);
+      t1._onSuiteAddedController.close$0(0);
+      t1._group.close$0(0);
+      t1._loadPool.close$0(0);
+    },
+    $signature: 0
+  };
+  O.Engine__runLiveTest_closure.prototype = {
+    call$1: function(state) {
+      var t1, t2;
+      if (type$.State._check(state).status !== C.Status_complete)
+        return;
+      t1 = this.$this;
+      t2 = t1._active;
+      t2.remove$1(t2, this.liveTest);
+      if (t2.get$length(t2) === 0 && t1._activeLoadTests._collection$_length !== 0) {
+        t1 = t1._activeLoadTests;
+        t2._queue_list$_add$1(t2.$ti._precomputed1._check(t1.get$first(t1)));
+      }
+    },
+    $signature: 23
+  };
+  O.Engine__runLiveTest_closure0.prototype = {
+    call$0: function() {
+      this.$this._engine$_subscriptions.remove$1(0, this._box_0.subscription);
+    },
+    $signature: 0
+  };
+  O.Engine__runLiveTest_closure1.prototype = {
+    call$0: function() {
+    },
+    $signature: 0
+  };
+  O.Engine__runSkippedTest_closure.prototype = {
+    call$0: function() {
+    },
+    $signature: 0
+  };
+  O.Engine__runSkippedTest_closure0.prototype = {
+    call$0: function() {
+      var t2,
+        t1 = this._box_0;
+      t1.controller.setState$1(C.State_Status_running_Result_success);
+      t1.controller.setState$1(C.State_Status_running_Result_skipped);
+      t2 = this.skipped.metadata.skipReason;
+      if (t2 != null)
+        t1.controller.message$1(0, new D.Message(C.MessageType_skip, "Skip: " + t2));
+      t1.controller.setState$1(C.State_Status_complete_Result_skipped);
+      t1.controller.completer.complete$0();
+    },
+    $signature: 0
+  };
+  O.Engine__runSkippedTest_closure1.prototype = {
+    call$0: function() {
+    },
+    $signature: 0
+  };
+  E.LiveSuite.prototype = {};
+  B._LiveSuite.prototype = {};
+  B.LiveSuiteController.prototype = {
+    LiveSuiteController$1: function(_suite) {
+      var _this = this;
+      _this._liveSuite = new B._LiveSuite(_this);
+      _this._onCompleteGroup._future_group$_completer.future.then$1$2$onError(new B.LiveSuiteController_closure(_this), new B.LiveSuiteController_closure0(), type$.Null);
+    },
+    reportLiveTest$2$countSuccess: function(liveTest, countSuccess) {
+      var t2, t3, _this = this,
+        t1 = _this._onTestStartedController;
+      if ((t1._state & 4) !== 0)
+        throw H.wrapException(P.StateError$("Can't call reportLiveTest() after noMoreTests()."));
+      t2 = liveTest._live_test_controller$_controller;
+      H.assertHelper(t2._live_test_controller$_suite == _this._live_suite_controller$_suite);
+      H.assertHelper(_this._live_suite_controller$_active == null);
+      _this._live_suite_controller$_active = liveTest;
+      t3 = t2._onStateChangeController;
+      new P._BroadcastStream(t3, H._instanceType(t3)._eval$1("_BroadcastStream<1>")).listen$1(new B.LiveSuiteController_reportLiveTest_closure(_this, liveTest, countSuccess));
+      t1.add$1(0, liveTest);
+      _this._onCompleteGroup.add$1(0, t2.completer.future);
+    },
+    close$0: function(_) {
+      return this._live_suite_controller$_closeMemo.runOnce$1(new B.LiveSuiteController_close_closure(this));
+    }
+  };
+  B.LiveSuiteController_closure.prototype = {
+    call$1: function(_) {
+      type$.List_dynamic._check(_);
+    },
+    $signature: 48
+  };
+  B.LiveSuiteController_closure0.prototype = {
+    call$1: function(_) {
+    },
+    $signature: 3
+  };
+  B.LiveSuiteController_reportLiveTest_closure.prototype = {
+    call$1: function(state) {
+      var t1, t2, _this = this;
+      type$.State._check(state);
+      if (state.status !== C.Status_complete)
+        return;
+      t1 = _this.$this;
+      t1._live_suite_controller$_active = null;
+      t2 = state.result;
+      if (t2 === C.Result_skipped)
+        t1._skipped.add$1(0, _this.liveTest);
+      else if (t2 !== C.Result_success) {
+        t2 = _this.liveTest;
+        t1._passed.remove$1(0, t2);
+        t1._failed.add$1(0, t2);
+      } else if (_this.countSuccess) {
+        t2 = _this.liveTest;
+        t1._passed.add$1(0, t2);
+        t1._failed.remove$1(0, t2);
+      }
+    },
+    $signature: 23
+  };
+  B.LiveSuiteController_close_closure.prototype = {
+    call$0: function() {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter(type$.Null),
+        $async$handler = 1, $async$currentError, $async$next = [], $async$self = this;
+      var $async$call$0 = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1) {
+          $async$currentError = $async$result;
+          $async$goto = $async$handler;
+        }
+        while (true)
+          switch ($async$goto) {
+            case 0:
+              // Function start
+              $async$handler = 2;
+              $async$goto = 5;
+              return P._asyncAwait($async$self.$this._live_suite_controller$_suite._runner_suite$_controller._runner_suite$_close$0(), $async$call$0);
+            case 5:
+              // returning from await.
+              $async$next.push(4);
+              // goto finally
+              $async$goto = 3;
+              break;
+            case 2:
+              // uncaught
+              $async$next = [1];
+            case 3:
+              // finally
+              $async$handler = 1;
+              $async$self.$this._live_suite_controller$_onCloseCompleter.complete$0();
+              // goto the next finally handler
+              $async$goto = $async$next.pop();
+              break;
+            case 4:
+              // after finally
+              // implicit return
+              return P._asyncReturn(null, $async$completer);
+            case 1:
+              // rethrow
+              return P._asyncRethrow($async$currentError, $async$completer);
+          }
+      });
+      return P._asyncStartSync($async$call$0, $async$completer);
+    },
+    $signature: 2
+  };
+  R.ExpandedReporter.prototype = {
+    _onTestStarted$1: function(liveTest) {
+      var t1, t2, t3, t4, _this = this;
+      type$.LiveTest._check(liveTest);
+      liveTest.toString;
+      t1 = _this._stopwatch;
+      t2 = t1._stop != null;
+      if (t2)
+        if (t2) {
+          t2 = t1._core$_start;
+          t3 = H._checkIntNullable($.Primitives_timerTicks.call$0());
+          t4 = t1._stop;
+          if (typeof t3 !== "number")
+            return t3.$sub();
+          if (typeof t4 !== "number")
+            return H.iae(t4);
+          t1._core$_start = t2 + (t3 - t4);
+          t1._stop = null;
+        }
+      t1 = _this._engine._active;
+      if (t1.get$length(t1) === 1)
+        _this._progressLine$1(_this._description$1(liveTest));
+      t1 = liveTest._live_test_controller$_controller._onStateChangeController;
+      _this._subscriptions.add$1(0, new P._BroadcastStream(t1, H._instanceType(t1)._eval$1("_BroadcastStream<1>")).listen$1(new R.ExpandedReporter__onTestStarted_closure(_this, liveTest)));
+      t1 = _this._subscriptions;
+      t2 = liveTest._live_test_controller$_controller;
+      t3 = t2._onErrorController;
+      t1.add$1(0, new P._BroadcastStream(t3, H._instanceType(t3)._eval$1("_BroadcastStream<1>")).listen$1(new R.ExpandedReporter__onTestStarted_closure0(_this, liveTest)));
+      t2 = t2._onMessageController;
+      t1.add$1(0, new P._BroadcastStream(t2, H._instanceType(t2)._eval$1("_BroadcastStream<1>")).listen$1(new R.ExpandedReporter__onTestStarted_closure1(_this, liveTest)));
+    },
+    _onStateChange$2: function(liveTest, state) {
+      var t1, t2, t3;
+      if (state.status !== C.Status_complete)
+        return;
+      t1 = this._engine._active;
+      t2 = type$.UnmodifiableListView_LiveTest;
+      t3 = new P.UnmodifiableListView(t1, t2);
+      if (t3.get$length(t3) !== 0) {
+        t1 = new P.UnmodifiableListView(t1, t2);
+        this._progressLine$1(this._description$1(t1.get$first(t1)));
+      }
+    },
+    _expanded$_onError$3: function(liveTest, error, stackTrace) {
+      var t1, _this = this;
+      if (liveTest._live_test_controller$_controller._live_test_controller$_state.status !== C.Status_complete)
+        return;
+      _this._progressLine$2$suffix(_this._description$1(liveTest), " " + _this._bold + _this._red + "[E]" + _this._noColor);
+      t1 = _this._expanded$_sink;
+      t1.writeln$1(B.indent(H.S(error), null));
+      t1.writeln$1(B.indent(H.S(stackTrace), null));
+      return;
+    },
+    _expanded$_onDone$1: function(success) {
+      var t1, t2, t3, t4, _this = this;
+      H._checkBoolNullable(success);
+      if (success == null)
+        return;
+      t1 = _this._engine;
+      t2 = t1.get$liveTests();
+      if (t2.get$length(t2) === 0)
+        _this._expanded$_sink.writeln$1("No tests ran.");
+      else if (!success) {
+        for (t2 = type$.UnmodifiableListView_LiveTest, t1 = new P.UnmodifiableListView(t1._active, t2), t2 = new H.ListIterator(t1, t1.get$length(t1), t2._eval$1("ListIterator<ListMixin.E>")), t1 = _this._bold, t3 = _this._red, t4 = _this._noColor; t2.moveNext$0();)
+          _this._progressLine$2$suffix(_this._description$1(t2.__internal$_current), " - did not complete " + t1 + t3 + "[E]" + t4);
+        _this._progressLine$2$color("Some tests failed.", t3);
+      } else {
+        t1 = t1._passedGroup._union_set_controller$_set;
+        if (t1.get$length(t1) === 0)
+          _this._progressLine$1("All tests skipped.");
+        else
+          _this._progressLine$1("All tests passed!");
+      }
+    },
+    _progressLine$3$color$suffix: function(message, color, suffix) {
+      var t4, t5, _this = this,
+        t1 = _this._engine,
+        t2 = t1._passedGroup,
+        t3 = t2._union_set_controller$_set;
+      if (t3.get$length(t3) == _this._lastProgressPassed) {
+        t3 = t1._skippedGroup._union_set_controller$_set;
+        if (t3.get$length(t3) == _this._lastProgressSkipped) {
+          t3 = t1._failedGroup._union_set_controller$_set;
+          if (t3.get$length(t3) == _this._lastProgressFailed)
+            if (message == _this._lastProgressMessage)
+              t3 = suffix == null || suffix === _this._lastProgressSuffix;
+            else
+              t3 = false;
+          else
+            t3 = false;
+        } else
+          t3 = false;
+      } else
+        t3 = false;
+      if (t3)
+        return;
+      t3 = t2._union_set_controller$_set;
+      _this._lastProgressPassed = t3.get$length(t3);
+      t3 = t1._skippedGroup;
+      t4 = t3._union_set_controller$_set;
+      _this._lastProgressSkipped = t4.get$length(t4);
+      t1 = t1._failedGroup;
+      t4 = t1._union_set_controller$_set;
+      _this._lastProgressFailed = t4.get$length(t4);
+      _this._lastProgressMessage = message;
+      _this._lastProgressSuffix = suffix;
+      if (suffix != null)
+        message = J.$add$ansx(message, suffix);
+      if (color == null)
+        color = "";
+      t4 = P.Duration$(_this._stopwatch.get$elapsedMicroseconds(), 0)._duration;
+      t4 = C.JSString_methods.padLeft$2(C.JSInt_methods.toString$0(C.JSInt_methods._tdivFast$1(t4, 60000000)), 2, "0") + ":" + C.JSString_methods.padLeft$2(C.JSInt_methods.toString$0(C.JSInt_methods.$mod(C.JSInt_methods._tdivFast$1(t4, 1000000), 60)), 2, "0") + " " + _this._green + "+";
+      t2 = t2._union_set_controller$_set;
+      t5 = _this._noColor;
+      t2 = t4 + H.S(t2.get$length(t2)) + t5;
+      t4 = t3._union_set_controller$_set;
+      if (t4.get$length(t4) !== 0) {
+        t2 = t2 + _this._yellow + " ~";
+        t3 = t3._union_set_controller$_set;
+        t3 = t2 + H.S(t3.get$length(t3)) + t5;
+        t2 = t3;
+      }
+      t3 = t1._union_set_controller$_set;
+      if (t3.get$length(t3) !== 0) {
+        t2 = t2 + _this._red + " -";
+        t1 = t1._union_set_controller$_set;
+        t1 = t2 + H.S(t1.get$length(t1)) + t5;
+      } else
+        t1 = t2;
+      t5 = t1 + ": " + color + H.S(message) + t5;
+      _this._expanded$_sink.writeln$1(t5.charCodeAt(0) == 0 ? t5 : t5);
+    },
+    _progressLine$2$suffix: function(message, suffix) {
+      return this._progressLine$3$color$suffix(message, null, suffix);
+    },
+    _progressLine$2$color: function(message, color) {
+      return this._progressLine$3$color$suffix(message, color, null);
+    },
+    _progressLine$1: function(message) {
+      return this._progressLine$3$color$suffix(message, null, null);
+    },
+    _description$1: function(liveTest) {
+      var t1 = liveTest._live_test_controller$_controller;
+      return t1._test.name;
+    }
+  };
+  R.ExpandedReporter__onTestStarted_closure.prototype = {
+    call$1: function(state) {
+      return this.$this._onStateChange$2(this.liveTest, type$.State._check(state));
+    },
+    $signature: 100
+  };
+  R.ExpandedReporter__onTestStarted_closure0.prototype = {
+    call$1: function(error) {
+      type$.AsyncError._check(error);
+      return this.$this._expanded$_onError$3(this.liveTest, error.error, error.stackTrace);
+    },
+    $signature: 101
+  };
+  R.ExpandedReporter__onTestStarted_closure1.prototype = {
+    call$1: function(message) {
+      var t1, text;
+      type$.Message._check(message);
+      t1 = this.$this;
+      t1._progressLine$1(t1._description$1(this.liveTest));
+      text = message.text;
+      if (message.type === C.MessageType_skip)
+        text = "  " + t1._yellow + text + t1._noColor;
+      t1._expanded$_sink.writeln$1(text);
+    },
+    $signature: 27
+  };
+  Y.RunnerSuite.prototype = {};
+  Y.RunnerSuiteController.prototype = {
+    _runner_suite$_close$0: function() {
+      return this._closeMemo.runOnce$1(new Y.RunnerSuiteController__close_closure(this));
+    },
+    set$_runner_suite$_suite: function(_suite) {
+      type$.Future_RunnerSuite._check(_suite);
+    }
+  };
+  Y.RunnerSuiteController__close_closure.prototype = {
+    call$0: function() {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter(type$.Null),
+        $async$self = this;
+      var $async$call$0 = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1)
+          return P._asyncRethrow($async$result, $async$completer);
+        while (true)
+          switch ($async$goto) {
+            case 0:
+              // Function start
+              $async$goto = 2;
+              return P._asyncAwait($async$self.$this._onDebuggingController.close$0(0), $async$call$0);
+            case 2:
+              // returning from await.
+              // implicit return
+              return P._asyncReturn(null, $async$completer);
+          }
+      });
+      return P._asyncStartSync($async$call$0, $async$completer);
+    },
+    $signature: 2
+  };
+  T.RuntimeSelection.prototype = {};
+  U.SuiteConfiguration.prototype = {};
+  X.PrintSink.prototype = {
+    writeln$1: function(obj) {
+      this._print_sink$_buffer._contents += obj + "\n";
+      this._flush$0();
+    },
+    _flush$0: function() {
+      var t1 = this._print_sink$_buffer;
+      if (C.JSString_methods.endsWith$1(t1.toString$0(0), "\n")) {
+        P.print(t1);
+        t1._contents = "";
+      }
+    },
+    $isStringSink: 1
+  };
+  E.JSStackTraceMapper.prototype = {};
+  E.JSStackTraceMapper__deserializePackageConfigMap_closure.prototype = {
+    call$2: function(key, value) {
+      return new P.MapEntry(H._checkStringNullable(key), P.Uri_parse(H._checkStringNullable(value)), type$.MapEntry_String_Uri);
+    },
+    $signature: 102
+  };
+  R._declarer_closure.prototype = {
+    call$0: function() {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter(type$.Null),
+        $async$returnValue, controller, suite, engine, t1, t2, t3, t4, $async$temp1;
+      var $async$call$0 = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1)
+          return P._asyncRethrow($async$result, $async$completer);
+        while (true)
+          switch ($async$goto) {
+            case 0:
+              // Function start
+              t1 = $.$get$SuiteConfiguration_empty();
+              t2 = $._globalDeclarer.build$0();
+              t3 = E.SuitePlatform$(C.Runtime_ql0, false, $.$get$currentOSGuess());
+              t4 = P.Uri_base();
+              t4 = $.$get$context().prettyUri$1(t4);
+              controller = new Y.RunnerSuiteController(t1, null, new P._AsyncBroadcastStreamController(null, null, type$._AsyncBroadcastStreamController_bool), P.LinkedHashSet_LinkedHashSet$_empty(type$.String), new S.AsyncMemoizer(new P._AsyncCompleter(new P._Future($.Zone__current, type$._Future_dynamic), type$._AsyncCompleter_dynamic), type$.AsyncMemoizer_dynamic));
+              suite = new Y.RunnerSuite(controller, t3, t4, U.Suite__filterGroup(t2, t3));
+              t1 = new P._Future($.Zone__current, type$._Future_RunnerSuite);
+              t1._asyncComplete$1(suite);
+              controller.set$_runner_suite$_suite(t1);
+              engine = O.Engine$();
+              t1 = engine._suiteController;
+              t1.add$1(0, H._instanceType(t1)._precomputed1._check(type$.RunnerSuite._check(suite)));
+              t1.close$0(0);
+              if ($.Stopwatch__frequency == null) {
+                H.Primitives_initTicker();
+                $.Stopwatch__frequency = $.Primitives_timerFrequency;
+              }
+              t1 = P.LinkedHashSet_LinkedHashSet$_empty(type$.StreamSubscription_dynamic);
+              t2 = new R.ExpandedReporter(true, "\x1b[32m", "\x1b[31m", "\x1b[33m", "\x1b[1;30m", "\x1b[1m", "\x1b[0m", engine, false, false, new P.Stopwatch(), t1, new X.PrintSink(new P.StringBuffer("")));
+              t3 = engine._onTestStartedGroup._stream_group$_controller;
+              t3.toString;
+              t1.add$1(0, new P._BroadcastStream(t3, H._instanceType(t3)._eval$1("_BroadcastStream<1>")).listen$1(t2.get$_onTestStarted()));
+              t3 = engine.get$success();
+              t3.toString;
+              t1.add$1(0, P.Stream_Stream$fromFuture(t3, t3.$ti._precomputed1).listen$1(t2.get$_expanded$_onDone()));
+              t2 = type$.dynamic;
+              $async$temp1 = H;
+              $async$goto = 3;
+              return P._asyncAwait(P.runZoned(new R._declarer__closure(engine), null, null, P.LinkedHashMap_LinkedHashMap$_literal([C.Symbol_Drw, $._globalDeclarer], t2, t2), type$.Future_bool), $async$call$0);
+            case 3:
+              // returning from await.
+              if ($async$temp1.boolConversionCheck($async$result)) {
+                $async$returnValue = null;
+                // goto return
+                $async$goto = 1;
+                break;
+              }
+              P.print("");
+              P.Future_Future$error("Dummy exception to set exit code.", null, type$.void);
+            case 1:
+              // return
+              return P._asyncReturn($async$returnValue, $async$completer);
+          }
+      });
+      return P._asyncStartSync($async$call$0, $async$completer);
+    },
+    $signature: 2
+  };
+  R._declarer__closure.prototype = {
+    call$0: function() {
+      return U.Invoker_guard(this.engine.get$run(), type$.Future_bool);
+    },
+    $signature: 31
+  };
+  G.main_closure0.prototype = {
+    call$0: function() {
+      R.test("sample test", new G.main__closure());
+    },
+    $signature: 0
+  };
+  G.main__closure.prototype = {
+    call$0: function() {
+      var $async$goto = 0,
+        $async$completer = P._makeAsyncAwaitCompleter(type$.Null),
+        res;
+      var $async$call$0 = P._wrapJsFunctionForAsync(function($async$errorCode, $async$result) {
+        if ($async$errorCode === 1)
+          return P._asyncRethrow($async$result, $async$completer);
+        while (true)
+          switch ($async$goto) {
+            case 0:
+              // Function start
+              res = G.method1();
+              if (res === 0)
+                G.method2();
+              G.expect(true, C.C__IsTrue, null);
+              // implicit return
+              return P._asyncReturn(null, $async$completer);
+          }
+      });
+      return P._asyncStartSync($async$call$0, $async$completer);
+    },
+    $signature: 2
+  };
+  R.main_closure.prototype = {
+    call$0: function() {
+      return G.main_test__main$closure();
+    },
+    $signature: 103
+  };
+  (function aliases() {
+    var _ = J.JavaScriptObject.prototype;
+    _.super$JavaScriptObject$toString = _.toString$0;
+    _ = P._BroadcastStreamController.prototype;
+    _.super$_BroadcastStreamController$_addEventError = _._addEventError$0;
+    _ = P.Iterable.prototype;
+    _.super$Iterable$where = _.where$1;
+    _.super$Iterable$skipWhile = _.skipWhile$1;
+    _ = W.EventTarget.prototype;
+    _.super$EventTarget$addEventListener = _.addEventListener$3;
+    _ = Y.DelegatingStreamSubscription.prototype;
+    _.super$DelegatingStreamSubscription$onError = _.onError$1;
+    _.super$DelegatingStreamSubscription$cancel = _.cancel$0;
+    _ = M.TypeMatcher.prototype;
+    _.super$TypeMatcher$describe = _.describe$1;
+    _.super$TypeMatcher$matches = _.matches$2;
+    _ = Y.SourceSpanMixin.prototype;
+    _.super$SourceSpanMixin$$eq = _.$eq;
+    _ = X.StringScanner.prototype;
+    _.super$StringScanner$matches = _.matches$1;
+  })();
+  (function installTearOffs() {
+    var _instance = hunkHelpers.installInstanceTearOff,
+      _static_0 = hunkHelpers._static_0,
+      _static_1 = hunkHelpers._static_1,
+      _static = hunkHelpers.installStaticTearOff,
+      _instance_0_u = hunkHelpers._instance_0u,
+      _instance_1_i = hunkHelpers._instance_1i,
+      _instance_0_i = hunkHelpers._instance_0i,
+      _instance_1_u = hunkHelpers._instance_1u,
+      _instance_2_u = hunkHelpers._instance_2u;
+    _instance(J.JSString.prototype, "get$startsWith", 1, 1, null, ["call$2", "call$1"], ["startsWith$2", "startsWith$1"], 57, 0);
+    _static_0(H, "_js_helper_Primitives_dateNow$closure", "Primitives_dateNow", 36);
+    _static_1(P, "async__AsyncRun__scheduleImmediateJsOverride$closure", "_AsyncRun__scheduleImmediateJsOverride", 20);
+    _static_1(P, "async__AsyncRun__scheduleImmediateWithSetImmediate$closure", "_AsyncRun__scheduleImmediateWithSetImmediate", 20);
+    _static_1(P, "async__AsyncRun__scheduleImmediateWithTimer$closure", "_AsyncRun__scheduleImmediateWithTimer", 20);
+    _static_1(P, "async_Future__kTrue$closure", "Future__kTrue", 9);
+    _static_0(P, "async___startMicrotaskLoop$closure", "_startMicrotaskLoop", 1);
+    _static_1(P, "async___nullDataHandler$closure", "_nullDataHandler", 11);
+    _static(P, "async___nullErrorHandler$closure", 1, null, ["call$2", "call$1"], ["_nullErrorHandler", function(error) {
+      return P._nullErrorHandler(error, null);
+    }], 12, 0);
+    _static_0(P, "async___nullDoneHandler$closure", "_nullDoneHandler", 1);
+    _static(P, "async___rootHandleUncaughtError$closure", 5, null, ["call$5"], ["_rootHandleUncaughtError"], 105, 0);
+    _static(P, "async___rootRun$closure", 4, null, ["call$1$4", "call$4"], ["_rootRun", function($self, $parent, zone, f) {
+      return P._rootRun($self, $parent, zone, f, type$.dynamic);
+    }], 106, 0);
+    _static(P, "async___rootRunUnary$closure", 5, null, ["call$2$5", "call$5"], ["_rootRunUnary", function($self, $parent, zone, f, arg) {
+      return P._rootRunUnary($self, $parent, zone, f, arg, type$.dynamic, type$.dynamic);
+    }], 107, 0);
+    _static(P, "async___rootRunBinary$closure", 6, null, ["call$3$6"], ["_rootRunBinary"], 108, 0);
+    _static(P, "async___rootRegisterCallback$closure", 4, null, ["call$1$4", "call$4"], ["_rootRegisterCallback", function($self, $parent, zone, f) {
+      return P._rootRegisterCallback($self, $parent, zone, f, type$.dynamic);
+    }], 35, 0);
+    _static(P, "async___rootRegisterUnaryCallback$closure", 4, null, ["call$2$4", "call$4"], ["_rootRegisterUnaryCallback", function($self, $parent, zone, f) {
+      return P._rootRegisterUnaryCallback($self, $parent, zone, f, type$.dynamic, type$.dynamic);
+    }], 33, 0);
+    _static(P, "async___rootRegisterBinaryCallback$closure", 4, null, ["call$3$4", "call$4"], ["_rootRegisterBinaryCallback", function($self, $parent, zone, f) {
+      return P._rootRegisterBinaryCallback($self, $parent, zone, f, type$.dynamic, type$.dynamic, type$.dynamic);
+    }], 109, 0);
+    _static(P, "async___rootErrorCallback$closure", 5, null, ["call$5"], ["_rootErrorCallback"], 32, 0);
+    _static(P, "async___rootScheduleMicrotask$closure", 4, null, ["call$4"], ["_rootScheduleMicrotask"], 110, 0);
+    _static(P, "async___rootCreateTimer$closure", 5, null, ["call$5"], ["_rootCreateTimer"], 111, 0);
+    _static(P, "async___rootCreatePeriodicTimer$closure", 5, null, ["call$5"], ["_rootCreatePeriodicTimer"], 112, 0);
+    _static(P, "async___rootPrint$closure", 4, null, ["call$4"], ["_rootPrint"], 37, 0);
+    _static_1(P, "async___printToZone$closure", "_printToZone", 113);
+    _static(P, "async___rootFork$closure", 5, null, ["call$5"], ["_rootFork"], 114, 0);
+    var _;
+    _instance_0_u(_ = P._BroadcastSubscription.prototype, "get$_onPause", "_onPause$0", 1);
+    _instance_0_u(_, "get$_onResume", "_onResume$0", 1);
+    _instance_1_i(_ = P._BroadcastStreamController.prototype, "get$add", "add$1", 11);
+    _instance(_, "get$addError", 0, 1, null, ["call$2", "call$1"], ["addError$2", "addError$1"], 12, 0);
+    _instance(P._AsyncCompleter.prototype, "get$complete", 0, 0, null, ["call$1", "call$0"], ["complete$1", "complete$0"], 47, 0);
+    _instance(P._SyncCompleter.prototype, "get$complete", 0, 0, null, ["call$1", "call$0"], ["complete$1", "complete$0"], 47, 0);
+    _instance(P._Future.prototype, "get$_completeError", 0, 1, null, ["call$2", "call$1"], ["_completeError$2", "_completeError$1"], 12, 0);
+    _instance_1_i(_ = P._StreamController.prototype, "get$add", "add$1", 11);
+    _instance(_, "get$addError", 0, 1, null, ["call$2", "call$1"], ["addError$2", "addError$1"], 12, 0);
+    _instance_0_i(_, "get$close", "close$0", 14);
+    _instance_1_u(_, "get$_add", "_add$1", 11);
+    _instance_2_u(_, "get$_async$_addError", "_async$_addError$2", 70);
+    _instance_0_u(_, "get$_close", "_close$0", 1);
+    _instance_0_u(_ = P._ControllerSubscription.prototype, "get$_onPause", "_onPause$0", 1);
+    _instance_0_u(_, "get$_onResume", "_onResume$0", 1);
+    _instance_1_i(P._StreamSinkWrapper.prototype, "get$add", "add$1", 11);
+    _instance_0_u(_ = P._BufferingStreamSubscription.prototype, "get$_onPause", "_onPause$0", 1);
+    _instance_0_u(_, "get$_onResume", "_onResume$0", 1);
+    _instance_0_u(P._DoneStreamSubscription.prototype, "get$_sendDone", "_sendDone$0", 1);
+    _instance_1_i(P._LinkedHashSet.prototype, "get$contains", "contains$1", 26);
+    _static_1(P, "core_Uri_decodeComponent$closure", "Uri_decodeComponent", 7);
+    _instance_0_i(S.NullStreamSink.prototype, "get$close", "close$0", 14);
+    _instance_0_u(_ = L.StreamGroup.prototype, "get$_onListen", "_onListen$0", 1);
+    _instance_0_u(_, "get$_onCancelBroadcast", "_onCancelBroadcast$0", 1);
+    _instance_1_i(M._DelegatingIterableBase.prototype, "get$contains", "contains$1", 26);
+    _instance(D._DeepMatcher.prototype, "get$_recursiveMatch", 0, 4, null, ["call$4"], ["_recursiveMatch$4"], 58, 0);
+    _static_1(Z, "pretty_print___escapeString$closure", "_escapeString", 7);
+    _static_1(M, "util___getHexLiteral$closure", "_getHexLiteral", 7);
+    _instance(Y.SourceSpanMixin.prototype, "get$message", 1, 1, null, ["call$2$color", "call$1"], ["message$2$color", "message$1"], 71, 0);
+    _instance(_ = O.StackZoneSpecification.prototype, "get$_stack_zone_specification$_registerCallback", 0, 4, null, ["call$1$4", "call$4"], ["_stack_zone_specification$_registerCallback$1$4", "_stack_zone_specification$_registerCallback$4"], 35, 0);
+    _instance(_, "get$_stack_zone_specification$_registerUnaryCallback", 0, 4, null, ["call$2$4", "call$4"], ["_stack_zone_specification$_registerUnaryCallback$2$4", "_stack_zone_specification$_registerUnaryCallback$4"], 33, 0);
+    _instance(_, "get$_stack_zone_specification$_registerBinaryCallback", 0, 4, null, ["call$3$4", "call$4"], ["_stack_zone_specification$_registerBinaryCallback$3$4", "_stack_zone_specification$_registerBinaryCallback$4"], 63, 0);
+    _instance(_, "get$_stack_zone_specification$_errorCallback", 0, 5, null, ["call$5"], ["_stack_zone_specification$_errorCallback$5"], 32, 0);
+    _instance(_ = K._GuaranteeSink.prototype, "get$addError", 0, 1, null, ["call$2", "call$1"], ["addError$2", "addError$1"], 12, 0);
+    _instance(_, "get$_addError", 0, 1, null, ["call$2", "call$1"], ["_addError$2", "_addError$1"], 66, 0);
+    _instance_0_i(_, "get$close", "close$0", 13);
+    _instance_0_u(D._MultiChannel.prototype, "get$_closeInnerChannel", "_closeInnerChannel$0", 1);
+    _instance_0_u(_ = U.Invoker.prototype, "get$_invoker$_onRun", "_invoker$_onRun$0", 1);
+    _instance_0_u(_, "get$_runTearDowns", "_runTearDowns$0", 13);
+    _instance_0_u(V._LiveTest.prototype, "get$run", "run$0", 13);
+    _instance_1_i(V.LiveTestController.prototype, "get$message", "message$1", 96);
+    _instance_0_u(O.Engine.prototype, "get$run", "run$0", 31);
+    _instance_1_u(_ = R.ExpandedReporter.prototype, "get$_onTestStarted", "_onTestStarted$1", 98);
+    _instance_1_u(_, "get$_expanded$_onDone", "_expanded$_onDone$1", 99);
+    _static_0(G, "main_test__main$closure", "main0", 34);
+    _static(P, "math__max$closure", 2, null, ["call$1$2", "call$2"], ["max", function(a, b) {
+      return P.max(a, b, type$.num);
+    }], 76, 0);
+  })();
+  (function inheritance() {
+    var _mixin = hunkHelpers.mixin,
+      _inherit = hunkHelpers.inherit,
+      _inheritMany = hunkHelpers.inheritMany;
+    _inherit(P.Object, null);
+    _inheritMany(P.Object, [H.JS_CONST, J.Interceptor, J.JSObject, J.ArrayIterator, P.Iterable, H.CastIterator, P.MapMixin, H.Closure, P._ListBase_Object_ListMixin, H.ListIterator, P.Iterator, H.ExpandIterator, H.EmptyIterator, H.FixedLengthListMixin, H.UnmodifiableListMixin, H.Symbol, H.ConstantMap, H.TypeErrorDecoder, P.Error, H.ExceptionAndStackTrace, H._StackTrace, H.LinkedHashMapCell, H.LinkedHashMapKeyIterator, H.JSSyntaxRegExp, H._MatchImplementation, H._AllMatchesIterator, H.StringMatch, H._StringAllMatchesIterator, H.Rti, H._FunctionParameters, H._Type, P._TimerImpl, P._AsyncAwaitCompleter, P.Stream, P._BufferingStreamSubscription, P._BroadcastStreamController, P.Future, P.TimeoutException, P.Completer, P._Completer, P._FutureListener, P._Future, P._AsyncCallbackEntry, P.StreamSubscription, P.StreamTransformerBase, P._StreamController, P._SyncStreamControllerDispatch, P._AsyncStreamControllerDispatch, P._StreamSinkWrapper, P._AddStreamState, P._PendingEvents, P._DelayedEvent, P._DelayedDone, P._DoneStreamSubscription, P._StreamIterator, P.Timer, P.AsyncError, P._ZoneFunction, P.ZoneSpecification, P._ZoneSpecification, P.ZoneDelegate, P.Zone, P._ZoneDelegate, P._Zone, P._HashMapKeyIterator, P._SetBase, P._LinkedHashSetCell, P._LinkedHashSetIterator, P.ListMixin, P._UnmodifiableMapMixin, P.MapView, P._ListQueueIterator, P.SetMixin, P._SetBase_Object_SetMixin, P.Codec, P._Utf8Encoder, P._Utf8Decoder, P.bool, P.DateTime, P.num, P.Duration, P.OutOfMemoryError, P.StackOverflowError, P._Exception, P.FormatException, P.Expando, P.Function, P.List, P.Map, P.MapEntry, P.Null, P.Pattern, P.Match, P.RegExpMatch, P.StackTrace, P._StringStackTrace, P.Stopwatch, P.String, P.RuneIterator, P.StringBuffer, P.Uri, P._Uri, P.UriData, P._SimpleUri, W.EventStreamProvider, P._StructuredClone, P._AcceptStructuredClone, P.ByteBuffer, P.ByteData, P.Int8List, P.Uint8List, P.Uint8ClampedList, P.Int16List, P.Uint16List, P.Int32List, P.Uint32List, P.Float32List, P.Float64List, S.AsyncMemoizer, O.DelegatingSink, Y.DelegatingStreamSubscription, F.FutureGroup, S.NullStreamSink, V.ErrorResult, E.Result, F.ValueResult, Y.StreamCompleter, L.StreamGroup, L._StreamGroupState, G.StreamQueue, G._EventRequest, G._NextRequest, G._RestRequest, T.StreamSinkCompleter, T._CompleterSink, X.BooleanSelector, X.All, U.VariableNode, U.NotNode, U.OrNode, U.AndNode, U.ConditionalNode, T.Evaluator, Y.BooleanSelectorImpl, R.IntersectionSelector, O.None, G.Parser, O.Scanner, L.Token, L.IdentifierToken, L.TokenType, B.RecursiveVisitor, Q._QueueList_Object_ListMixin, Y.UnionSetController, M._DelegatingIterableBase, L.UnmodifiableSetMixin, G.Matcher, E.StringDescription, F.PackageConfigResolver, D.PackageRootResolver, M.Context, M._PathDirection, M._PathRelation, O.Style, X.ParsedPath, X.PathException, O.Pool, O.PoolResource, T.Mapping, T.TargetLineEntry, T.TargetEntry, T._MappingTokenizer, T._TokenKind, Y.SourceSpanMixin, Y.SourceFile, D.SourceLocationMixin, U.Highlighter, V.SourceLocation, V.SourceSpan, G.SourceSpanException, U.Chain, A.Frame, X.LazyChain, T.LazyTrace, O.StackZoneSpecification, O._Node, Y.Trace, N.UnparsedFrame, R.StreamChannelMixin, K._GuaranteeSink, N.StreamChannelCompleter, B.StreamChannelController, R.StreamChannel, X.StringScanner, S._SpanScannerState, A.AsciiGlyphSet, K.UnicodeGlyphSet, K.ClosedException, X.Declarer, O.Group, V.GroupEntry, V.Test, U.Invoker, U._AsyncCounter, Z.LiveTest, V.LiveTestController, D.Message, D.MessageType, O.Metadata, N.OperatingSystem, E.PlatformSelector, B.Runtime, U.StackTraceFormatter, G.State, G.Status, G.Result0, U.Suite, E.SuitePlatform, G.TestFailure, R.Timeout, S.RemoteListener, N.SuiteChannelManager, E.StackTraceMapper, O.Engine, E.LiveSuite, B.LiveSuiteController, R.ExpandedReporter, Y.RunnerSuiteController, T.RuntimeSelection, U.SuiteConfiguration, X.PrintSink]);
+    _inheritMany(J.Interceptor, [J.JSBool, J.JSNull, J.JavaScriptObject, J.JSArray, J.JSNumber, J.JSString, H.NativeByteBuffer, H.NativeTypedData, W.Event, W.Blob, W.DomError, W.DomException, W.EventTarget, W.Location, W.MediaError, W.NavigatorUserMediaError, W.OverconstrainedError, W.PositionError, P.SqlError]);
+    _inheritMany(J.JavaScriptObject, [J.PlainJavaScriptObject, J.UnknownJavaScriptObject, J.JavaScriptFunction]);
+    _inherit(J.JSUnmodifiableArray, J.JSArray);
+    _inheritMany(J.JSNumber, [J.JSInt, J.JSDouble]);
+    _inheritMany(P.Iterable, [H._CastIterableBase, H.EfficientLengthIterable, H.MappedIterable, H.WhereIterable, H.ExpandIterable, H.SkipWhileIterable, H._ConstantMapKeyIterable, P.IterableBase, H._StringAllMatchesIterable, P.Runes]);
+    _inherit(H.CastIterable, H._CastIterableBase);
+    _inherit(H._EfficientLengthCastIterable, H.CastIterable);
+    _inherit(P.MapBase, P.MapMixin);
+    _inheritMany(P.MapBase, [H.CastMap, H.JsLinkedHashMap, P._HashMap, P._JsonMap]);
+    _inheritMany(H.Closure, [H.CastMap_forEach_closure, H.ConstantMap_map_closure, H.Instantiation, H.Primitives_initTicker_closure, H.unwrapException_saveStackTrace, H.TearOffClosure, H.JsLinkedHashMap_values_closure, H.JsLinkedHashMap_addAll_closure, H.initHooks_closure, H.initHooks_closure0, H.initHooks_closure1, P._AsyncRun__initializeScheduleImmediate_internalCallback, P._AsyncRun__initializeScheduleImmediate_closure, P._AsyncRun__scheduleImmediateJsOverride_internalCallback, P._AsyncRun__scheduleImmediateWithSetImmediate_internalCallback, P._TimerImpl_internalCallback, P._TimerImpl$periodic_closure, P._awaitOnObject_closure, P._awaitOnObject_closure0, P._wrapJsFunctionForAsync_closure, P._SyncBroadcastStreamController__sendData_closure, P._SyncBroadcastStreamController__sendError_closure, P._SyncBroadcastStreamController__sendDone_closure, P.Future_Future_closure, P.Future_Future$microtask_closure, P.Future_wait_handleError, P.Future_wait_closure, P.Future_forEach_closure, P.Future_doWhile_closure, P._Future__addListener_closure, P._Future__prependListeners_closure, P._Future__chainForeignFuture_closure, P._Future__chainForeignFuture_closure0, P._Future__chainForeignFuture_closure1, P._Future__asyncComplete_closure, P._Future__chainFuture_closure, P._Future__asyncCompleteError_closure, P._Future__propagateToListeners_handleWhenCompleteCallback, P._Future__propagateToListeners_handleWhenCompleteCallback_closure, P._Future__propagateToListeners_handleValueCallback, P._Future__propagateToListeners_handleError, P.Stream_Stream$fromFuture_closure, P.Stream_Stream$fromFuture_closure0, P.Stream_Stream$fromIterable_closure, P.Stream_pipe_closure, P.Stream_length_closure, P.Stream_length_closure0, P.Stream_first_closure, P.Stream_first_closure0, P.Stream_last_closure, P.Stream_last_closure0, P.Stream_firstWhere_closure, P.Stream_firstWhere__closure, P.Stream_firstWhere__closure0, P.Stream_firstWhere_closure0, P._StreamController__subscribe_closure, P._StreamController__recordCancel_complete, P._AddStreamState_makeErrorHandler_closure, P._AddStreamState_cancel_closure, P._BufferingStreamSubscription__sendError_sendError, P._BufferingStreamSubscription__sendDone_sendDone, P._PendingEvents_schedule_closure, P._cancelAndError_closure, P._cancelAndErrorClosure_closure, P._cancelAndValue_closure, P._CustomZone_bindCallback_closure, P._CustomZone_bindUnaryCallback_closure, P._CustomZone_bindCallbackGuarded_closure, P._CustomZone_bindUnaryCallbackGuarded_closure, P._rootHandleUncaughtError_closure, P._RootZone_bindCallback_closure, P._RootZone_bindCallbackGuarded_closure, P._RootZone_bindUnaryCallbackGuarded_closure, P.runZoned_closure, P.HashMap_HashMap$from_closure, P.LinkedHashMap_LinkedHashMap$from_closure, P.MapBase_mapToString_closure, P.Duration_toString_sixDigits, P.Duration_toString_twoDigits, P.Uri__parseIPv4Address_error, P.Uri_parseIPv6Address_error, P.Uri_parseIPv6Address_parseHex, P._Uri__Uri$notSimple_closure, P._Uri__checkNonWindowsPathReservedCharacters_closure, P._Uri__makePath_closure, P._createTables_closure, P._createTables_build, P._createTables_setChars, P._createTables_setRange, W._EventStreamSubscription_closure, P._StructuredClone_walk_closure, P._StructuredClone_walk_closure0, P._AcceptStructuredClone_walk_closure, P._convertDataTree__convert, P.promiseToFuture_closure, P.promiseToFuture_closure0, F.FutureGroup_add_closure, F.FutureGroup_add_closure0, S.NullStreamSink_addStream_closure, L.StreamGroup_add_closure, L.StreamGroup_add_closure0, L.StreamGroup__onListen_closure, L.StreamGroup__onCancelBroadcast_closure, L.StreamGroup__listenToStream_closure, G.StreamQueue__ensureListening_closure, G.StreamQueue__ensureListening_closure1, G.StreamQueue__ensureListening_closure0, T._CompleterSink__setDestinationSink_closure, T._CancelOnErrorSubscriptionWrapper_onError_closure, T._CancelOnErrorSubscriptionWrapper_onError__closure, Y.mapMap_closure, Y.mapMap_closure0, Y.mergeMaps_closure, M.UnionSet_length_closure, M.UnionSet__iterable_closure, D._DeepMatcher__compareSets_closure, Z.prettyPrint__prettyPrint, Z.prettyPrint__prettyPrint_pp, Z.prettyPrint__prettyPrint_closure, Z.prettyPrint__prettyPrint_closure0, Z.prettyPrint__prettyPrint_closure1, M.wrapMatcher_closure, M.escape_closure, F.PackageConfigResolver__normalizeMap_closure, M.Context_join_closure, M.Context_joinAll_closure, M.Context_split_closure, M._validateArgList_closure, X.ParsedPath_normalize_closure, L.WindowsStyle_absolutePathToUri_closure, O.Pool_close_closure, O.Pool__onResourceReleaseAllowed_closure, O.Pool__runOnRelease_closure, O.Pool__runOnRelease_closure0, O.mapStackTrace_closure, O.mapStackTrace_closure0, O.mapStackTrace_closure1, O._prettifyMember_closure, O._prettifyMember_closure0, T.SingleMapping$fromJson_closure, T.SingleMapping__findLine_closure, T.SingleMapping__findColumn_closure, L.closure, U.Highlighter__writeFirstLine_closure, U.Highlighter__writeFirstLine_closure0, U.Highlighter__writeFirstLine_closure1, U.Highlighter__writeFirstLine_closure2, U.Highlighter__writeIntermediateLines_closure, U.Highlighter__writeLastLine_closure, U.Highlighter__writeLastLine_closure0, U.Highlighter__writeLastLine_closure1, U.Highlighter__writeSidebar_closure, U.Chain_capture_closure, U.Chain_Chain$current_closure, U.Chain_Chain$forTrace_closure, U.Chain_Chain$parse_closure, U.Chain_Chain$parse_closure0, U.Chain_foldFrames_closure, U.Chain_foldFrames_closure0, U.Chain_toTrace_closure, U.Chain_toString_closure0, U.Chain_toString__closure0, U.Chain_toString_closure, U.Chain_toString__closure, A.Frame_Frame$parseVM_closure, A.Frame_Frame$parseV8_closure, A.Frame_Frame$parseV8_closure_parseLocation, A.Frame_Frame$parseFirefox_closure, A.Frame_Frame$parseFriendly_closure, X.LazyChain_foldFrames_closure, X.LazyChain_toTrace_closure, T.LazyTrace_foldFrames_closure, O.StackZoneSpecification_chainFor_closure, O.StackZoneSpecification_chainFor_closure0, O.StackZoneSpecification__registerCallback_closure, O.StackZoneSpecification__registerUnaryCallback_closure, O.StackZoneSpecification__registerUnaryCallback__closure, O.StackZoneSpecification__registerBinaryCallback_closure, O.StackZoneSpecification__registerBinaryCallback__closure, O.StackZoneSpecification__currentTrace_closure, Y.Trace_Trace$current_closure, Y.Trace_Trace$from_closure, Y.Trace__parseVM_closure, Y.Trace$parseV8_closure, Y.Trace$parseV8_closure0, Y.Trace$parseJSCore_closure, Y.Trace$parseJSCore_closure0, Y.Trace$parseFirefox_closure, Y.Trace$parseFirefox_closure0, Y.Trace$parseFriendly_closure, Y.Trace$parseFriendly_closure0, Y.Trace_foldFrames_closure, Y.Trace_foldFrames_closure0, Y.Trace_toString_closure0, Y.Trace_toString_closure, K.GuaranteeChannel_closure, K.GuaranteeChannel__closure, K._GuaranteeSink__addError_closure, K._GuaranteeSink_addStream_closure, D._MultiChannel_closure, D._MultiChannel_closure0, D._MultiChannel_closure1, D._MultiChannel__closure, D._MultiChannel_virtualChannel_closure, D._MultiChannel_virtualChannel_closure0, L.internalBootstrapBrowserTest_closure, N.postMessageChannel_closure, N.postMessageChannel_closure0, N.postMessageChannel__closure, N.postMessageChannel__closure0, N.postMessageChannel__closure1, X.Declarer_test_closure, X.Declarer_test__closure, X.Declarer_test___closure, X.Declarer_group_closure, X.Declarer_build_closure, X.Declarer__runSetUps_closure, X.Declarer__tearDownAll_closure, X.Declarer__tearDownAll__closure, X.Declarer__tearDownAll___closure, O.Group_forPlatform_closure, O.Group__map_closure, O.Group__map_closure0, U.Invoker_guard_closure, U.Invoker_guard__closure, U.Invoker_waitForOutstandingCallbacks_closure, U.Invoker_waitForOutstandingCallbacks_closure0, U.Invoker_heartbeat_message, U.Invoker_heartbeat_closure, U.Invoker_heartbeat__closure, U.Invoker__handleError_closure, U.Invoker__handleError_closure0, U.Invoker__onRun_closure, U.Invoker__onRun__closure, U.Invoker__onRun___closure, U.Invoker__onRun____closure, U.Invoker__onRun___closure0, O.Metadata_Metadata__unresolved, O.Metadata_Metadata_closure, O.Metadata$deserialize_closure, O.Metadata__validateTags_closure, O.Metadata__validateTags_closure0, O.Metadata_validatePlatformSelectors_closure, O.Metadata_merge_closure, O.Metadata_merge_closure0, O.Metadata_forPlatform_closure, O.Metadata_serialize_closure, O.Metadata_serialize_closure0, N.OperatingSystem_find_closure, N.OperatingSystem_find_closure0, E.PlatformSelector$parse_closure, E.PlatformSelector_validate_closure, E.PlatformSelector_validate__closure, E.PlatformSelector_evaluate_closure, B.Runtime_Runtime$deserialize_closure, U.StackTraceFormatter_formatStackTrace_closure, G._expect_closure0, G._expect_closure, S.RemoteListener_start_closure, S.RemoteListener_start_closure0, S.RemoteListener_start_closure1, S.RemoteListener_start__closure, S.RemoteListener_start___closure, S.RemoteListener_start____closure, S.RemoteListener_start____closure0, S.RemoteListener_start_____closure, S.RemoteListener_start___closure0, S.RemoteListener__serializeGroup_closure, S.RemoteListener__serializeTest_closure, S.RemoteListener__runLiveTest_closure, S.RemoteListener__runLiveTest_closure0, S.RemoteListener__runLiveTest_closure1, S.RemoteListener__runLiveTest_closure2, S.RemoteListener__runLiveTest_closure3, S.RemoteListener__runLiveTest__closure, V.errorsDontStopTest_closure, V.errorsDontStopTest_closure0, B.closure0, O.Engine_success_closure, O.Engine_closure, O.Engine_closure0, O.Engine_run_closure, O.Engine_run__closure, O.Engine_run___closure, O.Engine_run____closure, O.Engine_run_closure0, O.Engine__runLiveTest_closure, O.Engine__runLiveTest_closure0, O.Engine__runLiveTest_closure1, O.Engine__runSkippedTest_closure, O.Engine__runSkippedTest_closure0, O.Engine__runSkippedTest_closure1, B.LiveSuiteController_closure, B.LiveSuiteController_closure0, B.LiveSuiteController_reportLiveTest_closure, B.LiveSuiteController_close_closure, R.ExpandedReporter__onTestStarted_closure, R.ExpandedReporter__onTestStarted_closure0, R.ExpandedReporter__onTestStarted_closure1, Y.RunnerSuiteController__close_closure, E.JSStackTraceMapper__deserializePackageConfigMap_closure, R._declarer_closure, R._declarer__closure, G.main_closure0, G.main__closure, R.main_closure]);
+    _inherit(P.ListBase, P._ListBase_Object_ListMixin);
+    _inherit(H.UnmodifiableListBase, P.ListBase);
+    _inheritMany(H.UnmodifiableListBase, [H.CodeUnits, P.UnmodifiableListView]);
+    _inheritMany(H.EfficientLengthIterable, [H.ListIterable, H.LinkedHashMapKeyIterable, P._HashMapKeyIterable, P.Set]);
+    _inheritMany(H.ListIterable, [H.SubListIterable, H.MappedListIterable, H.ReversedListIterable, P.ListQueue, P._JsonMapKeyIterable]);
+    _inherit(H.EfficientLengthMappedIterable, H.MappedIterable);
+    _inheritMany(P.Iterator, [H.MappedIterator, H.WhereIterator, H.SkipWhileIterator]);
+    _inherit(H.ConstantStringMap, H.ConstantMap);
+    _inherit(H.Instantiation1, H.Instantiation);
+    _inheritMany(P.Error, [H.NullError, H.JsNoSuchMethodError, H.UnknownJsTypeError, H.TypeErrorImplementation, H.RuntimeError, P.AssertionError, H._Error, P.NullThrownError, P.ArgumentError, P.UnsupportedError, P.UnimplementedError, P.StateError, P.ConcurrentModificationError, P.CyclicInitializationError]);
+    _inheritMany(H.TearOffClosure, [H.StaticClosure, H.BoundClosure]);
+    _inherit(H._AssertionError, P.AssertionError);
+    _inheritMany(P.IterableBase, [H._AllMatchesIterable, O.EmptyUnmodifiableSet]);
+    _inheritMany(H.NativeTypedData, [H.NativeByteData, H.NativeTypedArray]);
+    _inheritMany(H.NativeTypedArray, [H._NativeTypedArrayOfDouble_NativeTypedArray_ListMixin, H._NativeTypedArrayOfInt_NativeTypedArray_ListMixin]);
+    _inherit(H._NativeTypedArrayOfDouble_NativeTypedArray_ListMixin_FixedLengthListMixin, H._NativeTypedArrayOfDouble_NativeTypedArray_ListMixin);
+    _inherit(H.NativeTypedArrayOfDouble, H._NativeTypedArrayOfDouble_NativeTypedArray_ListMixin_FixedLengthListMixin);
+    _inherit(H._NativeTypedArrayOfInt_NativeTypedArray_ListMixin_FixedLengthListMixin, H._NativeTypedArrayOfInt_NativeTypedArray_ListMixin);
+    _inherit(H.NativeTypedArrayOfInt, H._NativeTypedArrayOfInt_NativeTypedArray_ListMixin_FixedLengthListMixin);
+    _inheritMany(H.NativeTypedArrayOfDouble, [H.NativeFloat32List, H.NativeFloat64List]);
+    _inheritMany(H.NativeTypedArrayOfInt, [H.NativeInt16List, H.NativeInt32List, H.NativeInt8List, H.NativeUint16List, H.NativeUint32List, H.NativeUint8ClampedList, H.NativeUint8List]);
+    _inheritMany(H._Error, [H._CastError, H._TypeError]);
+    _inheritMany(P.Stream, [P._StreamImpl, P._EmptyStream, W._EventStream, Y._CompleterStream, T.SubscriptionStream]);
+    _inheritMany(P._StreamImpl, [P._ControllerStream, P._GeneratedStreamImpl]);
+    _inherit(P._BroadcastStream, P._ControllerStream);
+    _inherit(P._ControllerSubscription, P._BufferingStreamSubscription);
+    _inherit(P._BroadcastSubscription, P._ControllerSubscription);
+    _inheritMany(P._BroadcastStreamController, [P._SyncBroadcastStreamController, P._AsyncBroadcastStreamController]);
+    _inheritMany(P._Completer, [P._AsyncCompleter, P._SyncCompleter]);
+    _inheritMany(P._StreamController, [P._AsyncStreamController, P._SyncStreamController]);
+    _inherit(P._StreamControllerAddStreamState, P._AddStreamState);
+    _inheritMany(P._PendingEvents, [P._IterablePendingEvents, P._StreamImplEvents]);
+    _inheritMany(P._DelayedEvent, [P._DelayedData, P._DelayedError]);
+    _inheritMany(P._Zone, [P._CustomZone, P._RootZone]);
+    _inherit(P._IdentityHashMap, P._HashMap);
+    _inherit(P._LinkedHashSet, P._SetBase);
+    _inherit(P._UnmodifiableMapView_MapView__UnmodifiableMapMixin, P.MapView);
+    _inherit(P.UnmodifiableMapView, P._UnmodifiableMapView_MapView__UnmodifiableMapMixin);
+    _inherit(P.SetBase, P._SetBase_Object_SetMixin);
+    _inheritMany(P.Codec, [P.Encoding, P.Base64Codec, P._FusedCodec, P.JsonCodec]);
+    _inheritMany(P.Encoding, [P.AsciiCodec, P.Utf8Codec]);
+    _inherit(P.Converter, P.StreamTransformerBase);
+    _inheritMany(P.Converter, [P._UnicodeSubsetEncoder, P.Base64Encoder, P.JsonDecoder, P.Utf8Encoder, P.Utf8Decoder]);
+    _inherit(P.AsciiEncoder, P._UnicodeSubsetEncoder);
+    _inheritMany(P.num, [P.double, P.int]);
+    _inheritMany(P.ArgumentError, [P.RangeError, P.IndexError]);
+    _inherit(P._DataUri, P._Uri);
+    _inheritMany(W.Event, [W.ApplicationCacheErrorEvent, W.ErrorEvent, W.MediaKeyMessageEvent, W.MessageEvent, W.PresentationConnectionCloseEvent, W.SpeechRecognitionError]);
+    _inherit(W.File, W.Blob);
+    _inherit(W.MessagePort, W.EventTarget);
+    _inherit(W._EventStreamSubscription, P.StreamSubscription);
+    _inherit(P._StructuredCloneDart2Js, P._StructuredClone);
+    _inherit(P._AcceptStructuredCloneDart2Js, P._AcceptStructuredClone);
+    _inherit(T._CancelOnErrorSubscriptionWrapper, Y.DelegatingStreamSubscription);
+    _inherit(S.Validator, B.RecursiveVisitor);
+    _inherit(Q.QueueList, Q._QueueList_Object_ListMixin);
+    _inherit(M._UnionSet_SetBase_UnmodifiableSetMixin, P.SetBase);
+    _inherit(M.UnionSet, M._UnionSet_SetBase_UnmodifiableSetMixin);
+    _inherit(M.DelegatingIterable, M._DelegatingIterableBase);
+    _inherit(M.DelegatingSet, M.DelegatingIterable);
+    _inherit(L._UnmodifiableSetView_DelegatingSet_UnmodifiableSetMixin, M.DelegatingSet);
+    _inherit(L.UnmodifiableSetView, L._UnmodifiableSetView_DelegatingSet_UnmodifiableSetMixin);
+    _inheritMany(G.Matcher, [Y._IsTrue, M.TypeMatcher, D._DeepMatcher]);
+    _inherit(E.FeatureMatcher, M.TypeMatcher);
+    _inheritMany(E.FeatureMatcher, [Y._Predicate, D._StringEqualsMatcher]);
+    _inherit(B.InternalStyle, O.Style);
+    _inheritMany(B.InternalStyle, [E.PosixStyle, F.UrlStyle, L.WindowsStyle]);
+    _inheritMany(T.Mapping, [T.MultiSectionMapping, T.MappingBundle, T.SingleMapping]);
+    _inheritMany(Y.SourceSpanMixin, [V.SourceSpanBase, Y._FileSpan]);
+    _inheritMany(V.SourceSpanBase, [G.SourceMapSpan, X.SourceSpanWithContext]);
+    _inherit(Y.FileLocation, D.SourceLocationMixin);
+    _inherit(G.SourceSpanFormatException, G.SourceSpanException);
+    _inheritMany(R.StreamChannelMixin, [K.GuaranteeChannel, D._MultiChannel, D.VirtualChannel, R._StreamChannel]);
+    _inherit(E.StringScannerException, G.SourceSpanFormatException);
+    _inherit(S.SpanScanner, X.StringScanner);
+    _inherit(U.LocalTest, V.Test);
+    _inherit(V._LiveTest, Z.LiveTest);
+    _inherit(O._IterableSet_SetMixin_UnmodifiableSetMixin, P.SetMixin);
+    _inherit(O.IterableSet, O._IterableSet_SetMixin_UnmodifiableSetMixin);
+    _inherit(B._LiveSuite, E.LiveSuite);
+    _inherit(Y.RunnerSuite, U.Suite);
+    _inherit(E.JSStackTraceMapper, E.StackTraceMapper);
+    _mixin(H.UnmodifiableListBase, H.UnmodifiableListMixin);
+    _mixin(H._NativeTypedArrayOfDouble_NativeTypedArray_ListMixin, P.ListMixin);
+    _mixin(H._NativeTypedArrayOfDouble_NativeTypedArray_ListMixin_FixedLengthListMixin, H.FixedLengthListMixin);
+    _mixin(H._NativeTypedArrayOfInt_NativeTypedArray_ListMixin, P.ListMixin);
+    _mixin(H._NativeTypedArrayOfInt_NativeTypedArray_ListMixin_FixedLengthListMixin, H.FixedLengthListMixin);
+    _mixin(P._AsyncStreamController, P._AsyncStreamControllerDispatch);
+    _mixin(P._SyncStreamController, P._SyncStreamControllerDispatch);
+    _mixin(P._ListBase_Object_ListMixin, P.ListMixin);
+    _mixin(P._SetBase_Object_SetMixin, P.SetMixin);
+    _mixin(P._UnmodifiableMapView_MapView__UnmodifiableMapMixin, P._UnmodifiableMapMixin);
+    _mixin(Q._QueueList_Object_ListMixin, P.ListMixin);
+    _mixin(M._UnionSet_SetBase_UnmodifiableSetMixin, L.UnmodifiableSetMixin);
+    _mixin(L._UnmodifiableSetView_DelegatingSet_UnmodifiableSetMixin, L.UnmodifiableSetMixin);
+    _mixin(O._IterableSet_SetMixin_UnmodifiableSetMixin, L.UnmodifiableSetMixin);
+  })();
+  var init = {typeUniverse: {eC: new Map(), tR: {}, eT: {}, tPV: {}, sEA: []}, mangledGlobalNames: {int: "int", double: "double", num: "num", String: "String", bool: "bool", Null: "Null", List: "List"}, mangledNames: {}, getTypeFromName: getGlobalFromName, metadata: [], types: ["Null()", "~()", "Future<Null>()", "Null(@)", "bool(String)", "Null(@,StackTrace)", "Null(@,@)", "String(String)", "Trace()", "bool(@)", "Frame(String)", "~(Object)", "~(Object[StackTrace])", "Future<~>()", "Future<@>()", "~(@)", "Chain()", "Frame()", "@(@)", "Null(PlatformSelector,Metadata)", "~(~())", "bool(Frame)", "GroupEntry(GroupEntry)", "Null(State)", "String(Match)", "String(int)", "bool(Object)", "Null(Message)", "Null(Zone,ZoneDelegate,Zone,Object,StackTrace)", "Null(MessageEvent)", "Null(String)", "Future<bool>()", "AsyncError(Zone,ZoneDelegate,Zone,Object,StackTrace)", "0^(1^)(Zone,ZoneDelegate,Zone,0^(1^))<Object,Object>", "@()", "0^()(Zone,ZoneDelegate,Zone,0^())<Object>", "int()", "~(Zone,ZoneDelegate,Zone,String)", "String(Frame)", "int(Frame)", "String(@)", "~(Uint8List,String,int)", "Trace(String)", "Null(bool)", "Metadata(Metadata,Metadata)", "Trace(Trace)", "Frame(Frame)", "~([Object])", "Null(List<@>)", "bool()", "Future<List<@>>()", "Uri(@,@)", "bool(Trace)", "List<Frame>(Trace)", "int(Trace)", "String(@,int,Set<@>,bool)", "String(Trace)", "bool(Pattern[int])", "List<String>(Object,Object,String,int)", "Frame(@,@)", "@(@,@)", "@(Event)", "Uint8List(@,@)", "0^(1^,2^)(Zone,ZoneDelegate,Zone,Function)<Object,Object,Object>", "Uint8List(int)", "int(int,int)", "~(@[StackTrace])", "~(String[@])", "~(String,int)", "bool(MessageEvent)", "~(Object,StackTrace)", "String(String{color:@})", "bool(GroupEntry)", "Future<@>(@)", "String()", "_Future<@>(@)", "0^(0^,0^)<num>", "Metadata()", "Metadata(Metadata,BooleanSelector)", "MapEntry<BooleanSelector,Metadata>(@,@)", "Null(@[StackTrace])", "bool/()", "MapEntry<String,Map<String,@>>(BooleanSelector,Metadata)", "bool(OperatingSystem)", "BooleanSelector()", "bool(Runtime)", "String(@,Matcher,String,Map<@,@>,bool)", "Null(Zone,ZoneDelegate,Zone,String)", "Map<@,@>(GroupEntry)", "Null(int,@)", "Null(AsyncError)", "Null(~())", "~(~)", "Map<String,int>()", "@(String)", "bool(LiveTest)", "~(Message)", "Null(RunnerSuite)", "~(LiveTest)", "~(bool)", "~(State)", "~(AsyncError)", "MapEntry<String,Uri>(String,String)", "@()()", "@(@,String)", "~(Zone,ZoneDelegate,Zone,@,StackTrace)", "0^(Zone,ZoneDelegate,Zone,0^())<Object>", "0^(Zone,ZoneDelegate,Zone,0^(1^),1^)<Object,Object>", "0^(Zone,ZoneDelegate,Zone,0^(1^,2^),1^,2^)<Object,Object,Object>", "0^(1^,2^)(Zone,ZoneDelegate,Zone,0^(1^,2^))<Object,Object,Object>", "~(Zone,ZoneDelegate,Zone,~())", "Timer(Zone,ZoneDelegate,Zone,Duration,~())", "Timer(Zone,ZoneDelegate,Zone,Duration,~(Timer))", "~(String)", "Zone(Zone,ZoneDelegate,Zone,ZoneSpecification,Map<@,@>)", "OperatingSystem()"], interceptorsByTag: null, leafTags: null};
+  H._Universe_addRules(init.typeUniverse, JSON.parse('{"JavaScriptFunction":"JavaScriptObject","PlainJavaScriptObject":"JavaScriptObject","UnknownJavaScriptObject":"JavaScriptObject","AbortPaymentEvent":"Event","ExtendableEvent":"Event","Window":"EventTarget","JSBool":{"bool":[]},"JSNull":{"Null":[]},"JavaScriptObject":{"JSObject":[],"Function":[]},"JSArray":{"List":["1"],"EfficientLengthIterable":["1"],"Iterable":["1"]},"JSUnmodifiableArray":{"JSArray":["1"],"List":["1"],"EfficientLengthIterable":["1"],"Iterable":["1"]},"ArrayIterator":{"Iterator":["1"]},"JSNumber":{"double":[],"num":[]},"JSInt":{"int":[],"double":[],"num":[]},"JSDouble":{"double":[],"num":[]},"JSString":{"String":[],"Pattern":[]},"_CastIterableBase":{"Iterable":["2"]},"CastIterator":{"Iterator":["2"]},"CastIterable":{"_CastIterableBase":["1","2"],"Iterable":["2"],"Iterable.E":"2"},"_EfficientLengthCastIterable":{"CastIterable":["1","2"],"EfficientLengthIterable":["2"],"_CastIterableBase":["1","2"],"Iterable":["2"],"Iterable.E":"2"},"CastMap":{"MapMixin":["3","4"],"Map":["3","4"],"MapMixin.K":"3","MapMixin.V":"4"},"CodeUnits":{"UnmodifiableListMixin":["int"],"ListMixin":["int"],"List":["int"],"EfficientLengthIterable":["int"],"Iterable":["int"],"ListMixin.E":"int","UnmodifiableListMixin.E":"int"},"EfficientLengthIterable":{"Iterable":["1"]},"ListIterable":{"EfficientLengthIterable":["1"],"Iterable":["1"]},"SubListIterable":{"ListIterable":["1"],"EfficientLengthIterable":["1"],"Iterable":["1"],"Iterable.E":"1","ListIterable.E":"1"},"ListIterator":{"Iterator":["1"]},"MappedIterable":{"Iterable":["2"],"Iterable.E":"2"},"EfficientLengthMappedIterable":{"MappedIterable":["1","2"],"EfficientLengthIterable":["2"],"Iterable":["2"],"Iterable.E":"2"},"MappedIterator":{"Iterator":["2"]},"MappedListIterable":{"ListIterable":["2"],"EfficientLengthIterable":["2"],"Iterable":["2"],"Iterable.E":"2","ListIterable.E":"2"},"WhereIterable":{"Iterable":["1"],"Iterable.E":"1"},"WhereIterator":{"Iterator":["1"]},"ExpandIterable":{"Iterable":["2"],"Iterable.E":"2"},"ExpandIterator":{"Iterator":["2"]},"SkipWhileIterable":{"Iterable":["1"],"Iterable.E":"1"},"SkipWhileIterator":{"Iterator":["1"]},"EmptyIterator":{"Iterator":["1"]},"UnmodifiableListBase":{"UnmodifiableListMixin":["1"],"ListMixin":["1"],"List":["1"],"EfficientLengthIterable":["1"],"Iterable":["1"]},"ReversedListIterable":{"ListIterable":["1"],"EfficientLengthIterable":["1"],"Iterable":["1"],"Iterable.E":"1","ListIterable.E":"1"},"ConstantMap":{"Map":["1","2"]},"ConstantStringMap":{"ConstantMap":["1","2"],"Map":["1","2"]},"_ConstantMapKeyIterable":{"Iterable":["1"],"Iterable.E":"1"},"Instantiation":{"Closure":[],"Function":[]},"Instantiation1":{"Closure":[],"Function":[]},"NullError":{"NoSuchMethodError":[],"Error":[]},"JsNoSuchMethodError":{"NoSuchMethodError":[],"Error":[]},"UnknownJsTypeError":{"Error":[]},"_StackTrace":{"StackTrace":[]},"Closure":{"Function":[]},"TearOffClosure":{"Closure":[],"Function":[]},"StaticClosure":{"Closure":[],"Function":[]},"BoundClosure":{"Closure":[],"Function":[]},"TypeErrorImplementation":{"Error":[]},"RuntimeError":{"Error":[]},"_AssertionError":{"Error":[]},"JsLinkedHashMap":{"LinkedHashMap":["1","2"],"MapMixin":["1","2"],"Map":["1","2"],"MapMixin.K":"1","MapMixin.V":"2"},"LinkedHashMapKeyIterable":{"EfficientLengthIterable":["1"],"Iterable":["1"],"Iterable.E":"1"},"LinkedHashMapKeyIterator":{"Iterator":["1"]},"JSSyntaxRegExp":{"RegExp":[],"Pattern":[]},"_MatchImplementation":{"RegExpMatch":[],"Match":[]},"_AllMatchesIterable":{"Iterable":["RegExpMatch"],"Iterable.E":"RegExpMatch"},"_AllMatchesIterator":{"Iterator":["RegExpMatch"]},"StringMatch":{"Match":[]},"_StringAllMatchesIterable":{"Iterable":["Match"],"Iterable.E":"Match"},"_StringAllMatchesIterator":{"Iterator":["Match"]},"NativeByteBuffer":{"ByteBuffer":[]},"NativeByteData":{"NativeTypedData":[]},"NativeTypedArray":{"JavaScriptIndexingBehavior":["@"],"NativeTypedData":[]},"NativeTypedArrayOfDouble":{"ListMixin":["double"],"JavaScriptIndexingBehavior":["@"],"List":["double"],"NativeTypedData":[],"EfficientLengthIterable":["double"],"FixedLengthListMixin":["double"],"Iterable":["double"]},"NativeTypedArrayOfInt":{"ListMixin":["int"],"List":["int"],"JavaScriptIndexingBehavior":["@"],"NativeTypedData":[],"EfficientLengthIterable":["int"],"FixedLengthListMixin":["int"],"Iterable":["int"]},"NativeFloat32List":{"ListMixin":["double"],"JavaScriptIndexingBehavior":["@"],"List":["double"],"NativeTypedData":[],"EfficientLengthIterable":["double"],"FixedLengthListMixin":["double"],"Iterable":["double"],"ListMixin.E":"double"},"NativeFloat64List":{"ListMixin":["double"],"JavaScriptIndexingBehavior":["@"],"List":["double"],"NativeTypedData":[],"EfficientLengthIterable":["double"],"FixedLengthListMixin":["double"],"Iterable":["double"],"ListMixin.E":"double"},"NativeInt16List":{"ListMixin":["int"],"List":["int"],"JavaScriptIndexingBehavior":["@"],"NativeTypedData":[],"EfficientLengthIterable":["int"],"FixedLengthListMixin":["int"],"Iterable":["int"],"ListMixin.E":"int"},"NativeInt32List":{"ListMixin":["int"],"List":["int"],"JavaScriptIndexingBehavior":["@"],"NativeTypedData":[],"EfficientLengthIterable":["int"],"FixedLengthListMixin":["int"],"Iterable":["int"],"ListMixin.E":"int"},"NativeInt8List":{"ListMixin":["int"],"List":["int"],"JavaScriptIndexingBehavior":["@"],"NativeTypedData":[],"EfficientLengthIterable":["int"],"FixedLengthListMixin":["int"],"Iterable":["int"],"ListMixin.E":"int"},"NativeUint16List":{"ListMixin":["int"],"List":["int"],"JavaScriptIndexingBehavior":["@"],"NativeTypedData":[],"EfficientLengthIterable":["int"],"FixedLengthListMixin":["int"],"Iterable":["int"],"ListMixin.E":"int"},"NativeUint32List":{"Uint32List":[],"ListMixin":["int"],"List":["int"],"JavaScriptIndexingBehavior":["@"],"NativeTypedData":[],"EfficientLengthIterable":["int"],"FixedLengthListMixin":["int"],"Iterable":["int"],"ListMixin.E":"int"},"NativeUint8ClampedList":{"ListMixin":["int"],"List":["int"],"JavaScriptIndexingBehavior":["@"],"NativeTypedData":[],"EfficientLengthIterable":["int"],"FixedLengthListMixin":["int"],"Iterable":["int"],"ListMixin.E":"int"},"NativeUint8List":{"Uint8List":[],"ListMixin":["int"],"List":["int"],"JavaScriptIndexingBehavior":["@"],"NativeTypedData":[],"EfficientLengthIterable":["int"],"FixedLengthListMixin":["int"],"Iterable":["int"],"ListMixin.E":"int"},"_Type":{"Type":[]},"_Error":{"Error":[]},"_CastError":{"Error":[]},"_TypeError":{"Error":[]},"_TimerImpl":{"Timer":[]},"_AsyncAwaitCompleter":{"Completer":["1"]},"_BroadcastStream":{"_ControllerStream":["1"],"_StreamImpl":["1"],"Stream":["1"],"Stream.T":"1"},"_BroadcastSubscription":{"_ControllerSubscription":["1"],"_BufferingStreamSubscription":["1"],"_EventDispatch":["1"],"StreamSubscription":["1"],"_BufferingStreamSubscription.T":"1"},"_BroadcastStreamController":{"StreamController":["1"],"StreamSink":["1"],"EventSink":["1"],"_EventDispatch":["1"],"_StreamControllerLifecycle":["1"],"StreamConsumer":["1"],"Sink":["1"]},"_SyncBroadcastStreamController":{"_BroadcastStreamController":["1"],"StreamController":["1"],"StreamSink":["1"],"EventSink":["1"],"_EventDispatch":["1"],"_StreamControllerLifecycle":["1"],"StreamConsumer":["1"],"Sink":["1"]},"_AsyncBroadcastStreamController":{"_BroadcastStreamController":["1"],"StreamController":["1"],"StreamSink":["1"],"EventSink":["1"],"_EventDispatch":["1"],"_StreamControllerLifecycle":["1"],"StreamConsumer":["1"],"Sink":["1"]},"TimeoutException":{"Exception":[]},"_Completer":{"Completer":["1"]},"_AsyncCompleter":{"_Completer":["1"],"Completer":["1"]},"_SyncCompleter":{"_Completer":["1"],"Completer":["1"]},"_Future":{"Future":["1"]},"StreamTransformerBase":{"StreamTransformer":["1","2"]},"_StreamController":{"StreamController":["1"],"StreamSink":["1"],"EventSink":["1"],"_EventDispatch":["1"],"_StreamControllerLifecycle":["1"],"StreamConsumer":["1"],"Sink":["1"]},"_AsyncStreamController":{"_AsyncStreamControllerDispatch":["1"],"_StreamController":["1"],"StreamController":["1"],"StreamSink":["1"],"EventSink":["1"],"_EventDispatch":["1"],"_StreamControllerLifecycle":["1"],"StreamConsumer":["1"],"Sink":["1"]},"_SyncStreamController":{"_SyncStreamControllerDispatch":["1"],"_StreamController":["1"],"StreamController":["1"],"StreamSink":["1"],"EventSink":["1"],"_EventDispatch":["1"],"_StreamControllerLifecycle":["1"],"StreamConsumer":["1"],"Sink":["1"]},"_ControllerStream":{"_StreamImpl":["1"],"Stream":["1"],"Stream.T":"1"},"_ControllerSubscription":{"_BufferingStreamSubscription":["1"],"_EventDispatch":["1"],"StreamSubscription":["1"],"_BufferingStreamSubscription.T":"1"},"_StreamSinkWrapper":{"StreamSink":["1"],"EventSink":["1"],"StreamConsumer":["1"],"Sink":["1"]},"_StreamControllerAddStreamState":{"_AddStreamState":["1"]},"_BufferingStreamSubscription":{"_EventDispatch":["1"],"StreamSubscription":["1"],"_BufferingStreamSubscription.T":"1"},"_StreamImpl":{"Stream":["1"]},"_GeneratedStreamImpl":{"_StreamImpl":["1"],"Stream":["1"],"Stream.T":"1"},"_IterablePendingEvents":{"_PendingEvents":["1"]},"_DelayedData":{"_DelayedEvent":["1"]},"_DelayedError":{"_DelayedEvent":["@"]},"_DelayedDone":{"_DelayedEvent":["@"]},"_StreamImplEvents":{"_PendingEvents":["1"]},"_DoneStreamSubscription":{"StreamSubscription":["1"]},"_EmptyStream":{"Stream":["1"],"Stream.T":"1"},"AsyncError":{"Error":[]},"_ZoneSpecification":{"ZoneSpecification":[]},"_ZoneDelegate":{"ZoneDelegate":[]},"_Zone":{"Zone":[]},"_CustomZone":{"_Zone":[],"Zone":[]},"_RootZone":{"_Zone":[],"Zone":[]},"_HashMap":{"MapMixin":["1","2"],"Map":["1","2"],"MapMixin.K":"1","MapMixin.V":"2"},"_IdentityHashMap":{"_HashMap":["1","2"],"MapMixin":["1","2"],"Map":["1","2"],"MapMixin.K":"1","MapMixin.V":"2"},"_HashMapKeyIterable":{"EfficientLengthIterable":["1"],"Iterable":["1"],"Iterable.E":"1"},"_HashMapKeyIterator":{"Iterator":["1"]},"_LinkedHashSet":{"_SetBase":["1"],"LinkedHashSet":["1"],"Set":["1"],"EfficientLengthIterable":["1"],"Iterable":["1"]},"_LinkedHashSetIterator":{"Iterator":["1"]},"UnmodifiableListView":{"UnmodifiableListMixin":["1"],"ListMixin":["1"],"List":["1"],"EfficientLengthIterable":["1"],"Iterable":["1"],"ListMixin.E":"1","UnmodifiableListMixin.E":"1"},"IterableBase":{"Iterable":["1"]},"ListBase":{"ListMixin":["1"],"List":["1"],"EfficientLengthIterable":["1"],"Iterable":["1"]},"MapBase":{"MapMixin":["1","2"],"Map":["1","2"]},"MapMixin":{"Map":["1","2"]},"MapView":{"Map":["1","2"]},"UnmodifiableMapView":{"_UnmodifiableMapView_MapView__UnmodifiableMapMixin":["1","2"],"MapView":["1","2"],"_UnmodifiableMapMixin":["1","2"],"Map":["1","2"]},"ListQueue":{"ListIterable":["1"],"Queue":["1"],"EfficientLengthIterable":["1"],"Iterable":["1"],"Iterable.E":"1","ListIterable.E":"1"},"_ListQueueIterator":{"Iterator":["1"]},"SetMixin":{"Set":["1"],"EfficientLengthIterable":["1"],"Iterable":["1"]},"SetBase":{"SetMixin":["1"],"Set":["1"],"EfficientLengthIterable":["1"],"Iterable":["1"]},"_SetBase":{"Set":["1"],"EfficientLengthIterable":["1"],"Iterable":["1"]},"_JsonMap":{"MapMixin":["String","@"],"Map":["String","@"],"MapMixin.K":"String","MapMixin.V":"@"},"_JsonMapKeyIterable":{"ListIterable":["String"],"EfficientLengthIterable":["String"],"Iterable":["String"],"Iterable.E":"String","ListIterable.E":"String"},"AsciiCodec":{"Codec":["String","List<int>"],"Codec.S":"String"},"_UnicodeSubsetEncoder":{"Converter":["String","List<int>"],"StreamTransformer":["String","List<int>"]},"AsciiEncoder":{"Converter":["String","List<int>"],"StreamTransformer":["String","List<int>"]},"Base64Codec":{"Codec":["List<int>","String"],"Codec.S":"List<int>"},"Base64Encoder":{"Converter":["List<int>","String"],"StreamTransformer":["List<int>","String"]},"_FusedCodec":{"Codec":["1","3"],"Codec.S":"1"},"Converter":{"StreamTransformer":["1","2"]},"Encoding":{"Codec":["String","List<int>"]},"JsonCodec":{"Codec":["Object","String"],"Codec.S":"Object"},"JsonDecoder":{"Converter":["String","Object"],"StreamTransformer":["String","Object"]},"Utf8Codec":{"Codec":["String","List<int>"],"Codec.S":"String"},"Utf8Encoder":{"Converter":["String","List<int>"],"StreamTransformer":["String","List<int>"]},"Utf8Decoder":{"Converter":["List<int>","String"],"StreamTransformer":["List<int>","String"]},"double":{"num":[]},"AssertionError":{"Error":[]},"NullThrownError":{"Error":[]},"ArgumentError":{"Error":[]},"RangeError":{"Error":[]},"IndexError":{"Error":[]},"UnsupportedError":{"Error":[]},"UnimplementedError":{"Error":[]},"StateError":{"Error":[]},"ConcurrentModificationError":{"Error":[]},"OutOfMemoryError":{"Error":[]},"StackOverflowError":{"Error":[]},"CyclicInitializationError":{"Error":[]},"_Exception":{"Exception":[]},"FormatException":{"Exception":[]},"int":{"num":[]},"List":{"EfficientLengthIterable":["1"],"Iterable":["1"]},"RegExpMatch":{"Match":[]},"Set":{"EfficientLengthIterable":["1"],"Iterable":["1"]},"_StringStackTrace":{"StackTrace":[]},"String":{"Pattern":[]},"Runes":{"Iterable":["int"],"Iterable.E":"int"},"RuneIterator":{"Iterator":["int"]},"StringBuffer":{"StringSink":[]},"_Uri":{"Uri":[]},"_SimpleUri":{"Uri":[]},"_DataUri":{"Uri":[]},"ApplicationCacheErrorEvent":{"Event":[]},"ErrorEvent":{"Event":[]},"File":{"Blob":[]},"MediaKeyMessageEvent":{"Event":[]},"MessageEvent":{"Event":[]},"MessagePort":{"EventTarget":[]},"PresentationConnectionCloseEvent":{"Event":[]},"SpeechRecognitionError":{"Event":[]},"_EventStream":{"Stream":["1"],"Stream.T":"1"},"_EventStreamSubscription":{"StreamSubscription":["1"]},"Int8List":{"List":["int"],"EfficientLengthIterable":["int"],"Iterable":["int"]},"Uint8List":{"List":["int"],"EfficientLengthIterable":["int"],"Iterable":["int"]},"Uint8ClampedList":{"List":["int"],"EfficientLengthIterable":["int"],"Iterable":["int"]},"Int16List":{"List":["int"],"EfficientLengthIterable":["int"],"Iterable":["int"]},"Uint16List":{"List":["int"],"EfficientLengthIterable":["int"],"Iterable":["int"]},"Int32List":{"List":["int"],"EfficientLengthIterable":["int"],"Iterable":["int"]},"Uint32List":{"List":["int"],"EfficientLengthIterable":["int"],"Iterable":["int"]},"Float32List":{"List":["double"],"EfficientLengthIterable":["double"],"Iterable":["double"]},"Float64List":{"List":["double"],"EfficientLengthIterable":["double"],"Iterable":["double"]},"DelegatingSink":{"Sink":["1"]},"DelegatingStreamSubscription":{"StreamSubscription":["1"]},"FutureGroup":{"Sink":["Future<1>"]},"NullStreamSink":{"StreamSink":["1"],"EventSink":["1"],"StreamConsumer":["1"],"Sink":["1"]},"ErrorResult":{"Result":["Null"]},"ValueResult":{"Result":["1"]},"_CompleterStream":{"Stream":["1"],"Stream.T":"1"},"StreamGroup":{"Sink":["Stream<1>"]},"_NextRequest":{"_EventRequest":["1"]},"_RestRequest":{"_EventRequest":["1"]},"_CompleterSink":{"StreamSink":["1"],"EventSink":["1"],"StreamConsumer":["1"],"Sink":["1"]},"SubscriptionStream":{"Stream":["1"],"Stream.T":"1"},"_CancelOnErrorSubscriptionWrapper":{"DelegatingStreamSubscription":["1"],"StreamSubscription":["1"]},"All":{"BooleanSelector":[]},"VariableNode":{"Node":[]},"NotNode":{"Node":[]},"OrNode":{"Node":[]},"AndNode":{"Node":[]},"ConditionalNode":{"Node":[]},"Evaluator":{"Visitor":["bool"]},"BooleanSelectorImpl":{"BooleanSelector":[]},"IntersectionSelector":{"BooleanSelector":[]},"None":{"BooleanSelector":[]},"IdentifierToken":{"Token":[]},"Validator":{"Visitor":["@"]},"RecursiveVisitor":{"Visitor":["@"]},"EmptyUnmodifiableSet":{"Set":["1"],"EfficientLengthIterable":["1"],"Iterable":["1"],"Iterable.E":"1"},"QueueList":{"ListMixin":["1"],"Queue":["1"],"List":["1"],"EfficientLengthIterable":["1"],"Iterable":["1"],"ListMixin.E":"1"},"UnionSet":{"UnmodifiableSetMixin":["1"],"SetMixin":["1"],"Set":["1"],"EfficientLengthIterable":["1"],"Iterable":["1"]},"UnmodifiableSetView":{"_UnmodifiableSetView_DelegatingSet_UnmodifiableSetMixin":["1"],"DelegatingSet":["1"],"UnmodifiableSetMixin":["1"],"DelegatingIterable":["1"],"Set":["1"],"_DelegatingIterableBase":["1"],"EfficientLengthIterable":["1"],"Iterable":["1"]},"_DelegatingIterableBase":{"Iterable":["1"]},"DelegatingIterable":{"_DelegatingIterableBase":["1"],"Iterable":["1"]},"DelegatingSet":{"DelegatingIterable":["1"],"Set":["1"],"_DelegatingIterableBase":["1"],"EfficientLengthIterable":["1"],"Iterable":["1"]},"_IsTrue":{"Matcher":[]},"_Predicate":{"FeatureMatcher":["1"],"TypeMatcher":["1"],"Matcher":[],"TypeMatcher.T":"1","FeatureMatcher.T":"1"},"StringDescription":{"Description":[]},"_StringEqualsMatcher":{"FeatureMatcher":["String"],"TypeMatcher":["String"],"Matcher":[],"TypeMatcher.T":"String","FeatureMatcher.T":"String"},"_DeepMatcher":{"Matcher":[]},"FeatureMatcher":{"TypeMatcher":["1"],"Matcher":[]},"TypeMatcher":{"Matcher":[],"TypeMatcher.T":"1"},"PackageConfigResolver":{"SyncPackageResolver":[]},"PackageRootResolver":{"SyncPackageResolver":[]},"PathException":{"Exception":[]},"PosixStyle":{"InternalStyle":[]},"UrlStyle":{"InternalStyle":[]},"WindowsStyle":{"InternalStyle":[]},"MultiSectionMapping":{"Mapping":[]},"MappingBundle":{"Mapping":[]},"SingleMapping":{"Mapping":[]},"_MappingTokenizer":{"Iterator":["String"]},"SourceMapSpan":{"SourceSpan":[]},"FileLocation":{"SourceLocation":[]},"_FileSpan":{"FileSpan":[],"SourceSpanWithContext":[],"SourceSpan":[]},"SourceLocationMixin":{"SourceLocation":[]},"SourceSpanBase":{"SourceSpan":[]},"SourceSpanException":{"Exception":[]},"SourceSpanFormatException":{"FormatException":[],"Exception":[]},"SourceSpanMixin":{"SourceSpan":[]},"SourceSpanWithContext":{"SourceSpan":[]},"Chain":{"StackTrace":[]},"LazyChain":{"Chain":[],"StackTrace":[]},"LazyTrace":{"Trace":[],"StackTrace":[]},"Trace":{"StackTrace":[]},"UnparsedFrame":{"Frame":[]},"GuaranteeChannel":{"StreamChannelMixin":["1"],"StreamChannel":["1"]},"_GuaranteeSink":{"StreamSink":["1"],"EventSink":["1"],"StreamConsumer":["1"],"Sink":["1"]},"_MultiChannel":{"StreamChannelMixin":["1"],"MultiChannel":["1"],"StreamChannel":["1"]},"VirtualChannel":{"StreamChannelMixin":["1"],"MultiChannel":["1"],"StreamChannel":["1"]},"_StreamChannel":{"StreamChannelMixin":["1"],"StreamChannel":["1"]},"StreamChannelMixin":{"StreamChannel":["1"]},"StringScannerException":{"FormatException":[],"Exception":[]},"_SpanScannerState":{"LineScannerState":[]},"ClosedException":{"Exception":[]},"Group":{"GroupEntry":[]},"LocalTest":{"Test":[],"GroupEntry":[]},"_LiveTest":{"LiveTest":[]},"Test":{"GroupEntry":[]},"IterableSet":{"SetMixin":["1"],"UnmodifiableSetMixin":["1"],"Set":["1"],"EfficientLengthIterable":["1"],"Iterable":["1"]},"_LiveSuite":{"LiveSuite":[]},"RunnerSuite":{"Suite":[]},"PrintSink":{"StringSink":[]},"JSStackTraceMapper":{"StackTraceMapper":[]}}'));
+  H._Universe_addErasedTypes(init.typeUniverse, JSON.parse('{"UnmodifiableListBase":1,"StreamTransformerBase":2,"IterableBase":1,"ListBase":1,"MapBase":2,"SetBase":1,"_ListBase_Object_ListMixin":1,"_SetBase_Object_SetMixin":1,"_QueueList_Object_ListMixin":1,"_UnionSet_SetBase_UnmodifiableSetMixin":1,"_IterableSet_SetMixin_UnmodifiableSetMixin":1}'));
+  var type$ = (function rtii() {
+    var findType = H.findType;
+    return {
+      A_Function_2_B_and_C_Function_A_and_B_and_C_4_Zone_and_ZoneDelegate_and_Zone_and_A_Function_2_B_and_C: findType("0^(1^,2^)(Zone,ZoneDelegate,Zone,0^(1^,2^))<Object,Object,Object>"),
+      A_Function_A_4_Zone_and_ZoneDelegate_and_Zone_and_A_Function: findType("0^(Zone,ZoneDelegate,Zone,0^())<Object>"),
+      A_Function_A_and_B_5_Zone_and_ZoneDelegate_and_Zone_and_A_Function_B_and_B: findType("0^(Zone,ZoneDelegate,Zone,0^(1^),1^)<Object,Object>"),
+      A_Function_A_and_B_and_C_6_Zone_and_ZoneDelegate_and_Zone_and_A_Function_2_B_and_C_and_B_and_C: findType("0^(Zone,ZoneDelegate,Zone,0^(1^,2^),1^,2^)<Object,Object,Object>"),
+      A_Function_B_Function_A_and_B_4_Zone_and_ZoneDelegate_and_Zone_and_A_Function_B: findType("0^(1^)(Zone,ZoneDelegate,Zone,0^(1^))<Object,Object>"),
+      A_Function_Function_A_4_Zone_and_ZoneDelegate_and_Zone_and_A_Function: findType("0^()(Zone,ZoneDelegate,Zone,0^())<Object>"),
+      AsyncError: findType("AsyncError"),
+      AsyncMemoizer_dynamic: findType("AsyncMemoizer<@>"),
+      Blob: findType("Blob"),
+      BooleanSelector: findType("BooleanSelector"),
+      Chain: findType("Chain"),
+      CodeUnits: findType("CodeUnits"),
+      Completer_PoolResource: findType("Completer<PoolResource>"),
+      Declarer: findType("Declarer"),
+      Duration: findType("Duration"),
+      EfficientLengthIterable_dynamic: findType("EfficientLengthIterable<@>"),
+      Error: findType("Error"),
+      Event: findType("Event"),
+      Exception: findType("Exception"),
+      Expando__Node: findType("Expando<_Node>"),
+      File: findType("File"),
+      FileSpan: findType("FileSpan"),
+      FormatException: findType("FormatException"),
+      Frame: findType("Frame"),
+      Frame_Function_Frame: findType("Frame(Frame)"),
+      Frame_Function_String: findType("Frame(String)"),
+      Function: findType("Function"),
+      FutureGroup_dynamic: findType("FutureGroup<@>"),
+      FutureOr_void_Function: findType("~/()"),
+      Future_Null: findType("Future<Null>"),
+      Future_RunnerSuite: findType("Future<RunnerSuite>"),
+      Future_bool: findType("Future<bool>"),
+      Future_dynamic: findType("Future<@>"),
+      Future_void: findType("Future<~>"),
+      Group: findType("Group"),
+      GroupEntry: findType("GroupEntry"),
+      GroupEntry_Function_GroupEntry: findType("GroupEntry(GroupEntry)"),
+      IdentifierToken: findType("IdentifierToken"),
+      Invoker: findType("Invoker"),
+      IterableSet_LiveTest: findType("IterableSet<LiveTest>"),
+      Iterable_Group: findType("Iterable<Group>"),
+      Iterable_String: findType("Iterable<String>"),
+      Iterable_dynamic: findType("Iterable<@>"),
+      Iterator_Match: findType("Iterator<Match>"),
+      JSArray_AsyncError: findType("JSArray<AsyncError>"),
+      JSArray_Declarer: findType("JSArray<Declarer>"),
+      JSArray_Frame: findType("JSArray<Frame>"),
+      JSArray_Future_dynamic: findType("JSArray<Future<@>>"),
+      JSArray_Group: findType("JSArray<Group>"),
+      JSArray_GroupEntry: findType("JSArray<GroupEntry>"),
+      JSArray_Mapping: findType("JSArray<Mapping>"),
+      JSArray_Set_LiveTest: findType("JSArray<Set<LiveTest>>"),
+      JSArray_SourceFile: findType("JSArray<SourceFile>"),
+      JSArray_String: findType("JSArray<String>"),
+      JSArray_TargetEntry: findType("JSArray<TargetEntry>"),
+      JSArray_TargetLineEntry: findType("JSArray<TargetLineEntry>"),
+      JSArray_Trace: findType("JSArray<Trace>"),
+      JSArray_Zone: findType("JSArray<Zone>"),
+      JSArray_dynamic: findType("JSArray<@>"),
+      JSArray_int: findType("JSArray<int>"),
+      JSArray_of_dynamic_Function: findType("JSArray<@()>"),
+      JSObject: findType("JSObject"),
+      JavaScriptFunction: findType("JavaScriptFunction"),
+      JavaScriptIndexingBehavior_dynamic: findType("JavaScriptIndexingBehavior<@>"),
+      JsLinkedHashMap_of_Stream_LiveTest_and_StreamSubscription_LiveTest: findType("JsLinkedHashMap<Stream<LiveTest>,StreamSubscription<LiveTest>>"),
+      List_Group: findType("List<Group>"),
+      List_Object: findType("List<Object>"),
+      List_String: findType("List<String>"),
+      List_String_Function_dynamic_dynamic_String_int: findType("List<String>(@,@,String,int)"),
+      List_dynamic: findType("List<@>"),
+      List_int: findType("List<int>"),
+      LiveSuite: findType("LiveSuite"),
+      LiveTest: findType("LiveTest"),
+      MapEntry_BooleanSelector_Metadata: findType("MapEntry<BooleanSelector,Metadata>"),
+      MapEntry_String_Uri: findType("MapEntry<String,Uri>"),
+      MapEntry_of_String_and_Map_String_dynamic: findType("MapEntry<String,Map<String,@>>"),
+      Map_BooleanSelector_Metadata: findType("Map<BooleanSelector,Metadata>"),
+      Map_PlatformSelector_Metadata: findType("Map<PlatformSelector,Metadata>"),
+      Map_String_SourceFile: findType("Map<String,SourceFile>"),
+      Map_String_dynamic: findType("Map<String,@>"),
+      Map_dynamic_dynamic: findType("Map<@,@>"),
+      MappedIterable_String_Frame: findType("MappedIterable<String,Frame>"),
+      MappedListIterable_Frame_Frame: findType("MappedListIterable<Frame,Frame>"),
+      MappedListIterable_String_String: findType("MappedListIterable<String,String>"),
+      MappedListIterable_String_Trace: findType("MappedListIterable<String,Trace>"),
+      MappedListIterable_String_dynamic: findType("MappedListIterable<String,@>"),
+      Message: findType("Message"),
+      MessageEvent: findType("MessageEvent"),
+      MessagePort: findType("MessagePort"),
+      Metadata: findType("Metadata"),
+      NativeByteBuffer: findType("NativeByteBuffer"),
+      NativeTypedData: findType("NativeTypedData"),
+      NativeUint8List: findType("NativeUint8List"),
+      NoSuchMethodError: findType("NoSuchMethodError"),
+      Null: findType("Null"),
+      Null_Function: findType("Null()"),
+      Object: findType("Object"),
+      OperatingSystem: findType("OperatingSystem"),
+      Pattern: findType("Pattern"),
+      PlatformSelector: findType("PlatformSelector"),
+      RegExp: findType("RegExp"),
+      Result_dynamic: findType("Result<@>"),
+      ReversedListIterable_Declarer: findType("ReversedListIterable<Declarer>"),
+      RunnerSuite: findType("RunnerSuite"),
+      Runtime: findType("Runtime"),
+      Set_LiveTest: findType("Set<LiveTest>"),
+      Set_String: findType("Set<String>"),
+      Set_dynamic: findType("Set<@>"),
+      SingleMapping: findType("SingleMapping"),
+      SourceLocation: findType("SourceLocation"),
+      SourceSpan: findType("SourceSpan"),
+      SourceSpanWithContext: findType("SourceSpanWithContext"),
+      StackTrace: findType("StackTrace"),
+      StackTraceFormatter: findType("StackTraceFormatter"),
+      StackZoneSpecification: findType("StackZoneSpecification"),
+      State: findType("State"),
+      StreamChannelCompleter_dynamic: findType("StreamChannelCompleter<@>"),
+      StreamChannel_dynamic: findType("StreamChannel<@>"),
+      StreamCompleter_dynamic: findType("StreamCompleter<@>"),
+      StreamGroup_LiveTest: findType("StreamGroup<LiveTest>"),
+      StreamQueue_dynamic: findType("StreamQueue<@>"),
+      StreamSinkCompleter_dynamic: findType("StreamSinkCompleter<@>"),
+      StreamSubscription_dynamic: findType("StreamSubscription<@>"),
+      String: findType("String"),
+      String_Function_Match: findType("String(Match)"),
+      String_Function_String: findType("String(String)"),
+      SuiteChannelManager: findType("SuiteChannelManager"),
+      Test: findType("Test"),
+      Timer: findType("Timer"),
+      Trace: findType("Trace"),
+      Trace_Function_String: findType("Trace(String)"),
+      Type: findType("Type"),
+      Uint8List: findType("Uint8List"),
+      UnionSet_LiveTest: findType("UnionSet<LiveTest>"),
+      UnknownJavaScriptObject: findType("UnknownJavaScriptObject"),
+      UnmodifiableListView_LiveTest: findType("UnmodifiableListView<LiveTest>"),
+      UnmodifiableMapView_BooleanSelector_Metadata: findType("UnmodifiableMapView<BooleanSelector,Metadata>"),
+      UnmodifiableMapView_PlatformSelector_Metadata: findType("UnmodifiableMapView<PlatformSelector,Metadata>"),
+      UnmodifiableMapView_String_Uri: findType("UnmodifiableMapView<String,Uri>"),
+      UnmodifiableSetView_LiveTest: findType("UnmodifiableSetView<LiveTest>"),
+      UnmodifiableSetView_String: findType("UnmodifiableSetView<String>"),
+      Uri: findType("Uri"),
+      WhereIterable_String: findType("WhereIterable<String>"),
+      Zone: findType("Zone"),
+      ZoneDelegate: findType("ZoneDelegate"),
+      ZoneSpecification: findType("ZoneSpecification"),
+      _AsyncBroadcastStreamController_LiveSuite: findType("_AsyncBroadcastStreamController<LiveSuite>"),
+      _AsyncBroadcastStreamController_RunnerSuite: findType("_AsyncBroadcastStreamController<RunnerSuite>"),
+      _AsyncBroadcastStreamController_bool: findType("_AsyncBroadcastStreamController<bool>"),
+      _AsyncCompleter_List_dynamic: findType("_AsyncCompleter<List<@>>"),
+      _AsyncCompleter_PoolResource: findType("_AsyncCompleter<PoolResource>"),
+      _AsyncCompleter_dynamic: findType("_AsyncCompleter<@>"),
+      _AsyncCompleter_void: findType("_AsyncCompleter<~>"),
+      _AsyncCounter: findType("_AsyncCounter"),
+      _CompleterSink_dynamic: findType("_CompleterSink<@>"),
+      _CompleterStream_dynamic: findType("_CompleterStream<@>"),
+      _DelayedEvent_dynamic: findType("_DelayedEvent<@>"),
+      _EventRequest_dynamic: findType("_EventRequest<@>"),
+      _EventStream_MessageEvent: findType("_EventStream<MessageEvent>"),
+      _FutureListener_dynamic_dynamic: findType("_FutureListener<@,@>"),
+      _Future_List_dynamic: findType("_Future<List<@>>"),
+      _Future_PoolResource: findType("_Future<PoolResource>"),
+      _Future_RunnerSuite: findType("_Future<RunnerSuite>"),
+      _Future_dynamic: findType("_Future<@>"),
+      _Future_int: findType("_Future<int>"),
+      _Future_void: findType("_Future<~>"),
+      _IdentityHashMap_dynamic_dynamic: findType("_IdentityHashMap<@,@>"),
+      _LinkedHashSetCell: findType("_LinkedHashSetCell"),
+      _Node: findType("_Node"),
+      _Predicate_Object: findType("_Predicate<Object>"),
+      _Predicate_dynamic: findType("_Predicate<@>"),
+      _RestRequest_dynamic: findType("_RestRequest<@>"),
+      _StreamChannel_dynamic: findType("_StreamChannel<@>"),
+      _SyncBroadcastStreamController_AsyncError: findType("_SyncBroadcastStreamController<AsyncError>"),
+      _SyncBroadcastStreamController_LiveTest: findType("_SyncBroadcastStreamController<LiveTest>"),
+      _SyncBroadcastStreamController_Message: findType("_SyncBroadcastStreamController<Message>"),
+      _SyncBroadcastStreamController_State: findType("_SyncBroadcastStreamController<State>"),
+      _SyncCompleter_PoolResource: findType("_SyncCompleter<PoolResource>"),
+      _SyncCompleter_dynamic: findType("_SyncCompleter<@>"),
+      _ZoneFunction_Function: findType("_ZoneFunction<Function>"),
+      _ZoneFunction_of_AsyncError_Function_Zone_ZoneDelegate_Zone_Object_StackTrace: findType("_ZoneFunction<AsyncError(Zone,ZoneDelegate,Zone,Object,StackTrace)>"),
+      _ZoneFunction_of_Timer_Function_5_Zone_and_ZoneDelegate_and_Zone_and_Duration_and_void_Function: findType("_ZoneFunction<Timer(Zone,ZoneDelegate,Zone,Duration,~())>"),
+      _ZoneFunction_of_Timer_Function_5_Zone_and_ZoneDelegate_and_Zone_and_Duration_and_void_Function_Timer: findType("_ZoneFunction<Timer(Zone,ZoneDelegate,Zone,Duration,~(Timer))>"),
+      _ZoneFunction_of_Zone_Function_5_Zone_and_ZoneDelegate_and_Zone_and_ZoneSpecification_and_Map_dynamic_dynamic: findType("_ZoneFunction<Zone(Zone,ZoneDelegate,Zone,ZoneSpecification,Map<@,@>)>"),
+      _ZoneFunction_of_void_Function_4_Zone_and_ZoneDelegate_and_Zone_and_void_Function: findType("_ZoneFunction<~(Zone,ZoneDelegate,Zone,~())>"),
+      _ZoneFunction_of_void_Function_Zone_ZoneDelegate_Zone_Object_StackTrace: findType("_ZoneFunction<~(Zone,ZoneDelegate,Zone,Object,StackTrace)>"),
+      _ZoneFunction_of_void_Function_Zone_ZoneDelegate_Zone_String: findType("_ZoneFunction<~(Zone,ZoneDelegate,Zone,String)>"),
+      bool: findType("bool"),
+      bool_Function_Frame: findType("bool(Frame)"),
+      bool_Function_Null: findType("bool(Null)"),
+      bool_Function_Object: findType("bool(Object)"),
+      bool_Function_String: findType("bool(String)"),
+      bool_Function_dynamic: findType("bool(@)"),
+      dynamic: findType("@"),
+      dynamic_Function: findType("@()"),
+      dynamic_Function_Event: findType("@(Event)"),
+      dynamic_Function_Object: findType("@(Object)"),
+      dynamic_Function_Object_Object: findType("@(Object,Object)"),
+      dynamic_Function_Object_StackTrace: findType("@(Object,StackTrace)"),
+      dynamic_Function_String: findType("@(String)"),
+      dynamic_Function_dynamic_dynamic: findType("@(@,@)"),
+      int: findType("int"),
+      num: findType("num"),
+      void: findType("~"),
+      void_Function: findType("~()"),
+      void_Function_MessageEvent: findType("~(MessageEvent)"),
+      void_Function_Object: findType("~(Object)"),
+      void_Function_Object_StackTrace: findType("~(Object,StackTrace)"),
+      void_Function_String_dynamic: findType("~(String,@)"),
+      void_Function_Timer: findType("~(Timer)")
+    };
+  })();
+  (function constants() {
+    var makeConstList = hunkHelpers.makeConstList;
+    C.Interceptor_methods = J.Interceptor.prototype;
+    C.JSArray_methods = J.JSArray.prototype;
+    C.JSInt_methods = J.JSInt.prototype;
+    C.JSNumber_methods = J.JSNumber.prototype;
+    C.JSString_methods = J.JSString.prototype;
+    C.JavaScriptFunction_methods = J.JavaScriptFunction.prototype;
+    C.Location_methods = W.Location.prototype;
+    C.MessagePort_methods = W.MessagePort.prototype;
+    C.NativeUint32List_methods = H.NativeUint32List.prototype;
+    C.NativeUint8List_methods = H.NativeUint8List.prototype;
+    C.PlainJavaScriptObject_methods = J.PlainJavaScriptObject.prototype;
+    C.UnknownJavaScriptObject_methods = J.UnknownJavaScriptObject.prototype;
+    C.AsciiEncoder_127 = new P.AsciiEncoder(127);
+    C.List_empty = H.setRuntimeTypeInfo(makeConstList([]), type$.JSArray_String);
+    C.C_All = new X.All();
+    C.C_AsciiCodec = new P.AsciiCodec();
+    C.C_AsciiGlyphSet = new A.AsciiGlyphSet();
+    C.C_Base64Encoder = new P.Base64Encoder();
+    C.C_Base64Codec = new P.Base64Codec();
+    C.C_EmptyIterator = new H.EmptyIterator(H.findType("EmptyIterator<Null>"));
+    C.C_EmptyUnmodifiableSet = new O.EmptyUnmodifiableSet(H.findType("EmptyUnmodifiableSet<String>"));
+    C.C_JS_CONST = function getTagFallback(o) {
+  var s = Object.prototype.toString.call(o);
+  return s.substring(8, s.length - 1);
+};
+    C.C_JS_CONST0 = function() {
+  var toStringFunction = Object.prototype.toString;
+  function getTag(o) {
+    var s = toStringFunction.call(o);
+    return s.substring(8, s.length - 1);
+  }
+  function getUnknownTag(object, tag) {
+    if (/^HTML[A-Z].*Element$/.test(tag)) {
+      var name = toStringFunction.call(object);
+      if (name == "[object Object]") return null;
+      return "HTMLElement";
+    }
+  }
+  function getUnknownTagGenericBrowser(object, tag) {
+    if (self.HTMLElement && object instanceof HTMLElement) return "HTMLElement";
+    return getUnknownTag(object, tag);
+  }
+  function prototypeForTag(tag) {
+    if (typeof window == "undefined") return null;
+    if (typeof window[tag] == "undefined") return null;
+    var constructor = window[tag];
+    if (typeof constructor != "function") return null;
+    return constructor.prototype;
+  }
+  function discriminator(tag) { return null; }
+  var isBrowser = typeof navigator == "object";
+  return {
+    getTag: getTag,
+    getUnknownTag: isBrowser ? getUnknownTagGenericBrowser : getUnknownTag,
+    prototypeForTag: prototypeForTag,
+    discriminator: discriminator };
+};
+    C.C_JS_CONST6 = function(getTagFallback) {
+  return function(hooks) {
+    if (typeof navigator != "object") return hooks;
+    var ua = navigator.userAgent;
+    if (ua.indexOf("DumpRenderTree") >= 0) return hooks;
+    if (ua.indexOf("Chrome") >= 0) {
+      function confirm(p) {
+        return typeof window == "object" && window[p] && window[p].name == p;
+      }
+      if (confirm("Window") && confirm("HTMLElement")) return hooks;
+    }
+    hooks.getTag = getTagFallback;
+  };
+};
+    C.C_JS_CONST1 = function(hooks) {
+  if (typeof dartExperimentalFixupGetTag != "function") return hooks;
+  hooks.getTag = dartExperimentalFixupGetTag(hooks.getTag);
+};
+    C.C_JS_CONST2 = function(hooks) {
+  var getTag = hooks.getTag;
+  var prototypeForTag = hooks.prototypeForTag;
+  function getTagFixed(o) {
+    var tag = getTag(o);
+    if (tag == "Document") {
+      if (!!o.xmlVersion) return "!Document";
+      return "!HTMLDocument";
+    }
+    return tag;
+  }
+  function prototypeForTagFixed(tag) {
+    if (tag == "Document") return null;
+    return prototypeForTag(tag);
+  }
+  hooks.getTag = getTagFixed;
+  hooks.prototypeForTag = prototypeForTagFixed;
+};
+    C.C_JS_CONST5 = function(hooks) {
+  var userAgent = typeof navigator == "object" ? navigator.userAgent : "";
+  if (userAgent.indexOf("Firefox") == -1) return hooks;
+  var getTag = hooks.getTag;
+  var quickMap = {
+    "BeforeUnloadEvent": "Event",
+    "DataTransfer": "Clipboard",
+    "GeoGeolocation": "Geolocation",
+    "Location": "!Location",
+    "WorkerMessageEvent": "MessageEvent",
+    "XMLDocument": "!Document"};
+  function getTagFirefox(o) {
+    var tag = getTag(o);
+    return quickMap[tag] || tag;
+  }
+  hooks.getTag = getTagFirefox;
+};
+    C.C_JS_CONST4 = function(hooks) {
+  var userAgent = typeof navigator == "object" ? navigator.userAgent : "";
+  if (userAgent.indexOf("Trident/") == -1) return hooks;
+  var getTag = hooks.getTag;
+  var quickMap = {
+    "BeforeUnloadEvent": "Event",
+    "DataTransfer": "Clipboard",
+    "HTMLDDElement": "HTMLElement",
+    "HTMLDTElement": "HTMLElement",
+    "HTMLPhraseElement": "HTMLElement",
+    "Position": "Geoposition"
+  };
+  function getTagIE(o) {
+    var tag = getTag(o);
+    var newTag = quickMap[tag];
+    if (newTag) return newTag;
+    if (tag == "Object") {
+      if (window.DataView && (o instanceof window.DataView)) return "DataView";
+    }
+    return tag;
+  }
+  function prototypeForTagIE(tag) {
+    var constructor = window[tag];
+    if (constructor == null) return null;
+    return constructor.prototype;
+  }
+  hooks.getTag = getTagIE;
+  hooks.prototypeForTag = prototypeForTagIE;
+};
+    C.C_JS_CONST3 = function(hooks) { return hooks; }
+;
+    C.C_JsonCodec = new P.JsonCodec();
+    C.C_None = new O.None();
+    C.C_OutOfMemoryError = new P.OutOfMemoryError();
+    C.C_UnicodeGlyphSet = new K.UnicodeGlyphSet();
+    C.C_Utf8Codec = new P.Utf8Codec();
+    C.C_Utf8Encoder = new P.Utf8Encoder();
+    C.C__DelayedDone = new P._DelayedDone();
+    C.C__IsTrue = new Y._IsTrue();
+    C.C__RootZone = new P._RootZone();
+    C.Duration_0 = new P.Duration(0);
+    C.Duration_30000000 = new P.Duration(30000000);
+    C.JsonDecoder_null = new P.JsonDecoder(null);
+    C.List_127_2047_65535_1114111 = H.setRuntimeTypeInfo(makeConstList([127, 2047, 65535, 1114111]), type$.JSArray_int);
+    C.List_2Vk = H.setRuntimeTypeInfo(makeConstList([0, 0, 32776, 33792, 1, 10240, 0, 0]), type$.JSArray_int);
+    C.List_CVk = H.setRuntimeTypeInfo(makeConstList([0, 0, 65490, 45055, 65535, 34815, 65534, 18431]), type$.JSArray_int);
+    C.List_JYB = H.setRuntimeTypeInfo(makeConstList([0, 0, 26624, 1023, 65534, 2047, 65534, 2047]), type$.JSArray_int);
+    C.List_empty1 = H.setRuntimeTypeInfo(makeConstList([]), H.findType("JSArray<Null>"));
+    C.List_empty0 = H.setRuntimeTypeInfo(makeConstList([]), type$.JSArray_dynamic);
+    C.List_gRj = H.setRuntimeTypeInfo(makeConstList([0, 0, 32722, 12287, 65534, 34815, 65534, 18431]), type$.JSArray_int);
+    C.Runtime_ql0 = new B.Runtime("VM", "vm", null, true, false, false, false, false);
+    C.Runtime_4e8 = new B.Runtime("Chrome", "chrome", null, false, true, true, true, false);
+    C.Runtime_IBZ = new B.Runtime("PhantomJS", "phantomjs", null, false, true, true, true, true);
+    C.Runtime_8Rg = new B.Runtime("Firefox", "firefox", null, false, true, true, false, false);
+    C.Runtime_ivT = new B.Runtime("Safari", "safari", null, false, true, true, false, false);
+    C.Runtime_Mzn = new B.Runtime("Internet Explorer", "ie", null, false, true, true, false, false);
+    C.Runtime_R5O = new B.Runtime("Node.js", "node", null, false, false, true, false, false);
+    C.List_m7e = H.setRuntimeTypeInfo(makeConstList([C.Runtime_ql0, C.Runtime_4e8, C.Runtime_IBZ, C.Runtime_8Rg, C.Runtime_ivT, C.Runtime_Mzn, C.Runtime_R5O]), H.findType("JSArray<Runtime>"));
+    C.List_nxB = H.setRuntimeTypeInfo(makeConstList([0, 0, 24576, 1023, 65534, 34815, 65534, 18431]), type$.JSArray_int);
+    C.OperatingSystem_Windows_windows = new N.OperatingSystem("Windows", "windows");
+    C.OperatingSystem_RkP = new N.OperatingSystem("OS X", "mac-os");
+    C.OperatingSystem_Linux_linux = new N.OperatingSystem("Linux", "linux");
+    C.OperatingSystem_Android_android = new N.OperatingSystem("Android", "android");
+    C.OperatingSystem_iOS_ios = new N.OperatingSystem("iOS", "ios");
+    C.List_opx = H.setRuntimeTypeInfo(makeConstList([C.OperatingSystem_Windows_windows, C.OperatingSystem_RkP, C.OperatingSystem_Linux_linux, C.OperatingSystem_Android_android, C.OperatingSystem_iOS_ios]), H.findType("JSArray<OperatingSystem>"));
+    C.List_qFt = H.setRuntimeTypeInfo(makeConstList([0, 0, 27858, 1023, 65534, 51199, 65535, 32767]), type$.JSArray_int);
+    C.List_qNA = H.setRuntimeTypeInfo(makeConstList([0, 0, 32754, 11263, 65534, 34815, 65534, 18431]), type$.JSArray_int);
+    C.List_qg40 = H.setRuntimeTypeInfo(makeConstList([0, 0, 32722, 12287, 65535, 34815, 65534, 18431]), type$.JSArray_int);
+    C.List_qg4 = H.setRuntimeTypeInfo(makeConstList([0, 0, 65490, 12287, 65535, 34815, 65534, 18431]), type$.JSArray_int);
+    C.List_F9h = H.setRuntimeTypeInfo(makeConstList(["\n", "\r", "\f", "\b", "\t", "\v", "\x7f"]), type$.JSArray_String);
+    C.Map_F9GZw = new H.ConstantStringMap(7, {"\n": "\\n", "\r": "\\r", "\f": "\\f", "\b": "\\b", "\t": "\\t", "\v": "\\v", "\x7f": "\\x7F"}, C.List_F9h, H.findType("ConstantStringMap<String,String>"));
+    C.List_empty2 = H.setRuntimeTypeInfo(makeConstList([]), H.findType("JSArray<BooleanSelector>"));
+    C.Map_empty0 = new H.ConstantStringMap(0, {}, C.List_empty2, H.findType("ConstantStringMap<BooleanSelector,Metadata>"));
+    C.Map_empty1 = new H.ConstantStringMap(0, {}, C.List_empty1, H.findType("ConstantStringMap<Null,Null>"));
+    C.List_empty3 = H.setRuntimeTypeInfo(makeConstList([]), H.findType("JSArray<PlatformSelector>"));
+    C.Map_empty = new H.ConstantStringMap(0, {}, C.List_empty3, H.findType("ConstantStringMap<PlatformSelector,Metadata>"));
+    C.MessageType_print = new D.MessageType("print");
+    C.MessageType_skip = new D.MessageType("skip");
+    C.OperatingSystem_none_none = new N.OperatingSystem("none", "none");
+    C.PlatformSelector_All = new E.PlatformSelector(C.C_All);
+    C.Result_error = new G.Result0("error");
+    C.Result_skipped = new G.Result0("skipped");
+    C.Result_success = new G.Result0("success");
+    C.Status_complete = new G.Status("complete");
+    C.State_Status_complete_Result_error = new G.State(C.Status_complete, C.Result_error);
+    C.Result_failure = new G.Result0("failure");
+    C.State_Status_complete_Result_failure = new G.State(C.Status_complete, C.Result_failure);
+    C.State_Status_complete_Result_skipped = new G.State(C.Status_complete, C.Result_skipped);
+    C.Status_pending = new G.Status("pending");
+    C.State_Status_pending_Result_success = new G.State(C.Status_pending, C.Result_success);
+    C.Status_running = new G.Status("running");
+    C.State_Status_running_Result_skipped = new G.State(C.Status_running, C.Result_skipped);
+    C.State_Status_running_Result_success = new G.State(C.Status_running, C.Result_success);
+    C.Symbol_Drw = new H.Symbol("test.declarer");
+    C.Symbol_MAi = new H.Symbol("test.runner.test_channel");
+    C.Symbol_cQL = new H.Symbol("test.invoker");
+    C.Symbol_runCount = new H.Symbol("runCount");
+    C.Timeout_null_1 = new R.Timeout(null, 1);
+    C.Timeout_null_null = new R.Timeout(null, null);
+    C.TokenType_31K = new L.TokenType("right paren");
+    C.TokenType_69P = new L.TokenType("question mark");
+    C.TokenType_and = new L.TokenType("and");
+    C.TokenType_colon = new L.TokenType("colon");
+    C.TokenType_e7P = new L.TokenType("left paren");
+    C.TokenType_identifier = new L.TokenType("identifier");
+    C.TokenType_not = new L.TokenType("not");
+    C.TokenType_or = new L.TokenType("or");
+    C.TokenType_wwi = new L.TokenType("end of file");
+    C.Type_ByteBuffer_RkP = H.typeLiteral("ByteBuffer");
+    C.Type_ByteData_zNC = H.typeLiteral("ByteData");
+    C.Type_Float32List_LB7 = H.typeLiteral("Float32List");
+    C.Type_Float64List_LB7 = H.typeLiteral("Float64List");
+    C.Type_Int16List_uXf = H.typeLiteral("Int16List");
+    C.Type_Int32List_O50 = H.typeLiteral("Int32List");
+    C.Type_Int8List_ekJ = H.typeLiteral("Int8List");
+    C.Type_JSObject_8k0 = H.typeLiteral("JSObject");
+    C.Type_Null_Yyn = H.typeLiteral("Null");
+    C.Type_String_k8F = H.typeLiteral("String");
+    C.Type_Uint16List_2bx = H.typeLiteral("Uint16List");
+    C.Type_Uint32List_2bx = H.typeLiteral("Uint32List");
+    C.Type_Uint8ClampedList_Jik = H.typeLiteral("Uint8ClampedList");
+    C.Type_Uint8List_WLA = H.typeLiteral("Uint8List");
+    C.Type_bool_lhE = H.typeLiteral("bool");
+    C.Type_double_K1J = H.typeLiteral("double");
+    C.Type_int_tHn = H.typeLiteral("int");
+    C.Type_num_cv7 = H.typeLiteral("num");
+    C._PathDirection_8Gl = new M._PathDirection("at root");
+    C._PathDirection_988 = new M._PathDirection("below root");
+    C._PathDirection_FIw = new M._PathDirection("reaches root");
+    C._PathDirection_ZGD = new M._PathDirection("above root");
+    C._PathRelation_different = new M._PathRelation("different");
+    C._PathRelation_equal = new M._PathRelation("equal");
+    C._PathRelation_inconclusive = new M._PathRelation("inconclusive");
+    C._PathRelation_within = new M._PathRelation("within");
+    C._StreamGroupState_canceled = new L._StreamGroupState("canceled");
+    C._StreamGroupState_dormant = new L._StreamGroupState("dormant");
+    C._StreamGroupState_listening = new L._StreamGroupState("listening");
+    C._StreamGroupState_paused = new L._StreamGroupState("paused");
+    C._TokenKind_false_false_false = new T._TokenKind(false, false, false);
+    C._TokenKind_false_false_true = new T._TokenKind(false, false, true);
+    C._TokenKind_false_true_false = new T._TokenKind(false, true, false);
+    C._TokenKind_true_false_false = new T._TokenKind(true, false, false);
+    C._ZoneFunction_3bB = new P._ZoneFunction(C.C__RootZone, P.async___rootCreatePeriodicTimer$closure(), type$._ZoneFunction_of_Timer_Function_5_Zone_and_ZoneDelegate_and_Zone_and_Duration_and_void_Function_Timer);
+    C._ZoneFunction_7G2 = new P._ZoneFunction(C.C__RootZone, P.async___rootRegisterBinaryCallback$closure(), type$._ZoneFunction_Function);
+    C._ZoneFunction_Eeh = new P._ZoneFunction(C.C__RootZone, P.async___rootRegisterUnaryCallback$closure(), type$._ZoneFunction_Function);
+    C._ZoneFunction_NMc = new P._ZoneFunction(C.C__RootZone, P.async___rootHandleUncaughtError$closure(), type$._ZoneFunction_of_void_Function_Zone_ZoneDelegate_Zone_Object_StackTrace);
+    C._ZoneFunction__RootZone__rootCreateTimer = new P._ZoneFunction(C.C__RootZone, P.async___rootCreateTimer$closure(), type$._ZoneFunction_of_Timer_Function_5_Zone_and_ZoneDelegate_and_Zone_and_Duration_and_void_Function);
+    C._ZoneFunction__RootZone__rootErrorCallback = new P._ZoneFunction(C.C__RootZone, P.async___rootErrorCallback$closure(), type$._ZoneFunction_of_AsyncError_Function_Zone_ZoneDelegate_Zone_Object_StackTrace);
+    C._ZoneFunction__RootZone__rootFork = new P._ZoneFunction(C.C__RootZone, P.async___rootFork$closure(), type$._ZoneFunction_of_Zone_Function_5_Zone_and_ZoneDelegate_and_Zone_and_ZoneSpecification_and_Map_dynamic_dynamic);
+    C._ZoneFunction__RootZone__rootPrint = new P._ZoneFunction(C.C__RootZone, P.async___rootPrint$closure(), type$._ZoneFunction_of_void_Function_Zone_ZoneDelegate_Zone_String);
+    C._ZoneFunction__RootZone__rootRegisterCallback = new P._ZoneFunction(C.C__RootZone, P.async___rootRegisterCallback$closure(), type$._ZoneFunction_Function);
+    C._ZoneFunction__RootZone__rootRun = new P._ZoneFunction(C.C__RootZone, P.async___rootRun$closure(), type$._ZoneFunction_Function);
+    C._ZoneFunction__RootZone__rootRunBinary = new P._ZoneFunction(C.C__RootZone, P.async___rootRunBinary$closure(), type$._ZoneFunction_Function);
+    C._ZoneFunction__RootZone__rootRunUnary = new P._ZoneFunction(C.C__RootZone, P.async___rootRunUnary$closure(), type$._ZoneFunction_Function);
+    C._ZoneFunction__RootZone__rootScheduleMicrotask = new P._ZoneFunction(C.C__RootZone, P.async___rootScheduleMicrotask$closure(), type$._ZoneFunction_of_void_Function_4_Zone_and_ZoneDelegate_and_Zone_and_void_Function);
+    C._ZoneSpecification_ALf = new P._ZoneSpecification(null, null, null, null, null, null, null, null, null, null, null, null, null);
+  })();
+  (function staticFields() {
+    $.printToZone = null;
+    $.Primitives_timerFrequency = null;
+    $.Primitives_timerTicks = null;
+    $.Closure_functionCounter = 0;
+    $.BoundClosure_selfFieldNameCache = null;
+    $.BoundClosure_receiverFieldNameCache = null;
+    $.getTagFunction = null;
+    $.alternateTagFunction = null;
+    $.prototypeForTagFunction = null;
+    $.dispatchRecordsForInstanceTags = null;
+    $.interceptorsForUncacheableTags = null;
+    $.initNativeDispatchFlag = null;
+    $._nextCallback = null;
+    $._lastCallback = null;
+    $._lastPriorityCallback = null;
+    $._isInCallbackLoop = false;
+    $.Zone__current = C.C__RootZone;
+    $._RootZone__rootDelegate = null;
+    $._toStringVisiting = [];
+    $.Expando__keyCount = 0;
+    $.Stopwatch__frequency = null;
+    $._currentUriBase = null;
+    $._current = null;
+    $._glyphs = C.C_UnicodeGlyphSet;
+    $._macOSDirectories = P.LinkedHashSet_LinkedHashSet$_literal(["/Applications", "/Library", "/Network", "/System", "/Users"], type$.String);
+    $._globalDeclarer = null;
+    $.x = 0;
+  })();
+  (function lazyInitializers() {
+    var _lazy = hunkHelpers.lazy;
+    _lazy($, "DART_CLOSURE_PROPERTY_NAME", "$get$DART_CLOSURE_PROPERTY_NAME", function() {
+      return H.getIsolateAffinityTag("_$dart_dartClosure");
+    });
+    _lazy($, "JS_INTEROP_INTERCEPTOR_TAG", "$get$JS_INTEROP_INTERCEPTOR_TAG", function() {
+      return H.getIsolateAffinityTag("_$dart_js");
+    });
+    _lazy($, "TypeErrorDecoder_noSuchMethodPattern", "$get$TypeErrorDecoder_noSuchMethodPattern", function() {
+      return H.TypeErrorDecoder_extractPattern(H.TypeErrorDecoder_provokeCallErrorOn({
+        toString: function() {
+          return "$receiver$";
+        }
+      }));
+    });
+    _lazy($, "TypeErrorDecoder_notClosurePattern", "$get$TypeErrorDecoder_notClosurePattern", function() {
+      return H.TypeErrorDecoder_extractPattern(H.TypeErrorDecoder_provokeCallErrorOn({$method$: null,
+        toString: function() {
+          return "$receiver$";
+        }
+      }));
+    });
+    _lazy($, "TypeErrorDecoder_nullCallPattern", "$get$TypeErrorDecoder_nullCallPattern", function() {
+      return H.TypeErrorDecoder_extractPattern(H.TypeErrorDecoder_provokeCallErrorOn(null));
+    });
+    _lazy($, "TypeErrorDecoder_nullLiteralCallPattern", "$get$TypeErrorDecoder_nullLiteralCallPattern", function() {
+      return H.TypeErrorDecoder_extractPattern(function() {
+        var $argumentsExpr$ = '$arguments$';
+        try {
+          null.$method$($argumentsExpr$);
+        } catch (e) {
+          return e.message;
+        }
+      }());
+    });
+    _lazy($, "TypeErrorDecoder_undefinedCallPattern", "$get$TypeErrorDecoder_undefinedCallPattern", function() {
+      return H.TypeErrorDecoder_extractPattern(H.TypeErrorDecoder_provokeCallErrorOn(void 0));
+    });
+    _lazy($, "TypeErrorDecoder_undefinedLiteralCallPattern", "$get$TypeErrorDecoder_undefinedLiteralCallPattern", function() {
+      return H.TypeErrorDecoder_extractPattern(function() {
+        var $argumentsExpr$ = '$arguments$';
+        try {
+          (void 0).$method$($argumentsExpr$);
+        } catch (e) {
+          return e.message;
+        }
+      }());
+    });
+    _lazy($, "TypeErrorDecoder_nullPropertyPattern", "$get$TypeErrorDecoder_nullPropertyPattern", function() {
+      return H.TypeErrorDecoder_extractPattern(H.TypeErrorDecoder_provokePropertyErrorOn(null));
+    });
+    _lazy($, "TypeErrorDecoder_nullLiteralPropertyPattern", "$get$TypeErrorDecoder_nullLiteralPropertyPattern", function() {
+      return H.TypeErrorDecoder_extractPattern(function() {
+        try {
+          null.$method$;
+        } catch (e) {
+          return e.message;
+        }
+      }());
+    });
+    _lazy($, "TypeErrorDecoder_undefinedPropertyPattern", "$get$TypeErrorDecoder_undefinedPropertyPattern", function() {
+      return H.TypeErrorDecoder_extractPattern(H.TypeErrorDecoder_provokePropertyErrorOn(void 0));
+    });
+    _lazy($, "TypeErrorDecoder_undefinedLiteralPropertyPattern", "$get$TypeErrorDecoder_undefinedLiteralPropertyPattern", function() {
+      return H.TypeErrorDecoder_extractPattern(function() {
+        try {
+          (void 0).$method$;
+        } catch (e) {
+          return e.message;
+        }
+      }());
+    });
+    _lazy($, "_AsyncRun__scheduleImmediateClosure", "$get$_AsyncRun__scheduleImmediateClosure", function() {
+      return P._AsyncRun__initializeScheduleImmediate();
+    });
+    _lazy($, "Future__nullFuture", "$get$Future__nullFuture", function() {
+      return P._Future$zoneValue(null, C.C__RootZone, type$.Null);
+    });
+    _lazy($, "_RootZone__rootMap", "$get$_RootZone__rootMap", function() {
+      var t1 = type$.dynamic;
+      return P.HashMap_HashMap(t1, t1);
+    });
+    _lazy($, "Utf8Decoder__decoder", "$get$Utf8Decoder__decoder", function() {
+      return P.Utf8Decoder__makeDecoder();
+    });
+    _lazy($, "_Base64Decoder__inverseAlphabet", "$get$_Base64Decoder__inverseAlphabet", function() {
+      return H.NativeInt8List__create1(H._ensureNativeList(H.setRuntimeTypeInfo([-2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -1, -2, -2, -2, -2, -2, 62, -2, 62, -2, 63, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, -2, -2, -2, -1, -2, -2, -2, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, -2, -2, -2, -2, 63, -2, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, -2, -2, -2, -2, -2], type$.JSArray_int)));
+    });
+    _lazy($, "_Uri__isWindowsCached", "$get$_Uri__isWindowsCached", function() {
+      return typeof process != "undefined" && Object.prototype.toString.call(process) == "[object process]" && process.platform == "win32";
+    });
+    _lazy($, "_Uri__needsNoEncoding", "$get$_Uri__needsNoEncoding", function() {
+      return P.RegExp_RegExp("^[\\-\\.0-9A-Z_a-z~]*$", false);
+    });
+    _lazy($, "_hasErrorStackProperty", "$get$_hasErrorStackProperty", function() {
+      return new Error().stack != void 0;
+    });
+    _lazy($, "_scannerTables", "$get$_scannerTables", function() {
+      return P._createTables();
+    });
+    _lazy($, "_whitespaceAndSingleLineComments", "$get$_whitespaceAndSingleLineComments", function() {
+      return P.RegExp_RegExp("([ \\t\\n]+|//[^\\n]*(\\n|$))+", false);
+    });
+    _lazy($, "_multiLineCommentBody", "$get$_multiLineCommentBody", function() {
+      return P.RegExp_RegExp("([^/*]|/[^*]|\\*[^/])+", false);
+    });
+    _lazy($, "_hyphenatedIdentifier", "$get$_hyphenatedIdentifier0", function() {
+      return P.RegExp_RegExp("[a-zA-Z_-][a-zA-Z0-9_-]*", false);
+    });
+    _lazy($, "_dart2DynamicArgs", "$get$_dart2DynamicArgs", function() {
+      return P.RegExp_RegExp("<dynamic(, dynamic)*>", false);
+    });
+    _lazy($, "_escapeRegExp", "$get$_escapeRegExp", function() {
+      return P.RegExp_RegExp("[\\x00-\\x07\\x0E-\\x1F" + C.Map_F9GZw.get$keys().map$1$1(0, M.util___getHexLiteral$closure(), type$.String).join$0(0) + "]", false);
+    });
+    _lazy($, "windows", "$get$windows", function() {
+      return M.Context_Context($.$get$Style_windows());
+    });
+    _lazy($, "url", "$get$url", function() {
+      return M.Context_Context($.$get$Style_url());
+    });
+    _lazy($, "context", "$get$context", function() {
+      return new M.Context($.$get$Style_platform(), null);
+    });
+    _lazy($, "Style_posix", "$get$Style_posix", function() {
+      return new E.PosixStyle(P.RegExp_RegExp("/", false), P.RegExp_RegExp("[^/]$", false), P.RegExp_RegExp("^/", false));
+    });
+    _lazy($, "Style_windows", "$get$Style_windows", function() {
+      return new L.WindowsStyle(P.RegExp_RegExp("[/\\\\]", false), P.RegExp_RegExp("[^/\\\\]$", false), P.RegExp_RegExp("^(\\\\\\\\[^\\\\]+\\\\[^\\\\/]+|[a-zA-Z]:[/\\\\])", false), P.RegExp_RegExp("^[/\\\\](?![/\\\\])", false));
+    });
+    _lazy($, "Style_url", "$get$Style_url", function() {
+      return new F.UrlStyle(P.RegExp_RegExp("/", false), P.RegExp_RegExp("(^[a-zA-Z][-+.a-zA-Z\\d]*://|[^/])$", false), P.RegExp_RegExp("[a-zA-Z][-+.a-zA-Z\\d]*://[^/]*", false), P.RegExp_RegExp("^/", false));
+    });
+    _lazy($, "Style_platform", "$get$Style_platform", function() {
+      return O.Style__getPlatformStyle();
+    });
+    _lazy($, "_digits", "$get$_digits", function() {
+      return new L.closure().call$0();
+    });
+    _lazy($, "MAX_INT32", "$get$MAX_INT32", function() {
+      return H._checkIntNullable(P.pow(2, 31) - 1);
+    });
+    _lazy($, "MIN_INT32", "$get$MIN_INT32", function() {
+      return H._checkIntNullable(-P.pow(2, 31));
+    });
+    _lazy($, "_specKey", "$get$_specKey", function() {
+      return new P.Object();
+    });
+    _lazy($, "_vmFrame", "$get$_vmFrame", function() {
+      return P.RegExp_RegExp("^#\\d+\\s+(\\S.*) \\((.+?)((?::\\d+){0,2})\\)$", false);
+    });
+    _lazy($, "_v8Frame", "$get$_v8Frame", function() {
+      return P.RegExp_RegExp("^\\s*at (?:(\\S.*?)(?: \\[as [^\\]]+\\])? \\((.*)\\)|(.*))$", false);
+    });
+    _lazy($, "_v8UrlLocation", "$get$_v8UrlLocation", function() {
+      return P.RegExp_RegExp("^(.*):(\\d+):(\\d+)|native$", false);
+    });
+    _lazy($, "_v8EvalLocation", "$get$_v8EvalLocation", function() {
+      return P.RegExp_RegExp("^eval at (?:\\S.*?) \\((.*)\\)(?:, .*?:\\d+:\\d+)?$", false);
+    });
+    _lazy($, "_firefoxSafariFrame", "$get$_firefoxSafariFrame", function() {
+      return P.RegExp_RegExp("^(?:([^@(/]*)(?:\\(.*\\))?((?:/[^/]*)*)(?:\\(.*\\))?@)?(.*?):(\\d*)(?::(\\d*))?$", false);
+    });
+    _lazy($, "_friendlyFrame", "$get$_friendlyFrame", function() {
+      return P.RegExp_RegExp("^(\\S+)(?: (\\d+)(?::(\\d+))?)?\\s+([^\\d].*)$", false);
+    });
+    _lazy($, "_asyncBody", "$get$_asyncBody", function() {
+      return P.RegExp_RegExp("<(<anonymous closure>|[^>]+)_async_body>", false);
+    });
+    _lazy($, "_initialDot", "$get$_initialDot", function() {
+      return P.RegExp_RegExp("^\\.", false);
+    });
+    _lazy($, "Frame__uriRegExp", "$get$Frame__uriRegExp", function() {
+      return P.RegExp_RegExp("^[a-zA-Z][-+.a-zA-Z\\d]*://", false);
+    });
+    _lazy($, "Frame__windowsRegExp", "$get$Frame__windowsRegExp", function() {
+      return P.RegExp_RegExp("^([a-zA-Z]:[\\\\/]|\\\\\\\\)", false);
+    });
+    _lazy($, "StackZoneSpecification_disableKey", "$get$StackZoneSpecification_disableKey", function() {
+      return new P.Object();
+    });
+    _lazy($, "_terseRegExp", "$get$_terseRegExp", function() {
+      return P.RegExp_RegExp("(-patch)?([/\\\\].*)?$", false);
+    });
+    _lazy($, "_v8Trace", "$get$_v8Trace", function() {
+      return P.RegExp_RegExp("\\n    ?at ", false);
+    });
+    _lazy($, "_v8TraceLine", "$get$_v8TraceLine", function() {
+      return P.RegExp_RegExp("    ?at ", false);
+    });
+    _lazy($, "_firefoxSafariTrace", "$get$_firefoxSafariTrace", function() {
+      return P.RegExp_RegExp("^(([.0-9A-Za-z_$/<]|\\(.*\\))*@)?[^\\s]*:\\d*$", true);
+    });
+    _lazy($, "_friendlyTrace", "$get$_friendlyTrace", function() {
+      return P.RegExp_RegExp("^[^\\s<][^\\s]*( \\d+(:\\d+)?)?[ \\t]+[^\\s]+$", true);
+    });
+    _lazy($, "Metadata_empty", "$get$Metadata_empty", function() {
+      var _null = null;
+      return O.Metadata$_(_null, _null, _null, _null, _null, _null, _null, _null, _null, _null);
+    });
+    _lazy($, "_universalValidVariables", "$get$_universalValidVariables", function() {
+      var _i,
+        t1 = P.LinkedHashSet_LinkedHashSet(type$.String);
+      t1.add$1(0, "posix");
+      t1.add$1(0, "dart-vm");
+      t1.add$1(0, "browser");
+      t1.add$1(0, "js");
+      t1.add$1(0, "blink");
+      t1.add$1(0, "google");
+      for (_i = 0; _i < 7; ++_i)
+        t1.add$1(0, C.List_m7e[_i].identifier);
+      for (_i = 0; _i < 5; ++_i)
+        t1.add$1(0, C.List_opx[_i].identifier);
+      return t1;
+    });
+    _lazy($, "_currentKey", "$get$_currentKey0", function() {
+      return new P.Object();
+    });
+    _lazy($, "_currentKey0", "$get$_currentKey", function() {
+      return new P.Object();
+    });
+    _lazy($, "currentOSGuess", "$get$currentOSGuess", function() {
+      return new B.closure0().call$0();
+    });
+    _lazy($, "_hyphenatedIdentifier0", "$get$_hyphenatedIdentifier", function() {
+      return P.RegExp_RegExp("[a-zA-Z_-][a-zA-Z0-9_-]*", false);
+    });
+    _lazy($, "anchoredHyphenatedIdentifier", "$get$anchoredHyphenatedIdentifier", function() {
+      return P.RegExp_RegExp("^" + $.$get$_hyphenatedIdentifier().pattern + "$", false);
+    });
+    _lazy($, "SuiteConfiguration_empty", "$get$SuiteConfiguration_empty", function() {
+      var t1, _null = null;
+      U.SuiteConfiguration__list(_null, type$.String);
+      t1 = type$.Pattern;
+      L.UnmodifiableSetView$(P.LinkedHashSet_LinkedHashSet$_empty(t1), t1);
+      U.SuiteConfiguration__list(_null, H.findType("RuntimeSelection"));
+      t1 = H.findType("SuiteConfiguration");
+      U.SuiteConfiguration__map(_null, type$.BooleanSelector, t1);
+      U.SuiteConfiguration__map(_null, type$.PlatformSelector, t1);
+      $.$get$Metadata_empty();
+      return new U.SuiteConfiguration();
+    });
+  })();
+  (function nativeSupport() {
+    !function() {
+      var intern = function(s) {
+        var o = {};
+        o[s] = 1;
+        return Object.keys(hunkHelpers.convertToFastObject(o))[0];
+      };
+      init.getIsolateTag = function(name) {
+        return intern("___dart_" + name + init.isolateTag);
+      };
+      var tableProperty = "___dart_isolate_tags_";
+      var usedProperties = Object[tableProperty] || (Object[tableProperty] = Object.create(null));
+      var rootProperty = "_ZxYxX";
+      for (var i = 0;; i++) {
+        var property = intern(rootProperty + "_" + i + "_");
+        if (!(property in usedProperties)) {
+          usedProperties[property] = 1;
+          init.isolateTag = property;
+          break;
+        }
+      }
+      init.dispatchPropertyName = init.getIsolateTag("dispatch_record");
+    }();
+    hunkHelpers.setOrUpdateInterceptorsByTag({ArrayBuffer: H.NativeByteBuffer, ArrayBufferView: H.NativeTypedData, DataView: H.NativeByteData, Float32Array: H.NativeFloat32List, Float64Array: H.NativeFloat64List, Int16Array: H.NativeInt16List, Int32Array: H.NativeInt32List, Int8Array: H.NativeInt8List, Uint16Array: H.NativeUint16List, Uint32Array: H.NativeUint32List, Uint8ClampedArray: H.NativeUint8ClampedList, CanvasPixelArray: H.NativeUint8ClampedList, Uint8Array: H.NativeUint8List, ApplicationCacheErrorEvent: W.ApplicationCacheErrorEvent, Blob: W.Blob, DOMError: W.DomError, DOMException: W.DomException, ErrorEvent: W.ErrorEvent, AbortPaymentEvent: W.Event, AnimationEvent: W.Event, AnimationPlaybackEvent: W.Event, BackgroundFetchClickEvent: W.Event, BackgroundFetchEvent: W.Event, BackgroundFetchFailEvent: W.Event, BackgroundFetchedEvent: W.Event, BeforeInstallPromptEvent: W.Event, BeforeUnloadEvent: W.Event, BlobEvent: W.Event, CanMakePaymentEvent: W.Event, ClipboardEvent: W.Event, CloseEvent: W.Event, CompositionEvent: W.Event, CustomEvent: W.Event, DeviceMotionEvent: W.Event, DeviceOrientationEvent: W.Event, ExtendableEvent: W.Event, ExtendableMessageEvent: W.Event, FetchEvent: W.Event, FocusEvent: W.Event, FontFaceSetLoadEvent: W.Event, ForeignFetchEvent: W.Event, GamepadEvent: W.Event, HashChangeEvent: W.Event, InstallEvent: W.Event, KeyboardEvent: W.Event, MediaEncryptedEvent: W.Event, MediaQueryListEvent: W.Event, MediaStreamEvent: W.Event, MediaStreamTrackEvent: W.Event, MIDIConnectionEvent: W.Event, MIDIMessageEvent: W.Event, MouseEvent: W.Event, DragEvent: W.Event, MutationEvent: W.Event, NotificationEvent: W.Event, PageTransitionEvent: W.Event, PaymentRequestEvent: W.Event, PaymentRequestUpdateEvent: W.Event, PointerEvent: W.Event, PopStateEvent: W.Event, PresentationConnectionAvailableEvent: W.Event, ProgressEvent: W.Event, PromiseRejectionEvent: W.Event, PushEvent: W.Event, RTCDataChannelEvent: W.Event, RTCDTMFToneChangeEvent: W.Event, RTCPeerConnectionIceEvent: W.Event, RTCTrackEvent: W.Event, SecurityPolicyViolationEvent: W.Event, SensorErrorEvent: W.Event, SpeechRecognitionEvent: W.Event, SpeechSynthesisEvent: W.Event, StorageEvent: W.Event, SyncEvent: W.Event, TextEvent: W.Event, TouchEvent: W.Event, TrackEvent: W.Event, TransitionEvent: W.Event, WebKitTransitionEvent: W.Event, UIEvent: W.Event, VRDeviceEvent: W.Event, VRDisplayEvent: W.Event, VRSessionEvent: W.Event, WheelEvent: W.Event, MojoInterfaceRequestEvent: W.Event, ResourceProgressEvent: W.Event, USBConnectionEvent: W.Event, IDBVersionChangeEvent: W.Event, AudioProcessingEvent: W.Event, OfflineAudioCompletionEvent: W.Event, WebGLContextEvent: W.Event, Event: W.Event, InputEvent: W.Event, Window: W.EventTarget, DOMWindow: W.EventTarget, EventTarget: W.EventTarget, File: W.File, Location: W.Location, MediaError: W.MediaError, MediaKeyMessageEvent: W.MediaKeyMessageEvent, MessageEvent: W.MessageEvent, MessagePort: W.MessagePort, NavigatorUserMediaError: W.NavigatorUserMediaError, OverconstrainedError: W.OverconstrainedError, PositionError: W.PositionError, PresentationConnectionCloseEvent: W.PresentationConnectionCloseEvent, SpeechRecognitionError: W.SpeechRecognitionError, SQLError: P.SqlError});
+    hunkHelpers.setOrUpdateLeafTags({ArrayBuffer: true, ArrayBufferView: false, DataView: true, Float32Array: true, Float64Array: true, Int16Array: true, Int32Array: true, Int8Array: true, Uint16Array: true, Uint32Array: true, Uint8ClampedArray: true, CanvasPixelArray: true, Uint8Array: false, ApplicationCacheErrorEvent: true, Blob: false, DOMError: true, DOMException: true, ErrorEvent: true, AbortPaymentEvent: true, AnimationEvent: true, AnimationPlaybackEvent: true, BackgroundFetchClickEvent: true, BackgroundFetchEvent: true, BackgroundFetchFailEvent: true, BackgroundFetchedEvent: true, BeforeInstallPromptEvent: true, BeforeUnloadEvent: true, BlobEvent: true, CanMakePaymentEvent: true, ClipboardEvent: true, CloseEvent: true, CompositionEvent: true, CustomEvent: true, DeviceMotionEvent: true, DeviceOrientationEvent: true, ExtendableEvent: true, ExtendableMessageEvent: true, FetchEvent: true, FocusEvent: true, FontFaceSetLoadEvent: true, ForeignFetchEvent: true, GamepadEvent: true, HashChangeEvent: true, InstallEvent: true, KeyboardEvent: true, MediaEncryptedEvent: true, MediaQueryListEvent: true, MediaStreamEvent: true, MediaStreamTrackEvent: true, MIDIConnectionEvent: true, MIDIMessageEvent: true, MouseEvent: true, DragEvent: true, MutationEvent: true, NotificationEvent: true, PageTransitionEvent: true, PaymentRequestEvent: true, PaymentRequestUpdateEvent: true, PointerEvent: true, PopStateEvent: true, PresentationConnectionAvailableEvent: true, ProgressEvent: true, PromiseRejectionEvent: true, PushEvent: true, RTCDataChannelEvent: true, RTCDTMFToneChangeEvent: true, RTCPeerConnectionIceEvent: true, RTCTrackEvent: true, SecurityPolicyViolationEvent: true, SensorErrorEvent: true, SpeechRecognitionEvent: true, SpeechSynthesisEvent: true, StorageEvent: true, SyncEvent: true, TextEvent: true, TouchEvent: true, TrackEvent: true, TransitionEvent: true, WebKitTransitionEvent: true, UIEvent: true, VRDeviceEvent: true, VRDisplayEvent: true, VRSessionEvent: true, WheelEvent: true, MojoInterfaceRequestEvent: true, ResourceProgressEvent: true, USBConnectionEvent: true, IDBVersionChangeEvent: true, AudioProcessingEvent: true, OfflineAudioCompletionEvent: true, WebGLContextEvent: true, Event: false, InputEvent: false, Window: true, DOMWindow: true, EventTarget: false, File: true, Location: true, MediaError: true, MediaKeyMessageEvent: true, MessageEvent: true, MessagePort: true, NavigatorUserMediaError: true, OverconstrainedError: true, PositionError: true, PresentationConnectionCloseEvent: true, SpeechRecognitionError: true, SQLError: true});
+    H.NativeTypedArray.$nativeSuperclassTag = "ArrayBufferView";
+    H._NativeTypedArrayOfDouble_NativeTypedArray_ListMixin.$nativeSuperclassTag = "ArrayBufferView";
+    H._NativeTypedArrayOfDouble_NativeTypedArray_ListMixin_FixedLengthListMixin.$nativeSuperclassTag = "ArrayBufferView";
+    H.NativeTypedArrayOfDouble.$nativeSuperclassTag = "ArrayBufferView";
+    H._NativeTypedArrayOfInt_NativeTypedArray_ListMixin.$nativeSuperclassTag = "ArrayBufferView";
+    H._NativeTypedArrayOfInt_NativeTypedArray_ListMixin_FixedLengthListMixin.$nativeSuperclassTag = "ArrayBufferView";
+    H.NativeTypedArrayOfInt.$nativeSuperclassTag = "ArrayBufferView";
+  })();
+  Function.prototype.call$0 = function() {
+    return this();
+  };
+  Function.prototype.call$1 = function(a) {
+    return this(a);
+  };
+  Function.prototype.call$2 = function(a, b) {
+    return this(a, b);
+  };
+  Function.prototype.call$3$3 = function(a, b, c) {
+    return this(a, b, c);
+  };
+  Function.prototype.call$2$2 = function(a, b) {
+    return this(a, b);
+  };
+  Function.prototype.call$1$1 = function(a) {
+    return this(a);
+  };
+  Function.prototype.call$2$1 = function(a) {
+    return this(a);
+  };
+  Function.prototype.call$3 = function(a, b, c) {
+    return this(a, b, c);
+  };
+  Function.prototype.call$4 = function(a, b, c, d) {
+    return this(a, b, c, d);
+  };
+  Function.prototype.call$3$1 = function(a) {
+    return this(a);
+  };
+  Function.prototype.call$2$3 = function(a, b, c) {
+    return this(a, b, c);
+  };
+  Function.prototype.call$1$2 = function(a, b) {
+    return this(a, b);
+  };
+  Function.prototype.call$5 = function(a, b, c, d, e) {
+    return this(a, b, c, d, e);
+  };
+  Function.prototype.call$3$4 = function(a, b, c, d) {
+    return this(a, b, c, d);
+  };
+  Function.prototype.call$2$4 = function(a, b, c, d) {
+    return this(a, b, c, d);
+  };
+  Function.prototype.call$1$4 = function(a, b, c, d) {
+    return this(a, b, c, d);
+  };
+  Function.prototype.call$3$6 = function(a, b, c, d, e, f) {
+    return this(a, b, c, d, e, f);
+  };
+  Function.prototype.call$2$5 = function(a, b, c, d, e) {
+    return this(a, b, c, d, e);
+  };
+  Function.prototype.call$2$0 = function() {
+    return this();
+  };
+  convertAllToFastObject(holders);
+  convertToFastObject($);
+  (function(callback) {
+    if (typeof document === "undefined") {
+      callback(null);
+      return;
+    }
+    if (typeof document.currentScript != 'undefined') {
+      callback(document.currentScript);
+      return;
+    }
+    var scripts = document.scripts;
+    function onLoad(event) {
+      for (var i = 0; i < scripts.length; ++i)
+        scripts[i].removeEventListener("load", onLoad, false);
+      callback(event.target);
+    }
+    for (var i = 0; i < scripts.length; ++i)
+      scripts[i].addEventListener("load", onLoad, false);
+  })(function(currentScript) {
+    init.currentScript = currentScript;
+    if (typeof dartMainRunner === "function")
+      dartMainRunner(R.main, []);
+    else
+      R.main([]);
+  });
+})();
+
+//# sourceMappingURL=main_test.dart.browser_test.dart.js.map
diff --git a/pkgs/coverage/test/test_files/main_test.js.map b/pkgs/coverage/test/test_files/main_test.js.map
new file mode 100644
index 0000000..38669ba
--- /dev/null
+++ b/pkgs/coverage/test/test_files/main_test.js.map
@@ -0,0 +1 @@
+{"version":3,"engine":"v2","file":"main_test.dart.browser_test.dart.js","sourceRoot":"","sources":["google3:///third_party/dart_lang/v2/sdk/lib/internal/cast.dart","google3:///third_party/dart_lang/v2/sdk/lib/internal/internal.dart","google3:///third_party/dart_lang/v2/sdk/lib/internal/iterable.dart","google3:///third_party/dart_lang/v2/sdk/lib/core/errors.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/constant_map.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/instantiation.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/js_helper.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/rti.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/native_helper.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/core_patch.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/js_rti.dart","google3:///third_party/dart_lang/v2/sdk/lib/core/exceptions.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/interceptors.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/regexp_helper.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/string_helper.dart","google3:///third_party/dart_lang/v2/sdk/lib/core/iterable.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/native_typed_data.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/shared/recipe_syntax.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/js_names.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/js_primitives.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/js_array.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/js_string.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/async_patch.dart","google3:///third_party/dart_lang/v2/sdk/lib/core/duration.dart","google3:///third_party/dart_lang/v2/sdk/lib/async/future_impl.dart","google3:///third_party/dart_lang/v2/sdk/lib/async/zone.dart","google3:///third_party/dart_lang/v2/sdk/lib/async/future.dart","google3:///third_party/dart_lang/v2/sdk/lib/async/timer.dart","google3:///third_party/dart_lang/v2/sdk/lib/async/schedule_microtask.dart","google3:///third_party/dart_lang/v2/sdk/lib/async/stream.dart","google3:///third_party/dart_lang/v2/sdk/lib/async/stream_controller.dart","google3:///third_party/dart_lang/v2/sdk/lib/async/stream_impl.dart","google3:///third_party/dart_lang/v2/sdk/lib/async/stream_pipe.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/internal_patch.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/collection_patch.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/linked_hash_map.dart","google3:///third_party/dart_lang/v2/sdk/lib/collection/hash_map.dart","google3:///third_party/dart_lang/v2/sdk/lib/collection/iterable.dart","google3:///third_party/dart_lang/v2/sdk/lib/collection/linked_hash_map.dart","google3:///third_party/dart_lang/v2/sdk/lib/collection/linked_hash_set.dart","google3:///third_party/dart_lang/v2/sdk/lib/collection/maps.dart","google3:///third_party/dart_lang/v2/sdk/lib/collection/queue.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/convert_patch.dart","google3:///third_party/dart_lang/v2/sdk/lib/convert/base64.dart","google3:///third_party/dart_lang/v2/sdk/lib/convert/codec.dart","google3:///third_party/dart_lang/v2/sdk/lib/core/date_time.dart","google3:///third_party/dart_lang/v2/sdk/lib/core/list.dart","google3:///third_party/dart_lang/v2/sdk/lib/core/map.dart","google3:///third_party/dart_lang/v2/sdk/lib/core/print.dart","google3:///third_party/dart_lang/v2/sdk/lib/core/string.dart","google3:///third_party/dart_lang/v2/sdk/lib/core/uri.dart","google3:///third_party/dart_lang/v2/sdk/lib/convert/utf.dart","google3:///third_party/dart_lang/v2/sdk/lib/js_util/js_util.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/math_patch.dart","google3:///third_party/dart_lang/v2/sdk/lib/html/dart2js/html_dart2js.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/string_scanner-1.0.5/lib/src/span_scanner.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/source_span-1.5.5/lib/src/file.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/remote_listener.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/stream_channel-2.0.0/lib/src/multi_channel.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/stream_channel-2.0.0/lib/src/stream_channel_controller.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/suite_channel_manager.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/stream_channel-2.0.0/lib/src/guarantee_channel.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/backend/stack_trace_formatter.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/path-1.6.4/lib/src/style.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/pool-1.4.0/lib/pool.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/async-2.4.0/lib/src/async_memoizer.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/source_map_stack_trace-1.1.5/lib/source_map_stack_trace.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/stack_trace-1.9.3/lib/src/chain.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/stack_trace-1.9.3/lib/src/trace.dart","google3:///third_party/dart_lang/v2/sdk/lib/core/stacktrace.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/backend/group.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/backend/metadata.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/collection-1.14.12/lib/src/unmodifiable_wrappers.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/frontend/timeout.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_core/lib/src/runner/engine.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/async-2.4.0/lib/src/future_group.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/async-2.4.0/lib/src/stream_group.dart","google3:///third_party/dart_lang/v2/sdk/lib/async/broadcast_stream_controller.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/source_maps-0.10.8/lib/src/utils.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/collection-1.14.12/lib/src/functions.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/collection-1.14.12/lib/src/union_set_controller.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/collection-1.14.12/lib/src/union_set.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/stack_trace-1.9.3/lib/src/lazy_trace.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/package_resolver-1.0.10/lib/src/package_config_resolver.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/source_span-1.5.5/lib/src/location.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/backend/live_test_controller.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/util/test.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/backend/invoker.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/string_scanner-1.0.5/lib/src/exception.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/backend/platform_selector.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/backend/suite_platform.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_core/lib/src/util/stack_trace_mapper.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/package_resolver-1.0.10/lib/src/package_root_resolver.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/source_maps-0.10.8/lib/src/vlq.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/source_maps-0.10.8/lib/parser.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test/lib/src/bootstrap/browser.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_core/lib/src/runner/plugin/remote_platform_helpers.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/stream_channel-2.0.0/lib/stream_channel.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/source_span-1.5.5/lib/src/span_exception.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/frontend/expect.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/matcher-0.12.6/lib/src/description.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/utils.dart","file:///usr/local/google/home/grouma/Projects/sample-test/test/main_test.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/path-1.6.4/lib/src/parsed_path.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/path-1.6.4/lib/src/path_exception.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/source_span-1.5.5/lib/src/span_with_context.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/backend/declarer.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/boolean_selector-1.0.5/lib/src/ast.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/source_span-1.5.5/lib/src/highlighter.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/stack_trace-1.9.3/lib/src/stack_zone_specification.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/stack_trace-1.9.3/lib/src/lazy_chain.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/backend/suite.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_core/lib/src/runner/suite.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/util/remote_exception.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_core/lib/test_core.dart","","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/backend/runtime.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_core/lib/src/runner/live_suite_controller.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/package_resolver-1.0.10/lib/src/utils.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/path-1.6.4/lib/src/utils.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/source_span-1.5.5/lib/src/utils.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/string_scanner-1.0.5/lib/src/utils.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/collection-1.14.12/lib/src/queue_list.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/matcher-0.12.6/lib/src/util.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/matcher-0.12.6/lib/src/core_matchers.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/matcher-0.12.6/lib/src/equals_matcher.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/path-1.6.4/lib/src/context.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/path-1.6.4/lib/path.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/matcher-0.12.6/lib/src/pretty_print.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/stack_trace-1.9.3/lib/src/frame.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/stack_trace-1.9.3/lib/src/unparsed_frame.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test/lib/src/runner/browser/post_message_channel.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/backend/operating_system.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/backend/closed_exception.dart","google3:///third_party/dart_lang/v2/sdk/lib/collection/list.dart","google3:///third_party/dart_lang/v2/sdk/lib/_internal/js_runtime/lib/js_number.dart","google3:///third_party/dart_lang/v2/sdk/lib/internal/list.dart","google3:///third_party/dart_lang/v2/sdk/lib/internal/symbol.dart","google3:///third_party/dart_lang/v2/sdk/lib/collection/collections.dart","google3:///third_party/dart_lang/v2/sdk/lib/collection/set.dart","google3:///third_party/dart_lang/v2/sdk/lib/convert/ascii.dart","google3:///third_party/dart_lang/v2/sdk/lib/convert/json.dart","google3:///third_party/dart_lang/v2/sdk/lib/core/object.dart","google3:///third_party/dart_lang/v2/sdk/lib/core/expando.dart","google3:///third_party/dart_lang/v2/sdk/lib/core/null.dart","google3:///third_party/dart_lang/v2/sdk/lib/core/stopwatch.dart","google3:///third_party/dart_lang/v2/sdk/lib/html/html_common/conversions_dart2js.dart","google3:///third_party/dart_lang/v2/sdk/lib/html/html_common/conversions.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/async-2.4.0/lib/src/delegate/stream_subscription.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/async-2.4.0/lib/src/null_stream_sink.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/async-2.4.0/lib/src/result/error.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/async-2.4.0/lib/src/result/value.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/async-2.4.0/lib/src/stream_completer.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/async-2.4.0/lib/src/stream_queue.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/async-2.4.0/lib/src/subscription_stream.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/async-2.4.0/lib/src/stream_sink_completer.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/boolean_selector-1.0.5/lib/src/all.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/boolean_selector-1.0.5/lib/src/evaluator.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/boolean_selector-1.0.5/lib/src/impl.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/boolean_selector-1.0.5/lib/src/intersection_selector.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/boolean_selector-1.0.5/lib/src/validator.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/boolean_selector-1.0.5/lib/src/none.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/boolean_selector-1.0.5/lib/src/parser.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/boolean_selector-1.0.5/lib/src/scanner.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/string_scanner-1.0.5/lib/src/string_scanner.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/boolean_selector-1.0.5/lib/src/token.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/boolean_selector-1.0.5/lib/src/visitor.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/collection-1.14.12/lib/src/empty_unmodifiable_set.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/collection-1.14.12/lib/src/wrappers.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/matcher-0.12.6/lib/src/feature_matcher.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/matcher-0.12.6/lib/src/interfaces.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/matcher-0.12.6/lib/src/type_matcher.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/path-1.6.4/lib/src/internal_style.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/path-1.6.4/lib/src/style/posix.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/path-1.6.4/lib/src/style/url.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/path-1.6.4/lib/src/style/windows.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/async-2.4.0/lib/src/restartable_timer.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/source_maps-0.10.8/lib/src/source_map_span.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/term_glyph-1.1.0/lib/src/generated/top_level.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/term_glyph-1.1.0/lib/term_glyph.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/source_span-1.5.5/lib/src/location_mixin.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/source_span-1.5.5/lib/src/span.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/source_span-1.5.5/lib/src/span_mixin.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/stream_channel-2.0.0/lib/src/stream_channel_completer.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/term_glyph-1.1.0/lib/src/generated/ascii_glyph_set.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/term_glyph-1.1.0/lib/src/generated/unicode_glyph_set.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/backend/live_test.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/backend/state.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/backend/message.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_api/lib/src/util/iterable_set.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_core/lib/src/runner/runner_suite.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_core/lib/src/runner/reporter/expanded.dart","file:///usr/local/google/home/grouma/Projects/test/pkgs/test_core/lib/src/util/print_sink.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/async-2.4.0/lib/src/delegate/sink.dart","file:///usr/local/google/home/grouma/.pub-cache/hosted/pub.dartlang.org/async-2.4.0/lib/src/result/result.dart"],"names":["CastIterable","hexDigitValue","SubListIterable","MappedIterable","IterableElementError.noElement","IterableElementError.tooMany","IterableElementError.tooFew","ConstantMap._throwUnmodifiable","instantiate1","Instantiation1","unminifyOrTag","isJsIndexable","S","Primitives.objectHashCode","Primitives.parseInt","Primitives.objectTypeName","Primitives._objectTypeNameNewRti","Primitives._saneNativeClassName","Primitives.dateNow","Primitives.initTicker","Primitives.currentUri","Primitives._fromCharCodeApply","Primitives.stringFromCodePoints","Primitives.stringFromCharCodes","Primitives.stringFromNativeUint8List","Primitives.stringFromCharCode","Primitives.lazyAsJsDate","Primitives.getYear","Primitives.getMonth","Primitives.getDay","Primitives.getHours","Primitives.getMinutes","Primitives.getSeconds","Primitives.getMilliseconds","Primitives.getProperty","Primitives.setProperty","iae","ioore","diagnoseIndexError","diagnoseRangeError","argumentErrorValue","checkNum","wrapException","toStringWrapper","throwExpression","throwConcurrentModificationError","TypeErrorDecoder.extractPattern","TypeErrorDecoder.provokeCallErrorOn","TypeErrorDecoder.provokePropertyErrorOn","NullError","JsNoSuchMethodError","unwrapException","getTraceFromException","objectHashCode","fillLiteralMap","getLength","fillLiteralSet","invokeClosure","Exception","convertDartClosureToJS","Closure.fromTearOff","Closure._computeSignatureFunctionNewRti","Closure.cspForwardCall","Closure.forwardCallTo","Closure.cspForwardInterceptedCall","Closure.forwardInterceptedCallTo","closureFromTearOff","BoundClosure.evalRecipe","evalInInstance","BoundClosure.evalRecipeIntercepted","BoundClosure.selfOf","BoundClosure.receiverOf","BoundClosure.computeFieldNamed","boolConversionCheck","extractFunctionTypeObjectFromInternal","TypeErrorImplementation","_typeDescription","assertTest","assertThrow","assertHelper","throwCyclicInit","RuntimeError","getIsolateAffinityTag","setRuntimeTypeInfo","getRuntimeTypeInfo","getRuntimeTypeArguments","runtimeTypeToString","_runtimeTypeToString","_getRuntimeTypeAsString","getFutureOrArgument","_functionRtiToString","isInterestingBound","_joinArguments","getRuntimeType","_isClosure","substitute","computeSignature","invokeOn","defineProperty","lookupAndCacheInterceptor","patchProto","patchInteriorProto","makeLeafDispatchRecord","makeDefaultDispatchRecord","initNativeDispatch","initNativeDispatchContinue","lookupInterceptor","initHooks","applyHooksTransformer","JSSyntaxRegExp.makeNative","_MatchImplementation","stringContainsUnchecked","escapeReplacement","stringReplaceFirstRE","quoteStringForRegExp","stringReplaceAllUnchecked","stringReplaceAllUncheckedString","_stringIdentity","stringReplaceAllFuncUnchecked","_AllMatchesIterable.iterator","stringReplaceFirstUnchecked","stringReplaceRangeUnchecked","_ensureNativeList","NativeInt8List._create1","_checkValidIndex","_checkValidRange","Rti._getFutureFromFutureOr","Rti._isUnionOfFunctionType","Rti._getInterfaceTypeArguments","Rti._getBindingArguments","Rti._getFunctionParameters","Rti._getGenericFunctionBounds","Rti._getCanonicalRecipe","findType","instantiatedGenericFunctionType","_instantiate","_Universe._canonicalRecipeOfStar","_Universe._canonicalRecipeOfQuestion","_Universe._canonicalRecipeOfFutureOr","_instantiateArray","_instantiateNamed","_instantiateFunctionParameters","_FunctionParameters.allocate","closureFunctionType","instanceOrFunctionType","instanceType","_isDartObject","_arrayInstanceType","_instanceType","_instanceTypeFromConstructor","_instanceTypeFromConstructorMiss","getTypeFromTypesTable","createRuntimeType","typeLiteral","_installSpecializedIsTest","Rti._getInterfaceName","_generalIsTestImplementation","_isTestViaProperty","_generalAsCheckImplementation","_generalTypeCheckImplementation","checkTypeBound","_Error.compose","_CastError.fromMessage","_CastError.forType","_TypeError.fromMessage","_TypeError.forType","_isTop","_asTop","_isBool","_asBoolNullable","_checkBoolNullable","_asDoubleNullable","_checkDoubleNullable","_isInt","_asIntNullable","_checkIntNullable","_isNum","_asNumNullable","_checkNumNullable","_isString","_asStringNullable","_checkStringNullable","_rtiArrayToString","Rti._getReturnType","_rtiToString","Rti._getGenericFunctionParameterIndex","_unminifyOrTag","_Universe.findRule","_Universe.findErasedType","_Universe.addRules","_Universe.addErasedTypes","_Universe.eval","_Universe.evalInEnvironment","_Universe.bind","_Universe._parseRecipe","_Universe._finishRti","_Universe._lookupTerminalRti","Rti.allocate","_Universe._createTerminalRti","_Universe._lookupUnaryRti","_Universe._createUnaryRti","_Universe._lookupGenericFunctionParameterRti","_Universe._createGenericFunctionParameterRti","_Universe._canonicalRecipeJoin","_Universe._canonicalRecipeJoinNamed","_Universe._lookupInterfaceRti","_Universe._createInterfaceRti","_Universe._lookupBindingRti","_Universe._canonicalRecipeOfBinding","_Universe._createBindingRti","_Universe._lookupFunctionRti","_Universe._canonicalRecipeOfFunction","_Universe._createFunctionRti","_Universe._lookupGenericFunctionRti","_Universe._canonicalRecipeOfGenericFunction","_Universe._createGenericFunctionRti","_Parser.create","_Parser.parse","_Parser.pushStackFrame","_Parser.handleTypeArguments","_Parser.collectArray","_Parser.handleFunctionArguments","_Parser.handleOptionalGroup","_Parser.handleNamedGroup","_Parser.collectNamed","_Parser.handleDigit","_Parser.handleIdentifier","_Universe.evalTypeVariable","_Parser.handleExtendedOperations","_Parser.toType","_Parser.toTypes","_Parser.toTypesNamed","_Parser.indexToType","_isSubtype","Rti._getStarArgument","Rti._getGenericFunctionBase","_isFunctionSubtype","_isInterfaceSubtype","typeEqual","Rti._getBindingBase","typesEqual","namedTypesEqual","isLegacyTopType","isTopType","_Utils.objectAssign","extractKeys","unmangleGlobalNameIfPreservedAnyways","printString","makeDispatchRecord","getNativeInterceptor","JSArray.fixed","JSArray.markFixed","JSArray.markFixedList","JSString._isWhitespace","JSString._skipLeadingWhitespace","JSString._skipTrailingWhitespace","_AsyncRun._initializeScheduleImmediate","_AsyncRun._scheduleImmediateJsOverride","_AsyncRun._scheduleImmediateWithSetImmediate","_AsyncRun._scheduleImmediateWithTimer","Timer._createTimer","_TimerImpl","_TimerImpl.periodic","_makeAsyncAwaitCompleter","_AsyncAwaitCompleter._future","_Future","_asyncStartSync","_asyncAwait","_asyncReturn","_asyncRethrow","_awaitOnObject","_wrapJsFunctionForAsync","Future","Future.microtask","Future.sync","_Future.value","_Future.zoneValue","_nonNullError","Future.error","_Future.immediateError","Future.wait","Future.value","_Future.immediate","Future.forEach","JSArray.iterator","Future._kTrue","Future.doWhile","_completeWithErrorCallback","_Future._chainForeignFuture","_Future._setPendingComplete","_Future._chainCoreFuture","_Future._setChained","_Future._propagateToListeners","_Future._error","_Future._removeListeners","_Future._cloneResult","_Future._setErrorObject","_registerErrorHandler","_microtaskLoop","_startMicrotaskLoop","_scheduleAsyncCallback","_schedulePriorityAsyncCallback","scheduleMicrotask","Stream.fromFuture","_StreamController.stream","Stream.fromIterable","StreamIterator","StreamController","_runGuarded","_AddStreamState.makeErrorHandler","_BufferingStreamSubscription","_BufferingStreamSubscription._zone","_nullDataHandler","_nullErrorHandler","_nullDoneHandler","_runUserCode","_cancelAndError","_cancelAndErrorClosure","_cancelAndValue","Timer","_ZoneSpecification","Zone._enter","_parentDelegate","_rootHandleUncaughtError","_rootRun","_rootRunUnary","_rootRunBinary","_rootRegisterCallback","_rootRegisterUnaryCallback","_rootRegisterBinaryCallback","_rootErrorCallback","_rootScheduleMicrotask","_rootCreateTimer","_rootCreatePeriodicTimer","Timer._createPeriodicTimer","_rootPrint","_printToZone","_rootFork","_CustomZone","runZoned","_runZoned","HashMap","_HashMap._getTableEntry","_HashMap._setTableEntry","_HashMap._newHashTable","JsLinkedHashMap.es6","LinkedHashMap","LinkedHashMap._literal","LinkedHashMap._empty","LinkedHashSet","LinkedHashSet._empty","LinkedHashSet._literal","_LinkedHashSet._newHashTable","_LinkedHashSetIterator","HashMap.from","IterableBase.iterableToShortString","IterableBase.iterableToFullString","_isToStringVisiting","_iterablePartsToStrings","LinkedHashMap.from","LinkedHashSet.from","MapBase.mapToString","ListQueue","_ListQueueIterator","_parseJson","_convertJsonToDartLazy","Utf8Decoder._convertIntercepted","Utf8Decoder._convertInterceptedUint8List","Utf8Decoder._useTextDecoderChecked","Utf8Decoder._useTextDecoderUnchecked","Utf8Decoder._unsafe","Utf8Decoder._makeDecoder","_scanOneByteCharacters","Base64Codec._checkPadding","int.parse","Error._objectToString","List.filled","List.from","List.unmodifiable","String.fromCharCodes","String.fromCharCode","String._stringFromIterable","RegExp","StringBuffer._writeAll","Uri.base","_Uri._uriEncode","JSSyntaxRegExp.hasMatch","StringBuffer.writeCharCode","StackTrace.current","DateTime._fourDigits","DateTime._threeDigits","DateTime._twoDigits","Duration","Error.safeToString","AssertionError","ArgumentError","ArgumentError.value","ArgumentError.notNull","RangeError","RangeError.value","RangeError.range","RangeError.checkValueInInterval","RangeError.checkValidRange","RangeError.checkNotNegative","IndexError","UnsupportedError","UnimplementedError","StateError","ConcurrentModificationError","FormatException","List.generate","Map.castFrom","print","_combineSurrogatePair","Uri.parse","Uri.decodeComponent","Uri._parseIPv4Address","Uri.parseIPv6Address","NativeUint8List","_Uri.notSimple","_Uri","JSString.isNotEmpty","_Uri._defaultPort","_Uri._fail","_Uri.file","_Uri._checkNonWindowsPathReservedCharacters","_Uri._checkWindowsPathReservedCharacters","ListIterable.iterator","_Uri._checkWindowsDriveLetter","_Uri._makeFileUri","_Uri._makeWindowsFileUrl","_Uri._makePort","_Uri._makeHost","_Uri._checkZoneID","_Uri._normalizeZoneID","StringBuffer.write","_Uri._normalizeRegName","_Uri._makeScheme","_Uri._canonicalizeScheme","_Uri._makeUserInfo","_Uri._makePath","JSArray.map","_Uri._normalizePath","_Uri._makeQuery","_Uri._makeFragment","_Uri._normalizeEscape","_Uri._escapeChar","_Uri._normalizeOrSubstring","_Uri._normalize","_Uri._mayContainDotSegments","_Uri._removeDotSegments","JSArray.isNotEmpty","_Uri._normalizeRelativePath","_Uri._escapeScheme","_Uri._toWindowsFilePath","_Uri._hexCharPairToByte","_Uri._uriDecode","JSString.codeUnits","Utf8Codec.decode","_Uri._isAlphabeticCharacter","UriData._writeUri","UriData._validateMimeType","UriData._parse","UriData._uriEncodeBytes","_createTables","_scan","_convertDataTree","promiseToFuture","_Completer.future","Completer","max","pow","_EventStreamSubscription","_wrapZone","SpanScanner","SourceFile.decoded","SourceFile.fromString","RemoteListener.start","SuiteChannelManager","RemoteListener._deserializeSet","RemoteListener._sendLoadException","_MultiChannel.sink","RemoteListener._sendError","StackTraceFormatter.current","Style._getPlatformStyle","Pool","Pool._closeMemo","mapStackTrace","Trace","_prettifyMember","Group","Metadata._parseOnPlatform","Metadata._parseTags","Metadata","Metadata._","Metadata.parse","Metadata.deserialize","Metadata._deserializeTimeout","Engine","FutureGroup","Engine._onTestStartedGroup","StreamGroup.broadcast","StreamController.broadcast","Engine._group","binarySearch","mapMap","mergeMaps","UnionSetController","FileLocation._","_FileSpan","Trace.current","Trace.from","Trace.parse","Trace.parseVM","Trace._parseVM","ListIterable.map","Trace.parseV8","Trace.parseJSCore","WhereIterable.map","JSArray.where","Trace.parseFirefox","Trace.parseFriendly","PackageConfigResolver._normalizeMap","SourceLocation","LiveTestController","errorsDontStopTest","Invoker.current","StringScannerException","PlatformSelector.parse","PlatformSelector._wrapFormatException","SuitePlatform","JSStackTraceMapper.deserialize","JSStackTraceMapper._deserializePackageConfigMap","UnmodifiableSetView","decodeVlq","internalBootstrapBrowserTest","StreamChannelMixin.pipe","GuaranteeChannel.stream","SourceSpanFormatException","expect","_expect","Invoker.closed","Invoker._closable","_Completer.isCompleted","fail","formatFailure","prettyPrint","StringDescription._out","StringDescription.toString","StringBuffer.writeln","method1","method2","main","parseJsonExtended","parseJson","MultiSectionMapping.fromJson","MappingBundle.fromJson","SingleMapping.fromJson","ParsedPath.parse","PathException","SourceSpanWithContext","Declarer","Declarer._","Declarer._timeout","_expandSafe","Highlighter._normalizeNewlines","Highlighter._normalizeTrailingNewline","Highlighter._normalizeEndOfLine","Highlighter._lastLineLength","Chain.capture","Expando","StackZoneSpecification._chains","Chain.current","Chain._currentSpec","StackZoneSpecification.currentChain","StackZoneSpecification._createNode","Chain.forTrace","Chain.parse","Invoker.guard","Suite._filterGroup","Group.root","SuiteConfiguration._list","SuiteConfiguration._map","RemoteException.serialize","_declarer","Declarer.current","test","group","StreamChannelController","_StreamController.sink","Runtime.deserialize","indent","toSentence","pluralize","prefixLines","LiveSuiteController","LiveSuiteController._onCompleteGroup","LiveSuiteController._closeMemo","asUri","ensureTrailingSlash","JSArray.toList","isAlphabetic","isDriveLetter","countCodeUnits","ListMixin.iterator","findLineStart","validateErrorArgs","QueueList","QueueList._nextPowerOf2","wrapMatcher","predicate","equals","escape","_getHexLiteral","JSString.runes","Context","_parseUri","_validateArgList","_StringEqualsMatcher._writeLeading","_StringEqualsMatcher._writeTrailing","_MultiChannel","current","_typeName","_escapeString","Frame.parseVM","Frame.parseV8","Frame.parseFirefox","Frame.parseFriendly","Frame._uriOrPathToUri","Frame._catchFormatException","UnparsedFrame","postMessageChannel","EventStreamProvider.forTarget","OperatingSystem.find","GuaranteeChannel","ClosedException","Interceptor.hashCode","Interceptor.==","Interceptor.toString","Interceptor.runtimeType","JSBool.toString","JSBool.hashCode","JSBool.runtimeType","JSNull.==","JSNull.toString","JSNull.hashCode","JSNull.runtimeType","JavaScriptObject.hashCode","JavaScriptObject.runtimeType","JavaScriptObject.toString","JavaScriptFunction.toString","JSArray.add","JSArray.removeAt","JSArray.insert","JSArray.insertAll","JSArray.removeLast","JSArray.remove","JSArray.addAll","JSArray.forEach","JSArray.join","JSArray.join[function-entry$0]","JSArray.fold","JSArray.firstWhere","JSArray.firstWhere[function-entry$1]","JSArray.elementAt","JSArray.sublist","JSArray.first","JSArray.last","JSArray.single","JSArray.setRange","JSArray.setRange[function-entry$3]","JSArray.fillRange","JSArray.replaceRange","JSArray.contains","JSArray.isEmpty","JSArray.toString","JSArray.toSet","JSArray.hashCode","JSArray.length","JSArray.[]","JSArray.[]=","ArrayIterator.current","ArrayIterator.moveNext","ArrayIterator._current","JSNumber.floor","JSNumber.round","JSNumber.toRadixString","JSNumber.toString","JSNumber.hashCode","JSNumber.%","JSNumber.~/","JSNumber._tdivFast","JSNumber._tdivSlow","JSNumber._shlPositive","JSNumber._shrOtherPositive","JSNumber._shrReceiverPositive","JSNumber._shrBothPositive","JSNumber.runtimeType","JSInt.runtimeType","JSDouble.runtimeType","JSString.codeUnitAt","JSString._codeUnitAt","JSString.allMatches","allMatchesInStringUnchecked","JSString.allMatches[function-entry$1]","JSString.matchAsPrefix","JSString.+","JSString.endsWith","JSString.splitMapJoin","JSString.replaceFirst","JSString.replaceRange","JSString.startsWith","JSString.startsWith[function-entry$1]","JSString.substring","JSString.substring[function-entry$1]","JSString.trim","JSString.*","JSString.padLeft","JSString.padRight","JSString.indexOf","JSString.indexOf[function-entry$1]","JSString.lastIndexOf","JSString.lastIndexOf[function-entry$1]","JSString.contains","JSString.toString","JSString.hashCode","JSString.runtimeType","JSString.length","JSString.[]","_CastIterableBase.iterator","_CastIterableBase.length","_CastIterableBase.isEmpty","_CastIterableBase.first","_CastIterableBase.last","_CastIterableBase.contains","_CastIterableBase.toString","CastIterator.moveNext","CastIterator.current","CastMap.cast","CastMap.containsKey","CastMap.[]","CastMap.remove","CastMap.forEach","CastMap.keys","CastMap.length","CastMap.isEmpty","CastMap.forEach.<anonymous function>","CastMap_forEach_closure","CodeUnits.[]","CodeUnits.length","ListIterable.isEmpty","ListIterable.first","ListIterable.last","ListIterable.contains","ListIterable.join","ListIterable.join[function-entry$0]","ListIterable.fold","ListIterable.toList","ListIterable.toList[function-entry$0]","ListIterable.toSet","SubListIterable._endIndex","SubListIterable._startIndex","SubListIterable.length","SubListIterable.elementAt","SubListIterable.take","ListIterator.current","ListIterator.moveNext","ListIterator._current","MappedIterable.iterator","MappedIterable.length","MappedIterable.isEmpty","MappedIterable.first","MappedIterable.last","MappedIterator.moveNext","MappedIterator.current","MappedIterator._current","MappedListIterable.length","MappedListIterable.elementAt","WhereIterable.iterator","WhereIterator.moveNext","WhereIterator.current","ExpandIterable.iterator","ExpandIterator","ExpandIterator.current","ExpandIterator.moveNext","ExpandIterator._currentExpansion","ExpandIterator._current","SkipWhileIterable.iterator","SkipWhileIterator.moveNext","SkipWhileIterator.current","EmptyIterator.moveNext","EmptyIterator.current","FixedLengthListMixin.length","UnmodifiableListMixin.[]=","UnmodifiableListMixin.length","ReversedListIterable.length","ReversedListIterable.elementAt","Symbol.hashCode","Symbol.toString","Symbol.==","ConstantMap.cast","ConstantMap.isEmpty","ConstantMap.toString","ConstantMap.remove","ConstantMap.map","ConstantMap.map.<anonymous function>","ConstantMap_map_closure","ConstantStringMap.length","ConstantStringMap.containsKey","ConstantStringMap.[]","ConstantStringMap._fetch","ConstantStringMap.forEach","ConstantStringMap.keys","_ConstantMapKeyIterable.iterator","_ConstantMapKeyIterable.length","Instantiation","Instantiation.toString","Primitives.initTicker.<anonymous function>","TypeErrorDecoder.matchTypeError","NullError.toString","JsNoSuchMethodError.toString","UnknownJsTypeError.toString","unwrapException.saveStackTrace","_StackTrace.toString","Closure.toString","StaticClosure.toString","BoundClosure.==","BoundClosure.hashCode","BoundClosure.toString","TypeErrorImplementation.toString","RuntimeError.toString","_AssertionError.toString","JsLinkedHashMap.keys","JsLinkedHashMap.length","JsLinkedHashMap.isEmpty","JsLinkedHashMap.values","JsLinkedHashMap.containsKey","JsLinkedHashMap.internalContainsKey","JsLinkedHashMap.addAll","JsLinkedHashMap.[]","JsLinkedHashMap.internalGet","JsLinkedHashMap.[]=","JsLinkedHashMap.internalSet","JsLinkedHashMap.putIfAbsent","JsLinkedHashMap.remove","JsLinkedHashMap.internalRemove","JsLinkedHashMap.clear","JsLinkedHashMap.forEach","JsLinkedHashMap._addHashTableEntry","JsLinkedHashMap._removeHashTableEntry","JsLinkedHashMap._modified","JsLinkedHashMap._newLinkedCell","JsLinkedHashMap._unlinkCell","JsLinkedHashMap.internalComputeHashCode","JsLinkedHashMap.internalFindBucketIndex","JsLinkedHashMap.toString","JsLinkedHashMap._getTableCell","JsLinkedHashMap._getTableBucket","JsLinkedHashMap._setTableEntry","JsLinkedHashMap._deleteTableEntry","JsLinkedHashMap._containsTableEntry","JsLinkedHashMap._newHashTable","JsLinkedHashMap.values.<anonymous function>","JsLinkedHashMap_values_closure","JsLinkedHashMap.addAll.<anonymous function>","JsLinkedHashMap_addAll_closure","LinkedHashMapKeyIterable.length","LinkedHashMapKeyIterable.isEmpty","LinkedHashMapKeyIterable.iterator","LinkedHashMapKeyIterable.contains","LinkedHashMapKeyIterator","LinkedHashMapKeyIterator.current","LinkedHashMapKeyIterator.moveNext","LinkedHashMapKeyIterator._current","initHooks.<anonymous function>","JSSyntaxRegExp.toString","JSSyntaxRegExp._nativeGlobalVersion","JSSyntaxRegExp._nativeAnchoredVersion","JSSyntaxRegExp.firstMatch","JSSyntaxRegExp.allMatches","JSSyntaxRegExp.allMatches[function-entry$1]","JSSyntaxRegExp._execGlobal","JSSyntaxRegExp._execAnchored","JSSyntaxRegExp.matchAsPrefix","_MatchImplementation.start","_MatchImplementation.end","_MatchImplementation.[]","_AllMatchesIterator.current","_AllMatchesIterator.moveNext","JSSyntaxRegExp.isUnicode","StringMatch.end","StringMatch.[]","_StringAllMatchesIterable.iterator","_StringAllMatchesIterable.first","_StringAllMatchesIterator.moveNext","_StringAllMatchesIterator.current","NativeByteBuffer.runtimeType","NativeByteData.runtimeType","NativeTypedArray.length","NativeTypedArrayOfDouble.[]","NativeTypedArrayOfDouble.[]=","NativeTypedArrayOfInt.[]=","NativeFloat32List.runtimeType","NativeFloat64List.runtimeType","NativeInt16List.runtimeType","NativeInt16List.[]","NativeInt32List.runtimeType","NativeInt32List.[]","NativeInt8List.runtimeType","NativeInt8List.[]","NativeUint16List.runtimeType","NativeUint16List.[]","NativeUint32List.runtimeType","NativeUint32List.[]","NativeUint32List.sublist","NativeUint8ClampedList.runtimeType","NativeUint8ClampedList.length","NativeUint8ClampedList.[]","NativeUint8List.runtimeType","NativeUint8List.length","NativeUint8List.[]","NativeUint8List.sublist","Rti._eval","Rti._bind","_Type.hashCode","_Type.==","_Type.toString","_Error.toString","_TypeError.message","_AsyncRun._initializeScheduleImmediate.internalCallback","_AsyncRun._initializeScheduleImmediate.<anonymous function>","_AsyncRun._scheduleImmediateJsOverride.internalCallback","_AsyncRun._scheduleImmediateWithSetImmediate.internalCallback","_TimerImpl.cancel","_TimerImpl.internalCallback","_TimerImpl.periodic.<anonymous function>","_AsyncAwaitCompleter.complete","_AsyncAwaitCompleter.completeError","_awaitOnObject.<anonymous function>","_wrapJsFunctionForAsync.<anonymous function>","_BroadcastStream.isBroadcast","_BroadcastSubscription._onPause","_BroadcastSubscription._onResume","_BroadcastSubscription._next","_BroadcastSubscription._previous","_BroadcastStreamController._mayAddEvent","_BroadcastStreamController._ensureDoneFuture","_BroadcastStreamController._removeListener","_BroadcastStreamController._subscribe","_DoneStreamSubscription","_BroadcastSubscription","_BroadcastStreamController._recordCancel","_BroadcastStreamController._recordPause","_BroadcastStreamController._recordResume","_BroadcastStreamController._addEventError","_BroadcastStreamController.add","_BroadcastStreamController.addError","_BroadcastStreamController.addError[function-entry$1]","_BroadcastStreamController.close","_BroadcastStreamController._addError","_BroadcastStreamController._close","_BroadcastStreamController._forEachListener","_BroadcastStreamController._callOnCancel","_BroadcastStreamController._firstSubscription","_BroadcastStreamController._lastSubscription","_BroadcastStreamController._addStreamState","_SyncBroadcastStreamController._mayAddEvent","_SyncBroadcastStreamController._addEventError","_SyncBroadcastStreamController._sendData","_SyncBroadcastStreamController._sendError","_SyncBroadcastStreamController._sendDone","_SyncBroadcastStreamController._sendData.<anonymous function>","_SyncBroadcastStreamController__sendData_closure","_SyncBroadcastStreamController._sendError.<anonymous function>","_SyncBroadcastStreamController__sendError_closure","_SyncBroadcastStreamController._sendDone.<anonymous function>","_SyncBroadcastStreamController__sendDone_closure","_AsyncBroadcastStreamController._sendData","_AsyncBroadcastStreamController._sendError","_AsyncBroadcastStreamController._sendDone","Future.<anonymous function>","Future.microtask.<anonymous function>","Future.wait.handleError","Future.wait.<anonymous function>","Future_wait_closure","Future.forEach.<anonymous function>","Future.doWhile.<anonymous function>","_asyncCompleteWithErrorCallback","TimeoutException.toString","_Completer.completeError","_Completer.completeError[function-entry$1]","_AsyncCompleter.complete","_AsyncCompleter.complete[function-entry$0]","_AsyncCompleter._completeError","_SyncCompleter.complete","_SyncCompleter.complete[function-entry$0]","_SyncCompleter._completeError","_FutureListener.matchesErrorTest","_FutureListener.handleError","_FutureListener.hasErrorCallback","_Future.then","_Future.then[function-entry$1]","_Future._thenAwait","_Future.catchError","_Future.whenComplete","_Future._addListener","_Future._prependListeners","_Future._reverseListeners","_Future._complete","_Future._setValue","_Future._completeWithValue","_Future._completeError","_Future._setError","_Future._completeError[function-entry$1]","_Future._asyncComplete","_Future._chainFuture","_Future._asyncCompleteError","_Future._addListener.<anonymous function>","_Future._prependListeners.<anonymous function>","_Future._chainForeignFuture.<anonymous function>","_Future._clearPendingComplete","_Future._chainForeignFuture[function-entry$1].<anonymous function>","_Future._asyncComplete.<anonymous function>","_Future._chainFuture.<anonymous function>","_Future._asyncCompleteError.<anonymous function>","_Future._propagateToListeners.handleWhenCompleteCallback","_FutureListener.handleWhenComplete","_Future._propagateToListeners.handleWhenCompleteCallback.<anonymous function>","_Future._propagateToListeners.handleValueCallback","_FutureListener.handleValue","_FutureListener._onValue","_Future._propagateToListeners.handleError","Stream.isBroadcast","Stream.pipe","Stream.length","Stream.first","Stream.last","Stream.firstWhere","Stream.fromFuture.<anonymous function>","Stream_Stream$fromFuture_closure","Stream.fromIterable.<anonymous function>","_IterablePendingEvents","Stream_Stream$fromIterable_closure","Stream.pipe.<anonymous function>","Stream.length.<anonymous function>","Stream_length_closure","Stream.first.<anonymous function>","Stream_first_closure","Stream.last.<anonymous function>","Stream_last_closure","Stream.firstWhere.<anonymous function>","Stream_firstWhere_closure","Stream.firstWhere.<anonymous function>.<anonymous function>","_StreamController._pendingEvents","_StreamController._ensurePendingEvents","_StreamController._subscription","_StreamController._badEventState","_StreamController.addStream","_AddStreamState","_StreamControllerAddStreamState","_StreamController.isPaused","_StreamController._ensureDoneFuture","_StreamController.add","_StreamController.addError","_StreamController.addError[function-entry$1]","_StreamController.close","_StreamController._closeUnchecked","_StreamController._add","_StreamController._addError","_StreamController._close","_StreamController._subscribe","_ControllerSubscription","_StreamController._recordCancel","_StreamController._recordPause","_StreamController._recordResume","_StreamController._subscribe.<anonymous function>","_StreamController._recordCancel.complete","_SyncStreamControllerDispatch._sendData","_SyncStreamControllerDispatch._sendError","_SyncStreamControllerDispatch._sendDone","_AsyncStreamControllerDispatch._sendData","_AsyncStreamControllerDispatch._sendError","_AsyncStreamControllerDispatch._sendDone","_ControllerStream._createSubscription","_ControllerStream.hashCode","_ControllerStream.==","_ControllerSubscription._onCancel","_ControllerSubscription._onPause","_ControllerSubscription._onResume","_StreamSinkWrapper.add","_AddStreamState.cancel","_AddStreamState.makeErrorHandler.<anonymous function>","_AddStreamState.cancel.<anonymous function>","_BufferingStreamSubscription._setPendingEvents","_BufferingStreamSubscription.onData","_BufferingStreamSubscription.onError","_BufferingStreamSubscription.onDone","_BufferingStreamSubscription.pause","_BufferingStreamSubscription.pause[function-entry$0]","_BufferingStreamSubscription.resume","_BufferingStreamSubscription.cancel","_BufferingStreamSubscription._mayResumeInput","_BufferingStreamSubscription.isPaused","_BufferingStreamSubscription._cancel","_BufferingStreamSubscription._add","_BufferingStreamSubscription._addError","_BufferingStreamSubscription._close","_BufferingStreamSubscription._onPause","_BufferingStreamSubscription._onResume","_BufferingStreamSubscription._onCancel","_BufferingStreamSubscription._addPending","_BufferingStreamSubscription._sendData","_BufferingStreamSubscription._sendError","_BufferingStreamSubscription._sendDone","_BufferingStreamSubscription._guardCallback","_BufferingStreamSubscription._checkState","_BufferingStreamSubscription._onData","_BufferingStreamSubscription._onDone","_BufferingStreamSubscription._pending","_BufferingStreamSubscription._sendError.sendError","_BufferingStreamSubscription._sendDone.sendDone","_StreamImpl.listen","_StreamImpl.listen[function-entry$1$onDone]","_StreamImpl.listen[function-entry$1$onDone$onError]","_StreamImpl.listen[function-entry$1]","_StreamImpl._createSubscription","_GeneratedStreamImpl._createSubscription","_IterablePendingEvents.isEmpty","_IterablePendingEvents.handleNext","_IterablePendingEvents._iterator","_DelayedEvent.next","_DelayedData.perform","_DelayedError.perform","_DelayedDone.perform","_DelayedDone.next","_PendingEvents.schedule","_PendingEvents.schedule.<anonymous function>","_StreamImplEvents.isEmpty","_StreamImplEvents.add","_StreamImplEvents.handleNext","_DoneStreamSubscription.isPaused","_DoneStreamSubscription._schedule","_DoneStreamSubscription.onData","_DoneStreamSubscription.onError","_DoneStreamSubscription.onDone","_DoneStreamSubscription.pause","_DoneStreamSubscription.pause[function-entry$0]","_DoneStreamSubscription.resume","_DoneStreamSubscription.cancel","_DoneStreamSubscription._sendDone","_DoneStreamSubscription._onDone","_EmptyStream.isBroadcast","_EmptyStream.listen","_EmptyStream.listen[function-entry$1$onDone$onError]","_EmptyStream.listen[function-entry$1]","_cancelAndError.<anonymous function>","_cancelAndErrorClosure.<anonymous function>","_cancelAndValue.<anonymous function>","AsyncError.toString","_ZoneDelegate.handleUncaughtError","_ZoneDelegate.registerCallback","_ZoneDelegate.registerUnaryCallback","_ZoneDelegate.registerBinaryCallback","_ZoneDelegate.errorCallback","_CustomZone._delegate","_CustomZone.errorZone","_CustomZone.runGuarded","_CustomZone.runUnaryGuarded","_CustomZone.runBinaryGuarded","_CustomZone.bindCallback","_CustomZone.bindUnaryCallback","_CustomZone.bindCallbackGuarded","_CustomZone.bindUnaryCallbackGuarded","_CustomZone.[]","_CustomZone.handleUncaughtError","_CustomZone.fork","_CustomZone.run","_CustomZone.runUnary","_CustomZone.runBinary","_CustomZone.registerCallback","_CustomZone.registerUnaryCallback","_CustomZone.registerBinaryCallback","_CustomZone.errorCallback","_CustomZone.scheduleMicrotask","_CustomZone.createTimer","_CustomZone.print","_CustomZone._run","_CustomZone._runUnary","_CustomZone._runBinary","_CustomZone._registerCallback","_CustomZone._registerUnaryCallback","_CustomZone._registerBinaryCallback","_CustomZone._errorCallback","_CustomZone._scheduleMicrotask","_CustomZone._createTimer","_CustomZone._createPeriodicTimer","_CustomZone._print","_CustomZone._fork","_CustomZone._handleUncaughtError","_CustomZone.bindCallback.<anonymous function>","_CustomZone_bindCallback_closure","_CustomZone.bindUnaryCallback.<anonymous function>","_CustomZone_bindUnaryCallback_closure","_CustomZone.bindCallbackGuarded.<anonymous function>","_CustomZone.bindUnaryCallbackGuarded.<anonymous function>","_CustomZone_bindUnaryCallbackGuarded_closure","_rootHandleUncaughtError.<anonymous function>","_RootZone._map","_RootZone._run","_RootZone._runUnary","_RootZone._runBinary","_RootZone._registerCallback","_RootZone._registerUnaryCallback","_RootZone._registerBinaryCallback","_RootZone._errorCallback","_RootZone._scheduleMicrotask","_RootZone._createTimer","_RootZone._createPeriodicTimer","_RootZone._print","_RootZone._fork","_RootZone._handleUncaughtError","_RootZone.parent","_RootZone._delegate","_RootZone.errorZone","_RootZone.runGuarded","_RootZone.runUnaryGuarded","_RootZone.runBinaryGuarded","_RootZone.bindCallback","_RootZone.bindCallbackGuarded","_RootZone.bindUnaryCallbackGuarded","_RootZone.[]","_RootZone.handleUncaughtError","_RootZone.fork","_RootZone.run","_RootZone.runUnary","_RootZone.runBinary","_RootZone.registerCallback","_RootZone.registerUnaryCallback","_RootZone.registerBinaryCallback","_RootZone.errorCallback","_RootZone.scheduleMicrotask","_RootZone.createTimer","_RootZone.print","_RootZone.bindCallback.<anonymous function>","_RootZone_bindCallback_closure","_RootZone.bindCallbackGuarded.<anonymous function>","_RootZone.bindUnaryCallbackGuarded.<anonymous function>","_RootZone_bindUnaryCallbackGuarded_closure","runZoned.<anonymous function>","_HashMap.keys","_HashMap.length","_HashMap.isEmpty","_HashMap.containsKey","_HashMap._containsKey","_HashMap.[]","_HashMap._get","_HashMap.[]=","_HashMap._set","_HashMap.remove","_HashMap._remove","_HashMap.forEach","_HashMap._computeKeys","_HashMap._addHashTableEntry","_HashMap._computeHashCode","_HashMap._getBucket","_HashMap._findBucketIndex","_IdentityHashMap._computeHashCode","_IdentityHashMap._findBucketIndex","_HashMapKeyIterable.length","_HashMapKeyIterable.isEmpty","_HashMapKeyIterable.iterator","_HashMapKeyIterable.contains","_HashMapKeyIterator.current","_HashMapKeyIterator.moveNext","_HashMapKeyIterator._current","_LinkedHashSet._newSet","_LinkedHashSet.iterator","_LinkedHashSet.length","_LinkedHashSet.isEmpty","_LinkedHashSet.contains","_LinkedHashSet._contains","_LinkedHashSet.first","_LinkedHashSet.last","_LinkedHashSet.add","_LinkedHashSet._add","_LinkedHashSet.remove","_LinkedHashSet._remove","_LinkedHashSet._addHashTableEntry","_LinkedHashSet._removeHashTableEntry","_LinkedHashSet._modified","_LinkedHashSet._newLinkedCell","_LinkedHashSet._unlinkCell","_LinkedHashSet._computeHashCode","_LinkedHashSet._findBucketIndex","_LinkedHashSetIterator.current","_LinkedHashSetIterator.moveNext","_LinkedHashSetIterator._current","UnmodifiableListView.length","UnmodifiableListView.[]","HashMap.from.<anonymous function>","LinkedHashMap.from.<anonymous function>","ListMixin.elementAt","ListMixin.isEmpty","ListMixin.first","ListMixin.last","ListMixin.map","ListMixin.toList","ListMixin.toList[function-entry$0]","ListMixin.toSet","ListMixin.remove","ListMixin._closeGap","ListMixin.fillRange","ListMixin.toString","MapBase.mapToString.<anonymous function>","MapMixin.cast","MapMixin.forEach","MapMixin.map","MapMixin.containsKey","MapMixin.length","MapMixin.isEmpty","MapMixin.toString","_UnmodifiableMapMixin.remove","MapView.cast","MapView.[]","MapView.containsKey","MapView.forEach","MapView.isEmpty","MapView.length","MapView.keys","MapView.remove","MapView.toString","MapView.map","UnmodifiableMapView.cast","ListQueue.iterator","ListQueue.isEmpty","ListQueue.length","ListQueue.first","ListQueue.last","ListQueue.elementAt","ListQueue.clear","ListQueue.toString","ListQueue.removeFirst","ListQueue._add","ListQueue._table","_ListQueueIterator.current","_ListQueueIterator.moveNext","_ListQueueIterator._current","SetMixin.isEmpty","SetMixin.map","SetMixin.toString","SetMixin.every","SetMixin.first","SetMixin.last","_SetBase.toSet","_SetBase.isEmpty","_SetBase.addAll","_SetBase.union","_SetBase.toList","_SetBase.toList[function-entry$0]","_SetBase.map","_SetBase.toString","_SetBase.where","_SetBase.fold","_SetBase.every","_SetBase.any","_SetBase.first","_SetBase.last","_JsonMap.[]","_JsonMap.length","_JsonMap.isEmpty","_JsonMap.keys","_JsonMap.containsKey","_JsonMap.remove","_JsonMap.forEach","_JsonMap._upgradedMap","_JsonMap._computeKeys","_JsonMap._upgrade","_JsonMap._process","_JsonMapKeyIterable.length","_JsonMapKeyIterable.elementAt","_JsonMapKeyIterable.iterator","_JsonMapKeyIterable.contains","AsciiCodec.encode","_UnicodeSubsetEncoder.convert","Base64Codec.normalize","JsonCodec.decode","JsonCodec.decoder","Utf8Codec.encoder","Utf8Encoder.convert","_Utf8Encoder._writeSurrogate","_Utf8Encoder._fillBuffer","Utf8Decoder.convert","_Utf8Decoder.flush","_Utf8Decoder.convert","DateTime.==","DateTime.hashCode","DateTime.toString","Duration.==","Duration.hashCode","Duration.toString","Duration.unary-","Duration.toString.sixDigits","Duration.toString.twoDigits","AssertionError.toString","NullThrownError.toString","ArgumentError._errorName","ArgumentError._errorExplanation","ArgumentError.toString","RangeError._errorName","RangeError._errorExplanation","IndexError._errorName","IndexError._errorExplanation","UnsupportedError.toString","UnimplementedError.toString","StateError.toString","ConcurrentModificationError.toString","OutOfMemoryError.toString","StackOverflowError.toString","CyclicInitializationError.toString","_Exception.toString","FormatException.toString","Expando.[]","Expando.[]=","Expando._setOnObject","Expando.toString","Iterable.map","Iterable.where","Iterable.contains","Iterable.join","Iterable.join[function-entry$0]","Iterable.toList","Iterable.toList[function-entry$0]","Iterable.toSet","Iterable.length","Iterable.isEmpty","Iterable.skipWhile","Iterable.first","Iterable.last","Iterable.elementAt","Iterable.toString","MapEntry.toString","Null.hashCode","Null.toString","Object.hashCode","Object.==","Object.toString","Object.runtimeType","_StringStackTrace.toString","Stopwatch.elapsedMicroseconds","Stopwatch.elapsedTicks","Runes.iterator","Runes.last","RuneIterator.current","RuneIterator.moveNext","StringBuffer.length","StringBuffer.toString","Uri._parseIPv4Address.error","Uri.parseIPv6Address.error","Uri.parseIPv6Address[function-entry$1].error","Uri.parseIPv6Address.parseHex","_Uri.userInfo","_Uri.host","_Uri.port","_Uri.query","_Uri.fragment","_Uri.replace","_Uri.replace[function-entry$0$path]","_Uri.replace[function-entry$0$pathSegments]","_Uri.pathSegments","_Uri._mergePaths","_Uri.resolve","_Uri.resolveUri","_Uri.hasEmptyPath","_Uri.hasAuthority","_Uri.hasPort","_Uri.hasQuery","_Uri.hasFragment","_Uri.hasAbsolutePath","_Uri.toFilePath","_Uri._toFilePath","_Uri.toString","_Uri._initializeText","_Uri._writeAuthority","_Uri.==","_Uri.hashCode","_Uri._pathSegments","_Uri.notSimple.<anonymous function>","_Uri._checkNonWindowsPathReservedCharacters.<anonymous function>","_Uri._makePath.<anonymous function>","UriData.uri","UriData.toString","_createTables.<anonymous function>","_createTables.build","_createTables.setChars","_createTables.setRange","_SimpleUri._isFile","_SimpleUri.hasAuthority","_SimpleUri.hasPort","_SimpleUri.hasQuery","_SimpleUri.hasFragment","_SimpleUri._isHttp","_SimpleUri._isHttps","_SimpleUri.hasAbsolutePath","_SimpleUri.scheme","_SimpleUri.userInfo","_SimpleUri.host","_SimpleUri.port","_SimpleUri.path","_SimpleUri.query","_SimpleUri.fragment","_SimpleUri.pathSegments","_SimpleUri._isPort","_SimpleUri.removeFragment","_SimpleUri.replace","_SimpleUri.replace[function-entry$0$path]","_SimpleUri.replace[function-entry$0$pathSegments]","_SimpleUri.resolve","_SimpleUri.resolveUri","_SimpleUri._simpleMerge","_SimpleUri.toFilePath","_SimpleUri._toFilePath","_SimpleUri.hashCode","_SimpleUri.==","_SimpleUri._toNonSimple","_SimpleUri.toString","DomException.toString","EventTarget.addEventListener","EventTarget._addEventListener","EventTarget._removeEventListener","Location.origin","Location.toString","MessagePort.addEventListener","MessagePort.postMessage","convertDartToNative_PrepareForStructuredClone","_EventStream.isBroadcast","_EventStream.listen","_EventStream.listen[function-entry$1$onDone$onError]","_EventStream.listen[function-entry$1]","_EventStreamSubscription.cancel","_EventStreamSubscription.pause","_EventStreamSubscription.pause[function-entry$0]","_EventStreamSubscription.resume","_EventStreamSubscription._tryResume","_EventStreamSubscription._unlisten","_EventStreamSubscription._onData","_EventStreamSubscription.<anonymous function>","_StructuredClone.findSlot","_StructuredClone.walk","convertDartToNative_DateTime","_StructuredClone.copyList","_StructuredClone.walk.<anonymous function>","_AcceptStructuredClone.findSlot","_AcceptStructuredClone.walk","DateTime._withValue","convertNativeToDart_DateTime","_AcceptStructuredClone.convertNativeToDart_AcceptStructuredClone","_AcceptStructuredClone.walk.<anonymous function>","_StructuredCloneDart2Js.forEachObjectKey","_AcceptStructuredCloneDart2Js.forEachJsField","_convertDataTree._convert","promiseToFuture.<anonymous function>","AsyncMemoizer.runOnce","AsyncMemoizer.hasRun","DelegatingStreamSubscription.onData","DelegatingStreamSubscription.onError","DelegatingStreamSubscription.onDone","DelegatingStreamSubscription.pause","DelegatingStreamSubscription.pause[function-entry$0]","DelegatingStreamSubscription.resume","DelegatingStreamSubscription.cancel","FutureGroup.add","FutureGroup.close","FutureGroup.add.<anonymous function>","FutureGroup_add_closure","NullStreamSink.add","NullStreamSink.addStream","NullStreamSink._checkEventAllowed","NullStreamSink.close","NullStreamSink.addStream.<anonymous function>","ErrorResult.complete","ErrorResult.addTo","ErrorResult.hashCode","ErrorResult.==","ValueResult.complete","ValueResult.addTo","ValueResult.hashCode","ValueResult.==","StreamCompleter.setSourceStream","_CompleterStream.listen","_CompleterStream.listen[function-entry$1$onDone$onError]","_CompleterStream.listen[function-entry$1]","_CompleterStream._linkStreamToController","_CompleterStream._createController","_CompleterStream._controller","_CompleterStream._sourceStream","StreamGroup.add","StreamGroup._onListen","StreamGroup._onCancelBroadcast","StreamGroup._listenToStream","StreamGroup.close","StreamGroup._controller","StreamGroup.add.<anonymous function>","StreamGroup_add_closure","StreamGroup._onListen.<anonymous function>","StreamGroup__onListen_closure","StreamGroup._onCancelBroadcast.<anonymous function>","StreamGroup__onCancelBroadcast_closure","StreamGroup._listenToStream.<anonymous function>","_StreamGroupState.toString","StreamQueue.next","StreamQueue._updateRequests","StreamQueue._extractStream","SubscriptionStream","StreamQueue._ensureListening","StreamQueue._addResult","StreamQueue._failClosed","StreamQueue._addRequest","StreamQueue._subscription","StreamQueue._ensureListening.<anonymous function>","StreamQueue__ensureListening_closure","Result.error","_NextRequest.update","ListMixin.isNotEmpty","_RestRequest.update","StreamCompleter.setEmpty","_CompleterStream._setEmpty","_CompleterSink._canSendDirectly","_CompleterSink.done","Completer.sync","_CompleterSink.addStream","_CompleterSink.close","_CompleterSink._ensureController","_CompleterSink._setDestinationSink","_CompleterSink._controller","_CompleterSink._destinationSink","_CompleterSink._setDestinationSink.<anonymous function>","SubscriptionStream.listen","SubscriptionStream.listen[function-entry$1$onDone$onError]","SubscriptionStream.listen[function-entry$1]","SubscriptionStream._source","_CancelOnErrorSubscriptionWrapper.onError","_CancelOnErrorSubscriptionWrapper.onError.<anonymous function>","_CancelOnErrorSubscriptionWrapper.onError.<anonymous function>.<anonymous function>","All.evaluate","All.intersection","All.validate","All.toString","VariableNode.accept","VariableNode.toString","VariableNode.==","VariableNode.hashCode","NotNode.accept","NotNode.toString","NotNode.==","NotNode.hashCode","OrNode.span","OrNode.accept","OrNode.toString","OrNode.==","OrNode.hashCode","AndNode.span","AndNode.accept","AndNode.toString","AndNode.==","AndNode.hashCode","ConditionalNode.span","ConditionalNode.accept","ConditionalNode.toString","ConditionalNode.==","ConditionalNode.hashCode","Evaluator.visitVariable","Evaluator.visitNot","Evaluator.visitOr","Evaluator.visitAnd","Evaluator.visitConditional","BooleanSelectorImpl.evaluate","BooleanSelectorImpl.intersection","BooleanSelectorImpl.validate","BooleanSelectorImpl.toString","BooleanSelectorImpl.==","BooleanSelectorImpl.hashCode","IntersectionSelector.evaluate","IntersectionSelector.intersection","IntersectionSelector.validate","IntersectionSelector.toString","IntersectionSelector.==","IntersectionSelector.hashCode","None.evaluate","None.intersection","None.validate","None.toString","Parser.parse","Parser._conditional","Parser._or","Parser._and","Parser._simpleExpression","Scanner.peek","Scanner.next","Scanner.scan","Scanner._getNext","StringScanner.isDone","SpanScanner.state","Scanner._scanOr","Scanner._scanAnd","Scanner._scanIdentifier","Scanner._scanOperator","StringScanner.readChar","Scanner._consumeWhitespace","Scanner._multiLineComment","IdentifierToken.toString","TokenType.toString","Validator.visitVariable","RecursiveVisitor.visitNot","RecursiveVisitor.visitOr","RecursiveVisitor.visitAnd","RecursiveVisitor.visitConditional","EmptyUnmodifiableSet.toSet","EmptyUnmodifiableSet.iterator","EmptyUnmodifiableSet.length","EmptyUnmodifiableSet.contains","mapMap.<anonymous function>","mapMap_closure","mergeMaps.<anonymous function>","mergeMaps_closure","QueueList.toString","QueueList.removeFirst","QueueList.length","QueueList.[]","QueueList.[]=","QueueList._add","QueueList._writeToList","QueueList._preGrow","QueueList._table","UnionSet.length","UnionSet.iterator","UnionSet._iterable","_SetBase.expand","UnionSet.toSet","UnionSet.length.<anonymous function>","UnionSet_length_closure","UnionSet._iterable.<anonymous function>","UnionSet__iterable_closure","UnionSetController._set","_DelegatingIterableBase.contains","_DelegatingIterableBase.every","_DelegatingIterableBase.first","_DelegatingIterableBase.isEmpty","_DelegatingIterableBase.iterator","_DelegatingIterableBase.last","_DelegatingIterableBase.length","_DelegatingIterableBase.map","_DelegatingIterableBase.toList","_DelegatingIterableBase.toList[function-entry$0]","_DelegatingIterableBase.toSet","_DelegatingIterableBase.where","_DelegatingIterableBase.toString","DelegatingSet.union","DelegatingSet.toSet","_IsTrue.matches","_IsTrue.describe","_Predicate.typedMatches","_Predicate.describe","StringDescription.length","StringDescription.addDescriptionOf","_StringEqualsMatcher.typedMatches","_StringEqualsMatcher.describe","_StringEqualsMatcher.describeTypedMismatch","_DeepMatcher._compareIterables","_DeepMatcher._compareSets","_DeepMatcher._recursiveMatch","_DeepMatcher._match","_DeepMatcher.matches","_DeepMatcher.describe","_DeepMatcher.describeMismatch","_DeepMatcher._compareSets.<anonymous function>","FeatureMatcher.matches","FeatureMatcher.describeMismatch","FeatureMatcher.describeTypedMismatch","Matcher.describeMismatch","prettyPrint._prettyPrint","prettyPrint._prettyPrint.pp","prettyPrint._prettyPrint.<anonymous function>","TypeMatcher.describe","_stripDynamic","TypeMatcher.matches","wrapMatcher.<anonymous function>","escape.<anonymous function>","PackageConfigResolver._normalizeMap.<anonymous function>","Context.absolute","Context.absolute[function-entry$1]","Context.join","Context.join[function-entry$2]","Context.joinAll","Context.split","Context.normalize","Context._needsNormalization","Context.relative","Context.isRelative","Context.relative[function-entry$1]","Context._isWithinOrEquals","Context._isWithinOrEqualsFast","Context._pathDirection","Context.toUri","Context.prettyUri","Context.join.<anonymous function>","Context.joinAll.<anonymous function>","Context.split.<anonymous function>","_validateArgList.<anonymous function>","_PathDirection.toString","_PathRelation.toString","InternalStyle.getRoot","InternalStyle.relativePathToUri","InternalStyle.codeUnitsEqual","InternalStyle.pathsEqual","ParsedPath.hasTrailingSeparator","ParsedPath.removeTrailingSeparators","ParsedPath.normalize","ParsedPath.toString","ParsedPath.parts","ParsedPath.separators","ParsedPath.normalize.<anonymous function>","PathException.toString","Style.toString","PosixStyle.containsSeparator","PosixStyle.isSeparator","PosixStyle.needsSeparator","PosixStyle.rootLength","PosixStyle.rootLength[function-entry$1]","PosixStyle.isRootRelative","PosixStyle.pathFromUri","PosixStyle.absolutePathToUri","UrlStyle.containsSeparator","UrlStyle.isSeparator","UrlStyle.needsSeparator","UrlStyle.rootLength","UrlStyle.rootLength[function-entry$1]","UrlStyle.isRootRelative","UrlStyle.pathFromUri","UrlStyle.relativePathToUri","UrlStyle.absolutePathToUri","WindowsStyle.containsSeparator","WindowsStyle.isSeparator","WindowsStyle.needsSeparator","WindowsStyle.rootLength","WindowsStyle.rootLength[function-entry$1]","WindowsStyle.isRootRelative","WindowsStyle.pathFromUri","WindowsStyle.absolutePathToUri","WindowsStyle.codeUnitsEqual","WindowsStyle.pathsEqual","WindowsStyle.absolutePathToUri.<anonymous function>","Pool.request","Pool.isClosed","Pool.withResource","Pool.close","Pool._onResourceReleaseAllowed","Pool._runOnRelease","Pool._resetTimer","Pool.close.<anonymous function>","Pool._onResourceReleaseAllowed.<anonymous function>","Pool._runOnRelease.<anonymous function>","PoolResource.release","Pool._onResourceReleased","mapStackTrace.<anonymous function>","_prettifyMember.<anonymous function>","MultiSectionMapping._indexFor","MultiSectionMapping.spanFor","MultiSectionMapping.spanFor[function-entry$2$uri]","MultiSectionMapping.spanFor[function-entry$2$files]","MultiSectionMapping.toString","MappingBundle.toString","MappingBundle.spanFor","SourceMapSpan","MappingBundle.spanFor[function-entry$2$uri]","SingleMapping._segmentError","SingleMapping._findLine","SingleMapping._findColumn","SingleMapping.spanFor","SourceMapSpan.identifier","SingleMapping.spanFor[function-entry$2$uri]","SingleMapping.spanFor[function-entry$2$files]","SingleMapping.toString","SingleMapping.fromJson.<anonymous function>","SingleMapping._findLine.<anonymous function>","SingleMapping._findColumn.<anonymous function>","TargetLineEntry.toString","TargetEntry.toString","_MappingTokenizer.moveNext","_MappingTokenizer.current","_MappingTokenizer.hasTokens","_MappingTokenizer.nextKind","_MappingTokenizer.toString","_digits.<anonymous function>","SourceFile.length","SourceFile.lines","SourceFile.span","SourceFile.getLine","SourceFile._isNearCachedLine","SourceFile._binarySearch","SourceFile.getColumn","SourceFile.getOffset","SourceFile.getOffset[function-entry$1]","FileLocation.line","FileLocation.sourceUrl","FileLocation.column","_FileSpan.start","_FileSpan.sourceUrl","_FileSpan.length","_FileSpan.end","_FileSpan.text","_FileSpan.context","_FileSpan.==","_FileSpan.hashCode","_FileSpan.expand","Highlighter.highlight","downEnd","upEnd","Highlighter._writeFirstLine","Highlighter._writeIntermediateLines","Highlighter._writeLastLine","Highlighter._writeTrailingLines","Highlighter._writeText","Highlighter._writeSidebar","Highlighter._writeSidebar[function-entry$0$end]","Highlighter._writeSidebar[function-entry$0$line]","Highlighter._writeSidebar[function-entry$0]","Highlighter._countTabs","Highlighter._isOnlyWhitespace","Highlighter._colorize","Highlighter._colorize[function-entry$1]","Highlighter._writeFirstLine.<anonymous function>","glyphOrAscii","topLeftCorner","horizontalLine","Highlighter._writeIntermediateLines.<anonymous function>","verticalLine","Highlighter._writeLastLine.<anonymous function>","bottomLeftCorner","Highlighter._writeSidebar.<anonymous function>","SourceLocation.distance","SourceLocation.==","SourceLocation.hashCode","SourceLocation.toString","SourceLocationMixin.distance","SourceLocationMixin.==","SourceLocationMixin.hashCode","SourceLocationMixin.toString","SourceLocationMixin.toolString","SourceSpanBase","SourceSpanException.message","SourceSpanException.toString","SourceSpanException.toString[function-entry$0]","SourceSpanMixin.sourceUrl","SourceSpanMixin.length","SourceSpanMixin.message","SourceSpanMixin.message[function-entry$1]","SourceSpanMixin.highlight","Highlighter","Highlighter._buffer","SourceSpanMixin.==","SourceSpanMixin.hashCode","SourceSpanMixin.toString","SourceSpanWithContext.context","Chain.foldFrames","Chain.toTrace","JSArray.expand","Chain.toString","Chain.capture.<anonymous function>","Chain_capture_closure","Chain.current.<anonymous function>","Chain.forTrace.<anonymous function>","Chain.parse.<anonymous function>","Chain.foldFrames.<anonymous function>","Chain.toTrace.<anonymous function>","Chain.toString.<anonymous function>","Chain.toString.<anonymous function>.<anonymous function>","Frame.isCore","Frame.library","Frame.package","Frame.location","Frame.toString","Frame.parseVM.<anonymous function>","Frame.parseV8.<anonymous function>","Frame.parseV8.<anonymous function>.parseLocation","Frame.parseFirefox.<anonymous function>","Frame.parseFriendly.<anonymous function>","UriData.fromString","Uri.dataFromString","fromUri","LazyChain._chain","LazyChain.traces","LazyChain.foldFrames","LazyChain.toTrace","LazyChain.toString","LazyChain._inner","LazyChain.foldFrames.<anonymous function>","LazyChain.toTrace.<anonymous function>","LazyTrace._trace","LazyTrace.frames","LazyTrace.original","LazyTrace.foldFrames","LazyTrace.toString","LazyTrace._inner","LazyTrace.foldFrames.<anonymous function>","StackZoneSpecification.chainFor","StackZoneSpecification._registerCallback","StackZoneSpecification._disabled","StackZoneSpecification._registerCallback[function-entry$4]","StackZoneSpecification._registerUnaryCallback","StackZoneSpecification._registerUnaryCallback[function-entry$4]","StackZoneSpecification._registerBinaryCallback","StackZoneSpecification._registerBinaryCallback[function-entry$4]","StackZoneSpecification._errorCallback","StackZoneSpecification._run","StackZoneSpecification._currentTrace","StackZoneSpecification._trimVMChain","StackZoneSpecification._currentNode","StackZoneSpecification.chainFor.<anonymous function>","StackZoneSpecification._registerCallback.<anonymous function>","StackZoneSpecification__registerCallback_closure","StackZoneSpecification._registerUnaryCallback.<anonymous function>","StackZoneSpecification__registerUnaryCallback_closure","StackZoneSpecification._registerUnaryCallback.<anonymous function>.<anonymous function>","StackZoneSpecification__registerUnaryCallback__closure","StackZoneSpecification._registerBinaryCallback.<anonymous function>","StackZoneSpecification__registerBinaryCallback_closure","StackZoneSpecification._registerBinaryCallback.<anonymous function>.<anonymous function>","StackZoneSpecification__registerBinaryCallback__closure","StackZoneSpecification._currentTrace.<anonymous function>","_Node.toChain","Trace.foldFrames","JSArray.reversed","Trace.toString","Trace.current.<anonymous function>","Trace.from.<anonymous function>","Trace._parseVM.<anonymous function>","Trace.parseV8.<anonymous function>","Trace.parseJSCore.<anonymous function>","Trace.parseFirefox.<anonymous function>","Trace.parseFriendly.<anonymous function>","Trace.foldFrames.<anonymous function>","Trace.toString.<anonymous function>","UnparsedFrame.toString","GuaranteeChannel.sink","GuaranteeChannel._onSinkDisconnected","GuaranteeChannel._sink","GuaranteeChannel._streamController","GuaranteeChannel._subscription","GuaranteeChannel.<anonymous function>","GuaranteeChannel.<anonymous function>.<anonymous function>","_GuaranteeSink.done","_GuaranteeSink.add","_GuaranteeSink.addError","_GuaranteeSink.addError[function-entry$1]","_GuaranteeSink._addError","_GuaranteeSink._addError[function-entry$1]","_GuaranteeSink.addStream","_GuaranteeSink.close","_GuaranteeSink._onStreamDisconnected","_GuaranteeSink._addStreamSubscription","_GuaranteeSink._addError.<anonymous function>","_GuaranteeSink.addStream.<anonymous function>","_MultiChannel.virtualChannel","_MultiChannel.virtualChannel[function-entry$0]","_MultiChannel._closeChannel","_MultiChannel._closeInnerChannel","_MultiChannel.<anonymous function>","_MultiChannel_closure","_MultiChannel.<anonymous function>.<anonymous function>","_MultiChannel__closure","_MultiChannel.virtualChannel.<anonymous function>","_MultiChannel_virtualChannel_closure","StreamChannelCompleter._channel","StreamChannelController.local","StreamChannelController._local","StreamChannelController._foreign","SpanScanner.spanFrom","SpanScanner.matches","SpanScanner.error","StringScanner.lastMatch","StringScanner.peekChar","StringScanner.scan","StringScanner.expect","StringScanner._fail","StringScanner.expect[function-entry$1]","StringScanner.matches","AsciiGlyphSet.glyphOrAscii","AsciiGlyphSet.horizontalLine","AsciiGlyphSet.verticalLine","AsciiGlyphSet.topLeftCorner","AsciiGlyphSet.bottomLeftCorner","AsciiGlyphSet.upEnd","AsciiGlyphSet.downEnd","UnicodeGlyphSet.glyphOrAscii","UnicodeGlyphSet.horizontalLine","UnicodeGlyphSet.verticalLine","UnicodeGlyphSet.topLeftCorner","UnicodeGlyphSet.bottomLeftCorner","UnicodeGlyphSet.upEnd","UnicodeGlyphSet.downEnd","internalBootstrapBrowserTest.<anonymous function>","suiteChannel","setStackTraceMapper","postMessageChannel.<anonymous function>","convertNativeToDart_AcceptStructuredClone","convertNativeToDart_SerializedScriptValue","postMessageChannel.<anonymous function>.<anonymous function>","ClosedException.toString","Declarer.test","Declarer.group","Declarer.build","Declarer._checkNotBuilt","Declarer._runSetUps","Declarer._setUpAll","Declarer._tearDownAll","Declarer.test.<anonymous function>","Invoker.addTearDown","Declarer.test.<anonymous function>.<anonymous function>","Declarer.test.<anonymous function>.<anonymous function>.<anonymous function>","Declarer.group.<anonymous function>","Declarer.build.<anonymous function>","Declarer._runSetUps.<anonymous function>","Declarer._tearDownAll.<anonymous function>","Declarer._tearDownAll.<anonymous function>.<anonymous function>","Declarer._tearDownAll.<anonymous function>.<anonymous function>.<anonymous function>","Group.forPlatform","Group._map","Group.forPlatform.<anonymous function>","Group._map.<anonymous function>","LocalTest.load","Invoker._closableKey","Invoker._","Invoker._counterKey","Invoker.liveTest","LocalTest.forPlatform","Invoker._outstandingCallbacks","Invoker.addOutstandingCallback","Invoker.waitForOutstandingCallbacks","Invoker.unclosable","Invoker.heartbeat","LiveTest.isComplete","Invoker._handleError","State.shouldBeDone","Invoker._handleError[function-entry$2]","Invoker._onRun","Invoker._runTearDowns","Invoker.guard.<anonymous function>","Invoker.guard.<anonymous function>.<anonymous function>","Invoker.waitForOutstandingCallbacks.<anonymous function>","Invoker.heartbeat.message","niceDuration","Invoker.heartbeat.<anonymous function>","Invoker.heartbeat.<anonymous function>.<anonymous function>","Invoker._handleError.<anonymous function>","_AsyncCounter.complete","Invoker._onRun.<anonymous function>","Invoker._onRun.<anonymous function>.<anonymous function>","Invoker._onRun.<anonymous function>.<anonymous function>.<anonymous function>","Invoker._onRun.<anonymous function>.<anonymous function>.<anonymous function>.<anonymous function>","Invoker._print","_AsyncCounter.decrement","_LiveTest.run","LiveTestController._run","LiveTestController._isClosed","_LiveTest.onComplete","LiveTestController.addError","LiveTestController.setState","LiveTestController.message","_BroadcastStreamController.hasListener","LiveTestController._close","MessageType.toString","Metadata._validateTags","Metadata.validatePlatformSelectors","Metadata.merge","Metadata.change","Metadata.change[function-entry$0$onPlatform]","Metadata.change[function-entry$0$timeout]","Metadata.change[function-entry$0$skip$skipReason]","Metadata.forPlatform","Metadata.serialize","Metadata._serializeTimeout","Metadata._unresolved","Metadata.<anonymous function>","Metadata.deserialize.<anonymous function>","BooleanSelectorImpl.parse","Parser","Metadata._validateTags.<anonymous function>","Metadata.validatePlatformSelectors.<anonymous function>","Metadata.merge.<anonymous function>","Metadata.forPlatform.<anonymous function>","Metadata.serialize.<anonymous function>","OperatingSystem.toString","OperatingSystem.find.<anonymous function>","PlatformSelector.validate","PlatformSelector.evaluate","PlatformSelector.intersection","PlatformSelector.toString","PlatformSelector.==","PlatformSelector.hashCode","PlatformSelector.parse.<anonymous function>","PlatformSelector.validate.<anonymous function>","PlatformSelector.validate.<anonymous function>.<anonymous function>","PlatformSelector.evaluate.<anonymous function>","Runtime.toString","Runtime.deserialize.<anonymous function>","StackTraceFormatter.configure","StackTraceFormatter.configure[function-entry$0$except$only]","StackTraceFormatter.configure[function-entry$0$mapper]","StackTraceFormatter.formatStackTrace","parseExtended","JSStackTraceMapper.mapStackTrace","StackTraceFormatter._except","StackTraceFormatter._only","StackTraceFormatter.formatStackTrace.<anonymous function>","_LinkedHashSet.isNotEmpty","State.==","State.hashCode","State.toString","Status.toString","Result.toString","TestFailure.toString","_expect.<anonymous function>","Timeout.merge","Duration.*","Timeout.apply","Timeout.hashCode","Timeout.==","Timeout.toString","RemoteListener._serializeGroup","RemoteListener._serializeTest","RemoteListener._runLiveTest","_BroadcastStreamController.stream","_LiveTest.onStateChange","_LiveTest.onError","_LiveTest.onMessage","RemoteListener.start.<anonymous function>","StackTraceFormatter","RemoteListener.start.<anonymous function>.<anonymous function>","RemoteListener.start.<anonymous function>.<anonymous function>.<anonymous function>","StreamQueue._","RemoteListener.start.<anonymous function>.<anonymous function>.<anonymous function>.<anonymous function>","SuiteChannelManager.current","SuiteChannelManager.connectIn","StreamChannelCompleter.setChannel","StreamSinkCompleter.setDestinationSink","RemoteListener.start.<anonymous function>.<anonymous function>.<anonymous function>.<anonymous function>.<anonymous function>","RemoteListener._listen","RemoteListener._serializeGroup.<anonymous function>","RemoteListener._serializeTest.<anonymous function>","RemoteListener._runLiveTest.<anonymous function>","RemoteListener._runLiveTest.<anonymous function>.<anonymous function>","SuiteChannelManager.connectOut","StreamCompleter._stream","StreamSinkCompleter.sink","StreamChannelCompleter._streamCompleter","StreamChannelCompleter._sinkCompleter","StreamChannelCompleter","StreamChannel","IterableSet.length","IterableSet.iterator","IterableSet.toSet","errorsDontStopTest.<anonymous function>","currentOSGuess.<anonymous function>","Engine._onUnpaused","Engine.success","Engine.liveTests","UnionSet.from","Engine.passed","Engine.skipped","Engine.failed","Engine.active","Engine.run","Engine._runGroup","JSArray._toListGrowable","Engine._runLiveTest","Engine._runLiveTest[function-entry$2]","Engine._runSkippedTest","Engine._addLiveSuite","_LiveSuite.onTestStarted","_LiveSuite.passed","_LiveSuite.skipped","_LiveSuite.failed","Engine.success.<anonymous function>","Engine.<anonymous function>","Engine.run.<anonymous function>","Engine.run.<anonymous function>.<anonymous function>","Engine_run__closure","Engine.run.<anonymous function>.<anonymous function>.<anonymous function>","Engine.run.<anonymous function>.<anonymous function>.<anonymous function>.<anonymous function>","Engine._runLiveTest.<anonymous function>","Engine._runSkippedTest.<anonymous function>","LiveSuiteController.reportLiveTest","LiveSuiteController.close","LiveSuiteController.<anonymous function>","LiveSuiteController.reportLiveTest.<anonymous function>","LiveSuiteController.close.<anonymous function>","ExpandedReporter._onTestStarted","Stopwatch.start","ExpandedReporter._onStateChange","ExpandedReporter._onError","ExpandedReporter._onDone","ExpandedReporter._progressLine","ExpandedReporter._timeString","ExpandedReporter._progressLine[function-entry$1$suffix]","ExpandedReporter._progressLine[function-entry$1$color]","ExpandedReporter._progressLine[function-entry$1]","ExpandedReporter._description","ExpandedReporter._onTestStarted.<anonymous function>","RunnerSuiteController._close","RunnerSuiteController._suite","RunnerSuiteController._close.<anonymous function>","PrintSink.writeln","PrintSink._flush","JSStackTraceMapper._deserializePackageConfigMap.<anonymous function>","_declarer.<anonymous function>","RunnerSuiteController._local","RunnerSuite._","DelegatingSink.add","Engine.suiteSink","DelegatingSink.close","Stopwatch","ExpandedReporter._","StreamGroup.stream","_declarer.<anonymous function>.<anonymous function>","main.<anonymous function>","main.<anonymous function>.<anonymous function>","_nullErrorHandler[function-entry$1]","_rootRun[function-entry$4]","_rootRunUnary[function-entry$5]","_rootRegisterCallback[function-entry$4]","_rootRegisterUnaryCallback[function-entry$4]","_rootRegisterBinaryCallback[function-entry$4]","max[function-entry$2]","DART_CLOSURE_PROPERTY_NAME","JS_INTEROP_INTERCEPTOR_TAG","TypeErrorDecoder.noSuchMethodPattern","TypeErrorDecoder.notClosurePattern","TypeErrorDecoder.nullCallPattern","TypeErrorDecoder.nullLiteralCallPattern","TypeErrorDecoder.undefinedCallPattern","TypeErrorDecoder.undefinedLiteralCallPattern","TypeErrorDecoder.nullPropertyPattern","TypeErrorDecoder.nullLiteralPropertyPattern","TypeErrorDecoder.undefinedPropertyPattern","TypeErrorDecoder.undefinedLiteralPropertyPattern","_AsyncRun._scheduleImmediateClosure","Future._nullFuture","_RootZone._rootMap","Utf8Decoder._decoder","_Base64Decoder._inverseAlphabet","_Uri._isWindowsCached","_Uri._needsNoEncoding","_hasErrorStackProperty","_scannerTables","_whitespaceAndSingleLineComments","_multiLineCommentBody","_hyphenatedIdentifier","_dart2DynamicArgs","_escapeRegExp","windows","url","context","createInternal","Style.posix","PosixStyle","Style.windows","WindowsStyle","Style.url","UrlStyle","Style.platform","_digits","MAX_INT32","MIN_INT32","_specKey","_vmFrame","_v8Frame","_v8UrlLocation","_v8EvalLocation","_firefoxSafariFrame","_friendlyFrame","_asyncBody","_initialDot","Frame._uriRegExp","Frame._windowsRegExp","StackZoneSpecification.disableKey","_terseRegExp","_v8Trace","_v8TraceLine","_firefoxSafariTrace","_friendlyTrace","Metadata.empty","_universalValidVariables","_currentKey","currentOSGuess","anchoredHyphenatedIdentifier","SuiteConfiguration.empty","patchInstance","main_closure","fromTearOff","StaticClosure","BoundClosure","functionCounter","forwardCallTo","_computeSignatureFunctionNewRti","CyclicInitializationError","NullThrownError","safeToString","_objectToString","Closure","objectTypeName","_objectTypeNameNewRti","Object","_saneNativeClassName","_getInterfaceTypeArguments","_getGenericFunctionBounds","","value","_getFunctionParameters","markFixed","JSArray","markFixedList","StringBuffer","iterableToFullString","_toStringVisiting","_writeAll","noElement","ArrayIterator","ListIterator","ListMixin","Iterable","initNativeDispatchFlag","getTagFunction","dispatchRecordsForInstanceTags","interceptorsForUncacheableTags","alternateTagFunction","JavaScriptIndexingBehavior","prototypeForTagFunction","initHooks_closure","forType","_TypeError","compose","_CastError","fromMessage","_isUnionOfFunctionType","eval","_parseRecipe","create","parse","handleDigit","handleIdentifier","toType","_lookupGenericFunctionParameterRti","_lookupTerminalRti","toTypes","_lookupInterfaceRti","_lookupGenericFunctionRti","_lookupBindingRti","handleExtendedOperations","_lookupUnaryRti","_FunctionParameters","_lookupFunctionRti","toTypesNamed","_canonicalRecipeJoin","_canonicalRecipeJoinNamed","Rti","_finishRti","int","double","num","String","bool","_AssertionError","_getBindingArguments","indexToType","findRule","_getCanonicalRecipe","evalInEnvironment","_getFutureFromFutureOr","bind","findErasedType","evalRecipeIntercepted","evalRecipe","forwardInterceptedCallTo","cspForwardCall","selfFieldNameCache","computeFieldNamed","selfOf","receiverFieldNameCache","cspForwardInterceptedCall","receiverOf","internalBootstrapBrowserTest_closure","start","_ControllerStream","_current","Null","Stream","AsyncError","_propagateToListeners","_Future__propagateToListeners_handleWhenCompleteCallback","_Future__propagateToListeners_handleValueCallback","_Future__propagateToListeners_handleError","_chainCoreFuture","_Future__prependListeners_closure","ExceptionAndStackTrace","_StackTrace","unwrapException_saveStackTrace","UnknownJsTypeError","StackOverflowError","extractPattern","TypeErrorDecoder","provokePropertyErrorOn","provokeCallErrorOn","_Future__propagateToListeners_handleWhenCompleteCallback_closure","_FutureListener","_RootZone_bindCallbackGuarded_closure","_rootHandleUncaughtError_closure","_nextCallback","_lastPriorityCallback","_lastCallback","_AsyncCallbackEntry","_enter","_isInCallbackLoop","_initializeScheduleImmediate","_AsyncRun__initializeScheduleImmediate_internalCallback","_AsyncRun__initializeScheduleImmediate_closure","_createTimer","Duration_toString_twoDigits","Duration_toString_sixDigits","_TimerImpl_internalCallback","_AsyncRun__scheduleImmediateWithSetImmediate_internalCallback","_AsyncRun__scheduleImmediateJsOverride_internalCallback","_Exception","_Future__addListener_closure","_PendingEvents","_chainForeignFuture","_Future__chainForeignFuture_closure","_StreamControllerLifecycle","StreamConsumer","Stream_pipe_closure","_GuaranteeSink","_EventStream","postMessageChannel_closure","_literal","_EventStreamSubscription_closure","_convertDataTree__convert","_IdentityHashMap","mapToString","MapBase_mapToString_closure","MapMixin","_getTableEntry","_HashMapKeyIterable","iterableToShortString","checkNotNegative","range","_HashMapKeyIterator","MappedIterator","Iterator","EfficientLengthMappedIterable","MappedListIterable","ListIterable","_newHashTable","_setTableEntry","JsLinkedHashMap","LinkedHashMapKeyIterable","LinkedHashMapCell","postMessageChannel__closure","_StructuredCloneDart2Js","DateTime","_StructuredClone_walk_closure","_AcceptStructuredCloneDart2Js","StreamSink","StreamSubscription","_empty","_AcceptStructuredClone_walk_closure","getYear","_fourDigits","getMonth","_twoDigits","getDay","getHours","getMinutes","getSeconds","getMilliseconds","_threeDigits","lazyAsJsDate","_AsyncCompleter","promiseToFuture_closure","_Future__asyncCompleteError_closure","_Future__asyncComplete_closure","_Future__chainFuture_closure","Stream_firstWhere__closure","_cancelAndErrorClosure_closure","_cancelAndError_closure","zoneValue","_cancelAndValue_closure","_StreamSinkWrapper","GuaranteeChannel_closure","_StreamImplEvents","_SyncCompleter","_GuaranteeSink_addStream_closure","_GuaranteeSink__addError_closure","GuaranteeChannel__closure","_SyncStreamController","_AsyncStreamController","_EventDispatch","_PendingEvents_schedule_closure","_BufferingStreamSubscription__sendDone_sendDone","_StreamController__subscribe_closure","_StreamController__recordCancel_complete","_AddStreamState_cancel_closure","_DelayedError","_BufferingStreamSubscription__sendError_sendError","_DelayedData","RemoteListener_start_closure","fromIterable","Map","runZoned_closure","_rootDelegate","_ZoneDelegate","printToZone","from","_ZoneFunction","_CustomZone_bindCallbackGuarded_closure","periodic","_TimerImpl$periodic_closure","_HashMap","HashMap_HashMap$from_closure","_LinkedHashSet","RemoteListener_start__closure","RemoteListener_start___closure","_sendError","serialize","TestFailure","forTrace","Chain_toString_closure","Chain_toString__closure","_Type","Chain","unmodifiable","LazyChain","Chain_Chain$forTrace_closure","Chain_Chain$parse_closure","Trace_toString_closure","parseFriendly","WhereIterable","Trace$parseFriendly_closure","_StringStackTrace","WhereIterator","Context_split_closure","List","ParsedPath","filled","ParsedPath_normalize_closure","generate","JSSyntaxRegExp","makeNative","_uriDecode","StringMatch","CodeUnits","_hexCharPairToByte","Utf8Decoder","UnmodifiableListMixin","_convertIntercepted","checkValidRange","fromCharCodes","_Utf8Decoder","stringFromCharCode","stringFromCharCodes","stringFromNativeUint8List","_stringFromIterable","stringFromCodePoints","_fromCharCodeApply","_convertInterceptedUint8List","_useTextDecoderChecked","_unsafe","_useTextDecoderUnchecked","_makeDecoder","checkValueInInterval","_StringAllMatchesIterable","_StringAllMatchesIterator","_AllMatchesIterable","_AllMatchesIterator","tooFew","fixed","Context_join_closure","Context_joinAll_closure","_validateArgList_closure","base","_currentUriBase","currentUri","_parse","_SimpleUri","notSimple","parseInt","_defaultPort","_toWindowsFilePath","_checkNonWindowsPathReservedCharacters","_Uri__checkNonWindowsPathReservedCharacters_closure","_checkWindowsDriveLetter","_checkWindowsPathReservedCharacters","fromCharCode","_removeDotSegments","_makePort","_normalizeRelativePath","_mayContainDotSegments","_escapeScheme","_isAlphabeticCharacter","_makeScheme","_fail","_makeUserInfo","_makeHost","_Uri__Uri$notSimple_closure","_makePath","_makeQuery","_makeFragment","_normalizeOrSubstring","_normalize","_normalizeEscape","_escapeChar","_Uri__makePath_closure","_normalizePath","_uriEncode","Codec","_Utf8Encoder","_checkZoneID","_normalizeZoneID","parseIPv6Address","_normalizeRegName","Uri_parseIPv6Address_error","Uri_parseIPv6Address_parseHex","_parseIPv4Address","Uri__parseIPv4Address_error","_canonicalizeScheme","_createTables_closure","_createTables_build","_createTables_setChars","_createTables_setRange","_DataUri","UriData","_checkPadding","_create1","_getPlatformStyle","Frame_Frame$parseFriendly_closure","_catchFormatException","_writeUri","_uriEncodeBytes","Frame","WindowsStyle_absolutePathToUri_closure","_validateMimeType","_skipLeadingWhitespace","_skipTrailingWhitespace","_isWhitespace","parseV8","parseJSCore","parseFirefox","_parseVM","Trace__parseVM_closure","parseVM","Frame_Frame$parseVM_closure","ExpandIterable","Chain_toTrace_closure","Trace$parseFirefox_closure","Frame_Frame$parseFirefox_closure","_uriOrPathToUri","file","_makeWindowsFileUrl","_makeFileUri","Trace$parseJSCore_closure","Frame_Frame$parseV8_closure","Frame_Frame$parseV8_closure_parseLocation","Trace$parseV8_closure","SkipWhileIterable","SkipWhileIterator","StackZoneSpecification_chainFor_closure","_Node","LazyTrace","Trace_Trace$from_closure","LazyChain_toTrace_closure","getProperty","StackTraceFormatter_formatStackTrace_closure","LazyChain_foldFrames_closure","Chain_foldFrames_closure","tooMany","LazyTrace_foldFrames_closure","Trace_foldFrames_closure","ReversedListIterable","mapStackTrace_closure","_prettifyMember_closure","fromJson","notNull","_lastLineLength","_normalizeNewlines","_normalizeTrailingNewline","_normalizeEndOfLine","_glyphs","Highlighter__writeSidebar_closure","Highlighter__writeLastLine_closure","Highlighter__writeIntermediateLines_closure","Highlighter__writeFirstLine_closure","SingleMapping__findColumn_closure","SingleMapping__findLine_closure","SingleMapping","SourceFile","_MappingTokenizer","TargetLineEntry","TargetEntry","SingleMapping$fromJson_closure","closure","MultiSectionMapping","MappingBundle","_JsonMap","_JsonMapKeyIterable","_sendLoadException","StreamQueue","_CompleterStream","_RestRequest","StreamCompleter","RemoteListener_start____closure","deserialize","_deserializeSet","find","Suite","_filterGroup","Symbol","makeErrorHandler","_AddStreamState_makeErrorHandler_closure","Result","_wrapJsFunctionForAsync_closure","_StreamIterator","_awaitOnObject_closure","_AsyncAwaitCompleter","RemoteListener_start_____closure","guard","Invoker_guard_closure","Invoker_guard__closure","RemoteListener","RemoteListener__serializeGroup_closure","RemoteListener__serializeTest_closure","VirtualChannel","_EmptyStream","NullStreamSink","MultiChannel","NullStreamSink_addStream_closure","_LinkedHashSetCell","RemoteListener__runLiveTest_closure","_BroadcastStream","RemoteListener__runLiveTest__closure","Invoker","State","Invoker__onRun_closure","_AsyncCounter","capture","_keyCount","StackZoneSpecification","setProperty","StackZoneSpecification__currentTrace_closure","Invoker__onRun__closure","Invoker__onRun___closure","Message","Invoker__onRun____closure","Future_Future_closure","errorsDontStopTest_closure","Invoker_waitForOutstandingCallbacks_closure","sync","Invoker_heartbeat_closure","Invoker_heartbeat_message","Invoker_heartbeat__closure","TimeoutException","Timeout","Invoker__handleError_closure","Chain_Chain$current_closure","_SyncBroadcastStreamController","_LiveTest","_BroadcastStreamController","Metadata_serialize_closure","MapEntry","PlatformSelector","Group_forPlatform_closure","GroupEntry","Group__map_closure","Metadata_forPlatform_closure","Metadata_Metadata__unresolved","_","Metadata_Metadata_closure","Metadata_merge_closure","Set","UnmodifiableMapView","_throwUnmodifiable","_ConstantMapKeyIterable","ConstantStringMap","DelegatingSet","Metadata__validateTags_closure","LinkedHashMap_LinkedHashMap$from_closure","PlatformSelector_evaluate_closure","OperatingSystem_find_closure","Runtime_Runtime$deserialize_closure","Runtime","Declarer_build_closure","LocalTest","Declarer__tearDownAll_closure","Declarer__tearDownAll__closure","Declarer__tearDownAll___closure","_deserializeTimeout","Metadata$deserialize_closure","BooleanSelectorImpl","Scanner","AndNode","IntersectionSelector","OrNode","ConditionalNode","Evaluator","Token","_SpanScannerState","IdentifierToken","SourceSpanMixin","FileLocation","NotNode","VariableNode","PlatformSelector$parse_closure","_wrapFormatException","_CompleterSink","_CompleterSink__setDestinationSink_closure","StreamSinkCompleter","_EventRequest","_CancelOnErrorSubscriptionWrapper","_CancelOnErrorSubscriptionWrapper_onError_closure","_CancelOnErrorSubscriptionWrapper_onError__closure","ErrorResult","ValueResult","EventSink","_NextRequest","_GeneratedStreamImpl","PackageRootResolver","_deserializePackageConfigMap","_normalizeMap","PackageConfigResolver","JSStackTraceMapper","castFrom","CastMap","CastIterator","EfficientLengthIterable","_EfficientLengthCastIterable","PackageConfigResolver__normalizeMap_closure","JSStackTraceMapper__deserializePackageConfigMap_closure","_StreamChannel","Declarer_group_closure","Trace_Trace$current_closure","Metadata_validatePlatformSelectors_closure","PlatformSelector_validate_closure","PlatformSelector_validate__closure","Validator","_parseOnPlatform","_parseTags","_globalDeclarer","_declarer_closure","RunnerSuiteController","_AsyncBroadcastStreamController","AsyncMemoizer","RunnerSuite","_frequency","initTicker","timerFrequency","ExpandedReporter","PrintSink","fromFuture","_declarer__closure","error","UnmodifiableListView","timerTicks","UnionSet","IterableSet","ExpandedReporter__onTestStarted_closure","Engine_run_closure","Pool_close_closure","Engine_run___closure","Engine_run____closure","Pool__onResourceReleaseAllowed_closure","Pool__runOnRelease_closure","PoolResource","LiveSuiteController_close_closure","RunnerSuiteController__close_closure","Engine__runSkippedTest_closure","Engine__runLiveTest_closure","microtask","Future_Future$microtask_closure","LiveSuiteController_reportLiveTest_closure","_nextPowerOf2","StreamGroup__listenToStream_closure","_LiveSuite","LiveSuiteController_closure","wait","Engine_success_closure","Future_wait_handleError","Primitives_initTicker_closure","StreamGroup","Engine_closure","_macOSDirectories","_list","_map","SuiteConfiguration","main__closure","Declarer_test_closure","Declarer_test__closure","Declarer_test___closure","Declarer__runSetUps_closure","forEach","Future_forEach_closure","doWhile","Future_doWhile_closure","_expect_closure","StringDescription","Matcher","prettyPrint__prettyPrint","prettyPrint__prettyPrint_pp","prettyPrint__prettyPrint_closure","escape_closure","Runes","RuneIterator","_Predicate","wrapMatcher_closure","_StringEqualsMatcher","_DeepMatcher","_DeepMatcher__compareSets_closure","TypeMatcher","FeatureMatcher","_writeTrailing","_writeLeading","x","objectAssign","JS_CONST","Interceptor","JSBool","JSNull","JSObject","JavaScriptObject","PlainJavaScriptObject","UnknownJavaScriptObject","Function","JavaScriptFunction","JSUnmodifiableArray","JSNumber","JSInt","JSDouble","Pattern","JSString","_CastIterableBase","EmptyIterator","FixedLengthListMixin","UnmodifiableListBase","ConstantMap","noSuchMethodPattern","notClosurePattern","nullCallPattern","nullLiteralCallPattern","undefinedCallPattern","undefinedLiteralCallPattern","nullPropertyPattern","nullLiteralPropertyPattern","undefinedPropertyPattern","undefinedLiteralPropertyPattern","NoSuchMethodError","StackTrace","TearOffClosure","RegExpMatch","Match","NativeByteBuffer","ByteBuffer","NativeTypedData","NativeByteData","NativeTypedArray","NativeTypedArrayOfDouble","NativeTypedArrayOfInt","NativeFloat32List","NativeFloat64List","NativeInt16List","NativeInt32List","NativeInt8List","NativeUint16List","Uint32List","NativeUint32List","NativeUint8ClampedList","Uint8List","Type","_Error","Sink","_Completer","StreamTransformer","StreamTransformerBase","_StreamController","_SyncStreamControllerDispatch","_AsyncStreamControllerDispatch","_StreamImpl","_DelayedEvent","_DelayedDone","Error","ZoneSpecification","ZoneDelegate","Zone","_Zone","_rootMap","_RootZone","IterableBase","ListBase","MapBase","_UnmodifiableMapMixin","MapView","Queue","SetMixin","SetBase","_SetBase","AsciiCodec","_UnicodeSubsetEncoder","AsciiEncoder","Base64Codec","Base64Encoder","_FusedCodec","Converter","Encoding","JsonCodec","JsonDecoder","Utf8Codec","Utf8Encoder","_decoder","OutOfMemoryError","StringSink","Uri","_isWindowsCached","_needsNoEncoding","AbortPaymentEvent","AnimationEvent","AnimationPlaybackEvent","ApplicationCacheErrorEvent","BackgroundFetchClickEvent","BackgroundFetchEvent","BackgroundFetchFailEvent","BackgroundFetchedEvent","BeforeInstallPromptEvent","BeforeUnloadEvent","Blob","BlobEvent","CanMakePaymentEvent","ClipboardEvent","CloseEvent","CompositionEvent","CustomEvent","DeviceMotionEvent","DeviceOrientationEvent","DomError","DomException","ErrorEvent","Event","EventTarget","ExtendableEvent","ExtendableMessageEvent","FetchEvent","File","FocusEvent","FontFaceSetLoadEvent","ForeignFetchEvent","GamepadEvent","HashChangeEvent","InstallEvent","KeyboardEvent","Location","MediaEncryptedEvent","MediaError","MediaKeyMessageEvent","MediaQueryListEvent","MediaStreamEvent","MediaStreamTrackEvent","MessageEvent","MessagePort","MidiConnectionEvent","MidiMessageEvent","MouseEvent","MutationEvent","NavigatorUserMediaError","NotificationEvent","OverconstrainedError","PageTransitionEvent","PaymentRequestEvent","PaymentRequestUpdateEvent","PointerEvent","PopStateEvent","PositionError","PresentationConnectionAvailableEvent","PresentationConnectionCloseEvent","ProgressEvent","PromiseRejectionEvent","PushEvent","RtcDataChannelEvent","RtcDtmfToneChangeEvent","RtcPeerConnectionIceEvent","RtcTrackEvent","SecurityPolicyViolationEvent","SensorErrorEvent","SpeechRecognitionError","SpeechRecognitionEvent","SpeechSynthesisEvent","StorageEvent","SyncEvent","TextEvent","TouchEvent","TrackEvent","TransitionEvent","UIEvent","VRDeviceEvent","VRDisplayEvent","VRSessionEvent","WheelEvent","Window","_MojoInterfaceRequestEvent","_ResourceProgressEvent","_USBConnectionEvent","EventStreamProvider","_StructuredClone","_AcceptStructuredClone","VersionChangeEvent","ByteData","Int8List","Uint8ClampedList","Int16List","Uint16List","Int32List","Float32List","Float64List","AudioProcessingEvent","OfflineAudioCompletionEvent","ContextEvent","SqlError","DelegatingSink","DelegatingStreamSubscription","_StreamGroupState","BooleanSelector","All","Node","Visitor","None","TokenType","RecursiveVisitor","EmptyUnmodifiableSet","UnmodifiableSetMixin","_DelegatingIterableBase","DelegatingIterable","_IsTrue","Description","SyncPackageResolver","_PathDirection","_PathRelation","InternalStyle","Style","Mapping","_TokenKind","FileSpan","SourceLocationMixin","SourceSpan","SourceSpanException","_uriRegExp","_windowsRegExp","disableKey","StreamChannelMixin","LineScannerState","StringScanner","AsciiGlyphSet","UnicodeGlyphSet","LiveTest","MessageType","empty","OperatingSystem","Status","Test","StackTraceMapper","LiveSuite","RuntimeSelection","_NativeTypedArrayOfDouble&NativeTypedArray&ListMixin","_NativeTypedArrayOfDouble&NativeTypedArray&ListMixin&FixedLengthListMixin","_NativeTypedArrayOfInt&NativeTypedArray&ListMixin","_NativeTypedArrayOfInt&NativeTypedArray&ListMixin&FixedLengthListMixin","_ListBase&Object&ListMixin","_SetBase&Object&SetMixin","_UnmodifiableMapView&MapView&_UnmodifiableMapMixin","_QueueList&Object&ListMixin","_UnionSet&SetBase&UnmodifiableSetMixin","_UnmodifiableSetView&DelegatingSet&UnmodifiableSetMixin","_IterableSet&SetMixin&UnmodifiableSetMixin","dateNow","addRules","addErasedTypes","_scheduleImmediateJsOverride","_scheduleImmediateWithSetImmediate","_scheduleImmediateWithTimer","_kTrue","decodeComponent","_scheduleImmediateClosure","_nullFuture","_inverseAlphabet","posix","platform","getInterceptor$","getInterceptor$asx","async___startMicrotaskLoop$closure","async__AsyncRun__scheduleImmediateJsOverride$closure","async__AsyncRun__scheduleImmediateWithSetImmediate$closure","async__AsyncRun__scheduleImmediateWithTimer$closure","async___nullDoneHandler$closure","async___nullErrorHandler$closure","async___nullDataHandler$closure","getInterceptor$ax","async___printToZone$closure","math__max$closure","getInterceptor$s","core_Uri_decodeComponent$closure","main_test__main$closure","_js_helper_Primitives_dateNow$closure","async_Future__kTrue$closure","pretty_print___escapeString$closure","util___getHexLiteral$closure","getInterceptor$x","getInterceptor$ansx","getInterceptor$n","async___rootHandleUncaughtError$closure","async___rootRun$closure","async___rootRunUnary$closure","async___rootRunBinary$closure","async___rootRegisterCallback$closure","async___rootRegisterUnaryCallback$closure","async___rootRegisterBinaryCallback$closure","async___rootErrorCallback$closure","async___rootScheduleMicrotask$closure","async___rootCreateTimer$closure","async___rootCreatePeriodicTimer$closure","async___rootPrint$closure","async___rootFork$closure","_captured_K1_1","_captured_this_1","dart.async#_box_0","_captured_matcher_0","future","_captured_V1_2","_captured_listener_2","_captured_frame_0","_captured_expectedElement_1","_captured_getMain_1","location","channel","_captured_depth_3","controller","matches","_captured_beforeLoad_4","_captured_f_1","line","_captured_printZone_5","_captured_R_3","end","_captured_transform_1","result","_captured_selector_0","handleError","_captured_body_1","_captured_elements_0","_captured_x_0","suite","_captured_T_3","index","_captured_validVariables_0","_captured_terse_2","addEventListener","stackTrace","timeout","_withValue","message","immediate","_captured_performance_0","trace","_captured_div_1","level","span","_captured_registered_1","where","toString","callback","decoded","groups","liveTest","_captured_engine_0","_captured_chain_0","completer","_captured_longest_0","dart.async#_box_1","skipWhile","_captured_fn_2","call","_captured_oldPredicate_0","_captured_counter_3","_captured_hasError_3","_captured_loadResource_2","describe","id","_captured_milliseconds_1","_captured_originalSource_0","stream","immediateError","_captured_outstandingCallbacksForBody_1","_captured_sourceResult_2","_captured_K_1","_captured_serializedOnPlatform_0","_captured_V_2","broadcast","onData","_captured_target_0","_captured_sourceMap_1","_captured_invoker_0","_captured_minified_4","zone","_captured_sdkRoot_2","_captured_streamConsumer_0","_captured_e_1","_captured_s_2","_captured_sdkLib_3","_addEventError","column","_captured_cleanUp_3","_captured_eagerError_4","iterator","identifier","port","_captured_action_1","_captured_node_2","_captured_T1_3","_captured_T2_4","withResource","_captured_portSubscription_1","_captured_serialized_0","_captured_doneSignal_2","_captured_arg1_1","_captured_pos_1","_captured_arg2_2","_captured_dispatch_1","_captured_getTag_0","testOn","_captured_getUnknownTag_0","skip","verboseTrace","_captured_prototypeForTag_0","chainStackTraces","_captured_argumentError_0","==","retry","_captured_arg_1","skipReason","_captured__convertedObjects_0","onPlatform","uri","_captured_portStart_1","skipped","_captured_textInside_1","_captured_maxItems_0","_captured_maxLineLength_1","original","_runGroup","host","_captured__prettyPrint_1","_runLiveTest","_captured_indent_0","_runSkippedTest","_captured_computation_1","_captured_orElse_1","_captured_countSuccess_2","_captured_K2_0","_captured_protected_0","_captured_spec_6","_captured_pp_0","onError","_captured_object_1","_captured_ex_0","subscription","cancel","_captured_bodyFunction_0","_captured_tables_0","data","stream_channel_controller.dart#_foreign","stack_zone_specification.dart#_disabled","expanded.dart#_onTestStarted","newDartList","configure","elapsedMicroseconds","dart.core#_captured_argumentError_0","platform_selector.dart#_captured_this_0","dart.async#_completeWithValue","source_maps.parser#_captured_this_0","dart.async#_isScheduled","hashMapCellKey","dart.async#_captured_future_1","multi_channel.dart#_closeChannel","encode","dart.async#_error","dart.core#_start","onClose","dart.async#_captured_callback_1","dart.async#_completeError","dart.async#_captured_doneSignal_2","_js_helper#_captured_result_2","separators","async_memoizer.dart#_completer","invoker.dart#_counterKey","functions.dart#_captured_V1_2","prettyUri","metadata.dart#_captured_serializedOnPlatform_0","equals_matcher.dart#_compareSets","fold","getRoot","dart.collection#_newSet","invoker.dart#_captured_stackTrace_3","dart.core#_isPort","catchError","*","parser.dart#_and","metadata.dart#_captured_verboseTrace_4","scanner.dart#_scanOperator","highlighter.dart#_writeFirstLine","dart.async#_handleUncaughtError","engine.dart#_failedGroup","rti#_kind","isOdd","source_maps.parser#_findLine","functions.dart#_captured_V_3","stack_zone_specification.dart#_currentNode","engine.dart#_onSuiteStartedController","stack_zone_specification.dart#_captured_f_0","pool.dart#_requestedResources","indexOf","rti#_precomputed4","source_maps.parser#_consumeValue","replaceAll","stream_queue.dart#_completer","tags","source_map_stack_trace.dart#_captured_sdkRoot_3","_js_helper#_previous","needsSeparatorPattern","dart.async#_run","replace","dart.collection#_add","_interceptors#_shlPositive","stream_sink_completer.dart#_ensureController","dart.dom.html#_location","dart.async#_mayAddListener","lazy_chain.dart#_captured_terse_2","queue_list.dart#_preGrow","evaluate","wrappers.dart#_base","context.dart#_isWithinOrEqualsFast","_js_helper#_modified","shouldBeDone","isBlink","dart.core#_currentCodePoint","stream_queue.dart#_addResult","source_map_stack_trace.dart#_box_0","typedMatches","moveNext","_js_helper#_execAnchored","duration","guarantee_channel.dart#_onSinkDisconnected","isCompleted","query","visitVariable","bindCallback","stack_zone_specification.dart#_currentTrace","sourceRoot","take","expanded.dart#_progressLine","listenerHasError","liveTests","createPeriodicTimer","live_suite_controller.dart#_onCloseCompleter","remote_listener.dart#_captured_controller_0","dart.async#_onCancel","pathsEqual","distance","dart.core#_position","asStream","abs","listenerValueOrError","dart.async#_decrementPauseCount","html_common#_captured_this_1","hasTrailingSeparator","stack_trace_formatter.dart#_captured_this_0","declarer.dart#_name","stack_zone_specification.dart#_registerBinaryCallback","dart.collection#_tail","asUint8List","isScaffoldAll","remote_listener.dart#_captured_test_1","isWithin","platform_selector.dart#_captured_validVariables_0","functions.dart#_box_0","live_suite_controller.dart#_passed","addTearDown","dart._internal#_iterator","hashMapCellValue","functions.dart#_captured_K1_1","lastSpan","runner_suite.dart#_environment","registerCallback","handleUncaughtError","stack_zone_specification.dart#_captured_this_1","allMatches","dart.collection#_position","_js_helper#_expr","dart.convert#_data","runner_suite.dart#_suiteChannel","engine.dart#_captured_suite_1","onListen","equals_matcher.dart#_recursiveMatch","highlighter.dart#_writeSidebar","stream_group.dart#_onCancelBroadcast","dart._internal#_iterable","dart.convert#_buffer","print_sink.dart#_flush","operating_system.dart#_captured_identifier_0","invoker.dart#_print","scan","onCancel","dart.async#_schedule","declarer.dart#_metadata","highlighter.dart#_colorize","source_map_stack_trace.dart#_captured_sdkRoot_2","_js_helper#_target","highlighter.dart#_multiline","highlighter.dart#_paddingBeforeSidebar","dart._internal#_startIndex","rti#_specializedTestResource","_interceptors#_isInt32","dart.collection#_contains","invoker.dart#_handleError","engine.dart#_runPool","dart.async#_setPendingComplete","parser.dart#_simpleExpression","dart.async#_rootRunUnary","dart.async#_cloneResult","stack_zone_specification.dart#_trimVMChain","live_test_controller.dart#_run","dart.collection#_first","metadata.dart#_serializeTimeout","relative","declarer.dart#_collectTraces","span_exception.dart#_message","live_test_controller.dart#_onRun","join","stack_zone_specification.dart#_errorCallback","stack_zone_specification.dart#_registerUnaryCallback","runner_suite.dart#_closeMemo","change","addAll","dart.async#_isPaused","previous","dart.async#_addError","source_map_stack_trace.dart#_captured_minified_4","dart.core#_queryStart","dart.async#_captured_eagerError_4","dart.async#_captured_T_2","whenComplete","position","_js_helper#_newLinkedCell","asCurrent","addDescriptionOf","dart.async#_captured_orElse_1","dart.async#_captured_subscription_0","invoker.dart#_count","rti#_eval","dart.async#_addEventError","rti#_optionalPositional","queue_list.dart#_writeToList","dart.async#_hasPending","live_test_controller.dart#_test","runner_suite.dart#_captured_this_0","pool.dart#_captured_zone_0","invoker.dart#_controller","setRange","write","pretty_print.dart#_captured_maxItems_0","stream_queue.dart#_isClosed","multi_channel.dart#_closeInnerChannel","invoker.dart#_closable","update","test.src.runner.browser.post_message_channel#_captured_controller_0","dart.collection#_current=","dart.async#_thenAwait","dart.convert#_upgrade","_js_helper#_fetch","isNewSegment","evaluator.dart#_semantics","internalFindBucketIndex","stack_zone_specification.dart#_registerCallback","file.dart#_cachedLine","live_suite_controller.dart#_controller","dart.async#_cancel","isPassing","source_maps.parser#_lineStart","expanded.dart#_noColor","dart.async#_forEachListener","runner_suite.dart#_isDebugging","fillRange","dart.convert#_second","removeTrailingSeparators","dart.core#_errorName","union_set_controller.dart#_set","visitAnd","pool.dart#_closeMemo","dart.async#_chainFuture","declare","needsSeparator","second","dart.async#_isCanceled","handleNext","union_set.dart#_disjoint","live_test_controller.dart#_liveTest","dart.async#_ensurePendingEvents","failed","context.dart#_parse","string_scanner.dart#_lastMatch","replaceRange","dart.convert#_carry","expand","stack_zone_specification.dart#_captured_this_0","isAbsolute","peek","pretty_print.dart#_captured_object_1","dart.async#_rootRegisterCallback","guarantee_channel.dart#_doneCompleter","isValue","_interceptors#_defaultSplit","_js_helper#_execGlobal","pool.dart#_onResourceReleaseAllowed","_interceptors#_shrBothPositive","chain.dart#_captured_longest_0","dart.core#_captured_error_0","dart.collection#_remove","dart._internal#_string","padRight","dart.async#_iterator","success","stack_zone_specification.dart#_captured_stackTrace_2","multi_channel.dart#_pendingIds","dart.core#_toNonSimple","remote_listener.dart#_captured_spec_6","readChar","scaleFactor","_js_helper#_string","stream_group.dart#_controller","remote_listener.dart#_serializeGroup","microsecond","declarer.dart#_checkNotBuilt","dart.collection#_computeKeys","binaryOnError","parser.dart#_or","dart.async#_captured_computation_1","dart.collection#_findBucketIndex","release","runner_suite.dart#_close","union","_interceptors#_iterable","dart.typed_data.implementation#_setRangeFast","live_suite_controller.dart#_captured_countSuccess_2","dart.collection#_map","internalSet","dart.collection#_checkModification","single","functions.dart#_captured_K_2","joinAll","dart.async#_isEmpty","load","pipe","identicalInJs","dart.async#_asyncCompleteError","lazy_trace.dart#_trace","hashCode","pool.dart#_pool","decrement","registerUnaryCallback","pool.dart#_maxAllocatedResources","isComplete","indexable","hasTokens","dart.dom.html#_onData","_js_helper#_strings","pathSegments","expanded.dart#_green","dart.async#_captured_registered_1","describeTypedMismatch","equals_matcher.dart#_expected","whenFalse","decode","dart._internal#_captured_f_1","any","convert","[]=","future_group.dart#_completer","dart.async#_add","matchTypeError","_js_helper#_last","unclosable","containsKey","engine.dart#_runGroup","queue_list.dart#_grow","chain.dart#_captured_predicate_0","minute","source_maps.parser#_length","declarer.dart#_setUpAllTrace","codeUnitAt","modifiedObject","dart.js_util#_captured_completer_0","newJsObject","active","expanded.dart#_lastProgressSuffix","future_group.dart#_captured_index_1","union_set.dart#_dedupIterable","live_suite_controller.dart#_captured_this_0","endsWith","dart.async#_captured_streamConsumer_0","removeLast","urls","dart.async#_captured_hasError_3","remote_listener.dart#_captured_this_1","dart.async#_varData","_js_helper#_name","engine.dart#_coverage","dart._internal#_endIndex","codeUnitsEqual","dart.async#_captured_s_2","toTrace","source_maps.parser#_segmentError","pool.dart#_closeGroup","bindUnaryCallback","dart.collection#_length","runner_suite.dart#_controller","dart.js_util#_captured_T_1","dart.async#_delegationTarget","storedCallback","declarer.dart#_solo","round","rti#_bind","errorCallback","functions.dart#_captured_V1_3","dart.convert#_allowMalformed","lastIndexOf","expanded.dart#_onError","declarer.dart#_setUpAll","core_matchers.dart#_description","restartable_timer.dart#_callback","metadata.dart#_skip","dart2jsArgs","subscription_stream.dart#_captured_error_1","dart.async#_resultOrListeners","relativeRootPattern","dart.async#_onError","stream_completer.dart#_createController","dart.collection#_previous","dart.async#_setError","file.dart#_isNearCachedLine","wrappers.dart#_setBase","equals_matcher.dart#_compareIterables","add","stream_group.dart#_listenToStream","html_common#_box_0","visitNot","complete","cast","engine.dart#_skippedGroup","type_matcher.dart#_name","dart.core#_errorExplanation","close","highlight","source_maps.parser#_mappings","putIfAbsent","_js_helper#_captured_performance_0","isFinite","runSkipped","isUnicode","addError","toChain","_js_helper#_map","dart.async#_captured_this_1","setUpAll","declarer.dart#_noRetry","spanFor","dart.async#_errorCallback=","dart.dom.html#_captured_onData_0","count","dart.async#_isComplete","dart.async#_captured_span_2","remote_listener.dart#_captured_groups_2","setAll","dart.async#_onValue","setDestinationSink","scanner.dart#_getNext","packageConfigMap","dart.core#_captured_tables_0","writeln","expanded.dart#_printPlatform","_js_helper#_trace","dart.async#_mayResumeInput","invalidValue","dart.async#_recordPause","stack_zone_specification.dart#_captured_T1_3","span_scanner.dart#_scanner","expanded.dart#_bold","file.dart#_start","noMoreLiveTests","dart.dom.html#_unlisten","engine.dart#_runCalled","string_scanner.dart#_position","removeFragment","pool.dart#_released","dart.async#_setValue","firstMatch","dart.async#_captured_originalSource_0","liveSuite","_js_helper#_next","source_maps.parser#_internal","dart.core#_isFile","isLoadSuite","guarantee_channel.dart#_streamController","dart.dom.html#_addEventListener","dart._internal#_endOrLength","resolveUri","_js_helper#_addHashTableEntry","whenTrue","isEmpty","scanner.dart#_multiLineComment","iterable_set.dart#_base","dart.async#_checkState","dart.async#_captured_future_3","dart.async#_inCallback","expanded.dart#_captured_this_0","files","splitMapJoin","toFilePath","internalRemove","toolString","stream_queue.dart#_failClosed","_interceptors#_toListFixed","group.dart#_captured_platform_0","lazy_trace.dart#_captured_this_0","remaining","dart.core#_captured_portStart_1","parser.dart#_conditional","equals_matcher.dart#_match","dart.core#_pathSegments","firstWhere","floor","padLeft","stack_zone_specification.dart#_captured_R_5","trace.dart#_captured_longest_0","onMessage","engine.dart#_addedSuites","dart.core#_captured_host_0","engine.dart#_captured_skipped_1","expanded.dart#_color","stack_zone_specification.dart#_run","dart.core#_mergePaths","getText","declarer.dart#_trace","subscription_stream.dart#_captured_handleError_1","dart.core#_isHttp","expanded.dart#_lastProgressPassed","month","apply","invoker.dart#_captured_outstandingCallbacksForBody_1","dart.async#_badEventState","metadata.dart#_captured_validVariables_0","canonicalizePart","toRadixString","dart.collection#_cell","dart.core#_simpleMerge","remote_listener.dart#_runLiveTest","stream_queue.dart#_addRequest","dart.collection#_removeHashTableEntry","validate","queue_list.dart#_table","future_group.dart#_pending","matchesErrorTest","dart.async#_removeListener","hasErrorTest","expanded.dart#_onDone","dart.async#_onPause","packageConfigUri","expanded.dart#_lastProgressSkipped","engine.dart#_box_0","rti#_check","isRelative","platform_selector.dart#_captured_selector_0","metadata.dart#_retry","_js_helper#_input","nextIteration","expanded.dart#_timeString","pointSpan","variableName","dart.core#_schemeCache","insert","day","lazy_trace.dart#_captured_predicate_1","putIntoMap","live_test_controller.dart#_state","lines","dart.async#_recordCancel","dart.async#_sendError","_js_helper#_newHashTable","removeFirst","pool.dart#_runOnRelease","source_maps.parser#_findColumn","dart.async#_removeListeners","trim","stream_queue.dart#_close","queue_list.dart#_head","_js_helper#_index","isDartVM","stream_sink_completer.dart#_sink","virtualChannel","listeners","dart.core#_host","stream_queue.dart#_subscription","bindCallbackGuarded","containsSeparator","inMinutes","endColumn","stream_channel_completer.dart#_streamCompleter","right","hasAbsolutePath","_js_helper#_re","varData","onComplete","dart.collection#_get","toUri","dart.core#_fragmentStart","suite_channel_manager.dart#_outgoingConnections","hasPort","dart.collection#_modified","runtime","getLine","highlighter.dart#_countTabs","_js_helper#_nativeAnchoredRegExp","dart.async#_waitsForCancel","run","_js_helper#_captured_ex_0","errorZone","foundResult","engine.dart#_onSuiteAddedController","dart.async#_captured_future_2","stream_completer.dart#_setSourceStream","suite_channel_manager.dart#_incomingConnections","declarer.dart#_setUpAlls","getColumn","dart.collection#_element","dart.async#_errorTest","_js_helper#_argumentsExpr","schedule","dart.collection#_captured_result_0","stream_channel_completer.dart#_sinkCompleter","dart.async#_eventScheduled","highlighter.dart#_writeTrailingLines","rootLength","live_suite_controller.dart#_captured_liveTest_1","normalize","invoker.dart#_closableKey","live_test_controller.dart#_controller","isSync","dart.convert#_parent","source","engine.dart#_runLiveTest","dart.async#_isPendingComplete","source_maps.parser#_captured_line_0","copyList","dart.convert#_writeSurrogate","remote_listener.dart#_serializeTest","dart.convert#_fillBuffer","toJson","highlighter.dart#_writeLastLine","addOutstandingCallback","_interceptors#_codeUnitAt","chainFor","~/","dart.collection#_addHashTableEntry","package","isHeadless","completeError","verboseChain","declarer.dart#_parent","stream_group.dart#_subscriptions","listen","describeMismatch","closed","stream_queue.dart#_streamQueue","declarer.dart#_runSetUps","pretty_print.dart#_captured_indent_0","dart.typed_data.implementation#_checkPosition","declarer.dart#_prefix","stream_completer.dart#_linkStreamToController","setSourceStream","targetUrl","_js_helper#_message","inMilliseconds","dart.async#_previous","dart.js_util#_captured__convertedObjects_0","declarer.dart#_entries","dart.async#_setPendingEvents","stack_zone_specification.dart#_captured_node_2","dart._internal#_length","invoker.dart#_guardIfGuarded","done","declarer.dart#_platformVariables","highlighter.dart#_isOnlyWhitespace","isJS","isEof","sourceLine","dart._internal#_f","isBroadcast","invoker.dart#_captured_invoker_0","remote_listener.dart#_box_0","declarer.dart#_tearDowns","dart.async#_close","multi_channel.dart#_nextId","remote_listener.dart#_captured_liveTest_0","engine.dart#_closed","highlighter.dart#_writeText","matchAsPrefix","invoker.dart#_guarded","lazy_trace.dart#_inner","_js_helper#_unlinkCell","live_suite_controller.dart#_failed","stack_zone_specification.dart#_box_0","lazy_chain.dart#_captured_this_0","relativePathToUri","dart.async#_isChained","newJsMap","pool.dart#_allocatedResources","highlighter.dart#_color","dart.async#_mayAddEvent","group.dart#_map","multi_channel.dart#_captured_this_1","dart.collection#_computeHashCode","dart.async#_complete","dart.async#_captured_result_2","dart.async#_captured_e_1","null_stream_sink.dart#_captured_this_0","remote_listener.dart#_captured_printZone_0","dart.async#_isAddingStream","dart.collection#_newLinkedCell","_interceptors#_shrReceiverPositive","fragment","dart.async#_sendData","dart.dom.html#_pauseCount","runUnary","dart.convert#_upgradedMap","scanner.dart#_scanner","precompiledPath","dart.dom.html#_target","dart.core#_hashCodeCache","runGuarded","span_scanner.dart#_lastSpan","toList","metadata.dart#_verboseTrace","dart.async#_whenCompleteAction","replaceAllMapped","rti#_as","invoker.dart#_captured_counter_3","_js_helper#_nativeGlobalRegExp","declarer.dart#_soloEntries","addSubscription","increment","stack_zone_specification.dart#_captured_R_4","pool.dart#_onResourceReleased","dart.collection#_strings","dart.async#_handle","hasListener","dart.async#_ensureDoneFuture","stack_zone_specification.dart#_handleUncaughtError","remote_listener.dart#_captured_printZone_1","invoker.dart#_invokerZone","_js_helper#_captured_transform_1","pause","runUnaryGuarded","spanFrom","runner_suite.dart#_config","runner_suite.dart#_onClose","dart.async#_zone","stream_sink_completer.dart#_controller","highlighter.dart#_captured_textInside_1","[]","expanded.dart#_lastProgressMessage","invoker.dart#_captured_fn_2","lastPendingEvent","inMicroseconds","visitConditional","dart._internal#_index","stream_sink_completer.dart#_doneCompleter","inSeconds","live_test_controller.dart#_onStateChangeController","rti#_cachedRuntimeType","dart.async#_captured_controller_0","packageResolver","dart.async#_captured_eagerError_2","stack_zone_specification.dart#_captured_T2_4","live_test_controller.dart#_onClose","live_test_controller.dart#_groups","dart.core#_duration","file.dart#_decodedChars","parents","parent","_js_helper#_jsObject","dart.async#_captured_test_0","stream_group.dart#_state","startsWith","dart.collection#_set","absolute","foreign","dart.async#_hasError","merge","handleValue","resolve","rti#_message","stream_queue.dart#_updateRequests","dart.async#_delegateCache","hasFragment","traces","isScheduled","union_set.dart#_iterable","invoker.dart#_onCloseCompleter","isNotEmpty","test.dart#_captured_body_0","hasScheme","engine.dart#_closedBeforeDone","span_exception.dart#_span","dart.async#_captured_cleanUp_1","dart._internal#_source","fuse","live_suite_controller.dart#_suite","invoker.dart#_runTearDowns","dart.async#_captured_elements_0","addStream","rti#_precomputed3","null_stream_sink.dart#_checkEventAllowed","chain.dart#_captured_terse_0","patterns","stream_completer.dart#_setEmpty","dart.core#_fragment","createTimer","variables","runner_suite.dart#_onDebuggingController","dart.async#_captured_protected_0","every","trace.dart#_captured_trace_0","perform","dart.async#_captured_bodyFunction_0","dart.convert#_allowInvalid","pool.dart#_captured_this_0","outputId","dart.async#_onResume","dart.convert#_extraUnits","toUpperCase","equals_matcher.dart#_value","dart.async#_controller","multi_channel.dart#_captured_this_0","engine.dart#_group","guarantee_channel.dart#_addStreamSubscription","queue_list.dart#_add","forEachJsField","_js_helper#_regExp","_js_helper#_nums","_js_helper#_getTableBucket","dart.convert#_computeKeys","stack_trace_mapper.dart#_mapping","millisecondsSinceEpoch","_js_helper#_cell","connectOut","union_set.dart#_sets","engine.dart#_onUnpaused","_js_helper#_genericClosure","stack_trace_mapper.dart#_mapContents","pretty_print.dart#_captured_indent_2","multi_channel.dart#_innerStreamSubscription","substring","entries","multi_channel.dart#_inner","hasRun","stack_zone_specification.dart#_onError","elapsedTicks","engine.dart#_onTestStartedGroup","tearDownAll","core_matchers.dart#_matcher","expanded.dart#_engine","dart.async#_captured_future_0","_js_helper#_captured_getTag_0","names","internalContainsKey","dart.async#_captured_start_2","dart.async#_addStreamState","stream_queue.dart#_extractStream","setState","clear","dart.core#_stop","stream_group.dart#_closed","os","hasPartialInput","dart.collection#_getBucket","declarer.dart#_timeout","parts","context.dart#_pathDirection","findSlot","dart.async#_scheduleMicrotask","engine.dart#_loadPool","stream_sink_completer.dart#_canSendDirectly","local","hour","packageRoot","scanner.dart#_endOfFileEmitted","dart.async#_captured_callback_0","chain.dart#_captured_terse_1","future_group.dart#_closed","dart.convert#_value","readSlot","fork","elementAt","dart.async#_runUnary","writeAll","dart.async#_captured_callback_3","stack_zone_specification.dart#_captured_arg_1","writeSlot","dart.async#_next","rti#_hashCode","stream_group.dart#_onListen","dart.async#_captured_sourceResult_2","runOnce","dart.convert#_reviver","invoker.dart#_captured_this_1","innerStream","lazy_chain.dart#_thunk","stream_queue.dart#_ensureListening","stack_zone_specification.dart#_chains","dart.async#_captured_listener_1","startColumn","status","dart.async#_removeAfterFiring","multi_channel.dart#_box_0","dart.dom.html#_eventType","dart.collection#_head","resume","_js_helper#_removeHashTableEntry","_js_helper#_match","dart.async#_isFiring","includeTags","_interceptors#_current=","intersection_selector.dart#_selector2","rti#_rti","dart.async#_asyncComplete","request","expanded.dart#_gray","stack_trace_formatter.dart#_except","engine.dart#_subscriptions","subscription_stream.dart#_source","stack_trace_mapper.dart#_sdkRoot","dart.async#_recordResume","scheme","dart.convert#_expectedUnits","source_maps.parser#_captured_column_0","dart.collection#_closeGap","highlighter.dart#_buffer","sink.dart#_sink","map","parser.dart#_scanner","rti#_bindCache","dart._internal#_name","stack_trace_formatter.dart#_only","removeEventListener","_js_helper#_setTableEntry","live_test_controller.dart#_close","dart.core#_queryParameters","_js_helper#_length","engine.dart#_captured_this_1","pretty_print.dart#_box_0","addMapping","description.dart#_out","dart.async#_captured_R_3","dart.async#_isClosed","flush","remote_listener.dart#_captured_getMain_1","expanded.dart#_onStateChange","functions.dart#_captured_K1_2","toLowerCase","heartbeat","registerBinaryCallback","_js_helper#_method","dart.collection#_writeToList","contains","removeOutstandingCallback","functions.dart#_captured_value_1","dart.async#_prependListeners","dart.core#_data","chain.dart#_captured_callback_0","guarantee_channel.dart#_inner","dart.async#_fork","_js_helper#_nextIndex","dart.core#_captured_uri_0","source_maps.parser#_maps","dart.convert#_bufferIndex","expanded.dart#_red","dart.collection#_unlinkCell","forEachObjectKey","isRootRelative","engine.dart#_restarted","platform_selector.dart#_captured_validVariables_1","dart.async#_doneFuture","dart.convert#_original","dart.async#_registerCallback=","foldFrames","remote_listener.dart#_captured_channel_3","live_test_controller.dart#_onMessageController","separatorPattern","dart.convert#_isFirstCharacter","stack_zone_specification.dart#_errorZone","addStreamFuture","declarer.dart#_built","rti#_requiredPositional","dart.async#_captured_test_2","dart.collection#_table","_js_helper#_deleteTableEntry","split","group.dart#_captured_callback_0","remote_listener.dart#_listen","source_maps.parser#_mapUrl","validatePlatformSelectors","dart.async#_map","hasEmptyPath","sublist","stream_completer.dart#_stream","invoker.dart#_onRun","dart.async#_subscribe","util.dart#_captured_x_0","stream_completer.dart#_sourceStream","metadata.dart#_chainStackTraces","stream_sink_completer.dart#_setDestinationSink","addTearDownAll","live_suite_controller.dart#_isComplete","dart.async#_captured_result_0","equals_matcher.dart#_captured_expectedElement_1","package_config_resolver.dart#_uri","dart.async#_reverseListeners","dart.collection#_last","invoker.dart#_captured_timeout_0","walk","dart.core#_userInfo","formatStackTrace","remove","dart.async#_captured_listener_2","_js_helper#_keys","dart.convert#_encoder","runBinary","dart.async#_cancelFuture","future_group.dart#_captured_this_0","handlesComplete","trace.dart#_box_0","dart.async#_captured_pos_1","invoker.dart#_test","metadata.dart#_captured_timeout_2","guarantee_channel.dart#_box_0","cancelSchedule","sourceNameId","runtimeType","dart.collection#_modifications","then","pretty_print.dart#_captured_maxLineLength_1","dart.convert#_subsetMask","testRandomizeOrderingSeed","visitOr","expanded.dart#_lastProgressFailed","dart.convert#_first","millisecond","highlighter.dart#_captured_this_1","dart.async#_rootRegisterUnaryCallback","dart.async#_captured_f_1","remote_listener.dart#_captured_this_0","reversed","dart.core#_queryParameterLists","hasErrorCallback","metadata.dart#_captured_testOn_1","left","live_test_controller.dart#_isClosed","highlighter.dart#_captured_this_0","dart.dom.html#_start","lazy_chain.dart#_chain","null_stream_sink.dart#_addingStream","_js_helper#_getTableCell","forTarget","source_map_stack_trace.dart#_captured_minified_2","peekChar","dart.collection#_next","build","dart.convert#_process","rti#_precomputed2","lastMatch","expanded.dart#_description","metadata.dart#_captured_chainStackTraces_5","remote_listener.dart#_captured_printZone_5","decoder","hasAuthority","unaryOnError","context.dart#_needsNormalization","onResume","expanded.dart#_printPath","_interceptors#_tdivSlow","_js_helper#_rest","expanded.dart#_paused","declarer.dart#_tearDownAll","dart.async#_captured_result_3","lazy_trace.dart#_thunk","waitForOutstandingCallbacks","dart.async#_mayComplete","dart.async#_captured_T_5","function","dart.collection#_offset","dart.async#_captured_value_1","bindUnaryCallbackGuarded","dart.async#_sendDone","invoker.dart#_outstandingCallbacks","extensions","dart.async#_closeUnchecked","_interceptors#_toListGrowable","highlighter.dart#_captured_end_2","invoker.dart#_captured_this_0","codeUnits","rti#_precomputed1","stack_zone_specification.dart#_captured_f_1","internalGet","suite_channel_manager.dart#_names","pattern","dart.async#_captured_stackTrace_1","live_suite_controller.dart#_liveSuite","source_maps.parser#_consumeNewLine","metadata.dart#_box_0","suiteSink","dart.core#_port","engine.dart#_passedGroup","dart.core#_hostStart","context.dart#_isWithinOrEquals","expanded.dart#_captured_liveTest_1","live_suite_controller.dart#_closeMemo","dart.async#_captured_target_0","dart.core#_captured_host_1","dart.core#_uriCache","_js_helper#_nativeAnchoredVersion","scanner.dart#_consumeWhitespace","scanner.dart#_scanOr","dart.dom.html#_tryResume","runner_suite.dart#_suite=","toSet","chain.dart#_captured_level_1","sourceColumn","dart.async#_nextListener","connectIn","_js_helper#_isCaseSensitive","invoker.dart#_body","encoder","metadata","dart.async#_isInputPaused","inHours","allowRelease","_js_helper#_captured_getUnknownTag_0","invoker.dart#_completer","intersection","state","dart.async#_state","reportLiveTest","dart.async#_clearPendingComplete","invoker.dart#_captured_timeout_2","stack_trace_mapper.dart#_mapUrl","multi_channel.dart#_controllers","declarer.dart#_tearDownAllTrace","chain.dart#_captured_T_1","highlighter.dart#_box_0","multi_channel.dart#_captured_T_2","expanded.dart#_subscriptions","dart.collection#_captured_V_2","stack_zone_specification.dart#_captured_original_1","subscription_stream.dart#_captured_this_0","stream_queue.dart#_captured_this_0","live_test_controller.dart#_runCalled","group.dart#_testCount","onDone","dart.async#_isInitialState","isEven","_js_helper#_types","root","highlighter.dart#_writeIntermediateLines","library","dart.core#_hasValue","member","dart.async#_lastSubscription=","dartException","dart.core#_schemeEnd","_js_helper#_captured_this_0","isPosix","dart._internal#_hasSkipped","dart.convert#_isUpgraded","dart.async#_print=","dart.async#_rootRegisterBinaryCallback","dart.dom.html#_useCapture","test.src.runner.browser.post_message_channel#_captured_port_0","type","scanner.dart#_scanIdentifier","dart.async#_onDone","origin","multi_channel.dart#_parent","%","_js_helper#_keysArray","span_scanner.dart#_sourceFile","metadata.dart#_captured_skip_3","insertAll","platform_selector.dart#_inner","pretty_print.dart#_captured_pp_0","engine.dart#_captured_this_0","dart.async#_eventState","child","forTag","guarantee_channel.dart#_channel","dart.async#_captured_iterator_0","checkMutable","remote_listener.dart#_captured_controller_3","replaceFirst","file.dart#_binarySearch","transform","stack_trace_formatter.dart#_mapper","_interceptors#_tdivFast","trace.dart#_captured_oldPredicate_0","_js_helper#_exception","stack_zone_specification.dart#_captured_arg2_2","remote_listener.dart#_suite","isIdentifier","rti#_primary","removeAt","dart.async#_captured_div_1","dart._internal#_current=","_js_helper#_current=","dart.dom.html#_removeEventListener","rti#_optionalNamed","dart.async#_isSent","_js_helper#_receiver","forPlatform","dart.async#_delegate","firstPendingEvent","inSameErrorZone","frames","highlighter.dart#_span","remote_listener.dart#_captured_channel_2","dart._internal#_currentExpansion","union_set_controller.dart#_sets","dart.async#_captured_this_0","_js_helper#_isUnicode","lazy_trace.dart#_captured_terse_2","span_exception.dart#_source","dart._internal#_start","_js_helper#_modifications","dart.core#_nextPosition","dart.convert#_toEncodable","hasMatch","dart.async#_canFire","postMessage","internalComputeHashCode","invoker.dart#_outstandingCallbackZones","invoker.dart#_captured_zone_1","rootPattern","multi_channel.dart#_captured_id_1","platform_selector.dart#_span","isUtc","dart.dom.html#_postMessage_2","set","pathFromUri","dart.async#_hasOneListener","engine.dart#_activeLoadTests","_js_helper#_containsTableEntry","restartable_timer.dart#_timer","dart.async#_pendingEvents","guarantee_channel.dart#_addError","_js_helper#_captured_prototypeForTag_0","dart.async#_nullErrorHandler","dart.async#_captured_cleanUp_3","+","dart.async#_chainSource","dart.core#_portStart","remote_listener.dart#_printZone","multi_channel.dart#_captured_T_1","frame.dart#_captured_frame_0","source_maps.parser#_columnStart","functions.dart#_captured_result_0","engine.dart#_addLiveSuite","_js_helper#_pattern","guarantee_channel.dart#_onStreamDisconnected","dart.core#_stackTrace","elapsed","accept","dart.async#_subscription","stack_trace_mapper.dart#_packageResolver","stream_queue.dart#_eventsReceived","_js_helper#_isMultiLine","live_test_controller.dart#_errors","_interceptors#_index","onZero","chain.dart#_captured_chain_0","engine.dart#_runSkippedTest","pretty_print.dart#_captured__prettyPrint_1","removeAll","stack_zone_specification.dart#_captured_arg1_1","dart.async#_callOnCancel","live_suite_controller.dart#_onCompleteGroup","last","runner_suite.dart#_channelNames","sourceUrl","dart.async#_onListen","pool.dart#_resetTimer","engine.dart#_liveSuites","stream_channel_completer.dart#_set","file.dart#_end","dart.async#_captured_value_2","runner_suite.dart#_gatherCoverage","dart.core#_isHttps","dart.collection#_captured_result_1","multi_channel.dart#_closedIds","remote_listener.dart#_captured_channel_0","isNewLine","invoker.dart#_runCount","union_set.dart#_captured_this_0","suite.dart#_runSkipped","live_suite_controller.dart#_skipped","stack_zone_specification.dart#_captured_R_2","dart.core#_isPackage","dart.async#_expectsEvent","metadata.dart#_validateTags","copy","invoker.dart#_captured_error_2","dart.async#_addPending","dart.convert#_stringSink","remainder","guarantee_channel.dart#_inAddStream","pool.dart#_captured_registered_1","runtime.dart#_captured_serialized_0","pool.dart#_onReleaseCompleters","functions.dart#_captured_result_1","inGoogle","runBinaryGuarded","guarantee_channel.dart#_allowErrors","declarer.dart#_captured_body_0","dart.async#_createSubscription","condition","checkGrowable","absolutePathToUri","suite.dart#_runtimes","engine.dart#_captured_loadResource_2","dart.collection#_rest","dart.async#_setRemoveAfterFiring","guarantee_channel.dart#_sink","metadata.dart#_captured_retry_6","context.dart#_current","dart.async#_registerBinaryCallback=","stream_completer.dart#_controller","isCore","highlighter.dart#_captured_line_1","getOffset","dart.async#_createPeriodicTimer","pool.dart#_timeout","mustCopy","dart.async#_firstSubscription","scanner.dart#_next","onTestStarted","scanner.dart#_scanAnd","dart.async#_once","dart.core#_query","config","dart.async#_future","next","style","invoker.dart#_tearDowns","_js_helper#_getBucket","expanded.dart#_stopwatch","engine.dart#_active","dart.async#_rootRun","dart.async#_guardCallback","live_suite_controller.dart#_onTestStartedController","path","dart.async#_target","functions.dart#_captured_K2_0","suite.dart#_knownTags","dart.async#_tick","pool.dart#_onReleaseCallbacks","remote_listener.dart#_captured_suite_0","dart.core#_pathStart","platform_selector.dart#_captured_platform_0","restartable_timer.dart#_duration","test.src.runner.browser.post_message_channel#_captured_portSubscription_1","guarantee_channel.dart#_captured_this_0","setEmpty","dart.typed_data.implementation#_invalidPosition","dart.collection#_containsKey","string_scanner.dart#_lastMatchPosition","metadata.dart#_captured_onPlatform_8","lazy_chain.dart#_captured_predicate_1","dart.async#_addListener","multi_channel.dart#_mainController","guarantee_channel.dart#_captured_this_1","invoker.dart#_box_0","_interceptors#_length","nextKind","dart.collection#_box_0","guarantee_channel.dart#_subscription","addTo","dart.core#_uri","isDone","dart.async#_stateData","setChannel","dart.async#_captured_R_2","stream_channel_completer.dart#_channel=","runes","dart.core#_jsWeakMapOrKey","dart.collection#_queue","null_stream_sink.dart#_closed","file.dart#_lineStarts","stream_queue.dart#_eventQueue","isSeparator","_js_helper#_arguments","guarantee_channel.dart#_disconnected","span_with_context.dart#_context","stream_group.dart#_captured_stream_1","source_maps.parser#_indexFor","dart.async#_cancelOnError","rest","rti#_rest","dart.async#_captured_stackTrace_2","stream_subscription.dart#_source","dart.core#_toFilePath","sourceUrlId","_interceptors#_shrOtherPositive","guarantee_channel.dart#_closed","future_group.dart#_onIdleController","dart.core#_value","dart.async#_captured_error_1","writeCharCode","declarer.dart#_tearDownAlls","source_map_stack_trace.dart#_captured_sourceMap_1","_js_helper#_self","onStateChange","invoker.dart#_timeoutTimer","currentChain","print_sink.dart#_buffer","live_test_controller.dart#_suite","string","engine.dart#_captured_liveTest_1","isBrowser","engine.dart#_suiteController","rti#_canonicalRecipe","dart.dom.html#_canceled","_js_helper#_nativeGlobalVersion","dart.async#_pending","queue_list.dart#_tail","dart.async#_createTimer","passed","dart.async#_onData","dart.async#_captured_action_1","declarer.dart#_captured_body_1","stream_group.dart#_captured_this_0","remote_listener.dart#_captured_liveTest_1","remote_listener.dart#_captured_beforeLoad_4","invoker.dart#_printsOnFailure","dart.core#_writeAuthority","pool.dart#_onTimeout","startChunkedConversion","handleWhenComplete","guarantee_channel.dart#_addStreamCompleter","dart.collection#_captured_K_1","inputId","cloneNotRequired","first","shuffle","engine.dart#_pauseCompleter","newJsList","dart.async#_registerUnaryCallback=","key","_js_helper#_first","dart.async#_captured_T_1","name","dart.dom.html#_postMessage_1","dart.collection#_keys","onPause","dart.async#_captured_data_1","hasQuery","dart.collection#_nums","dart.async#_setErrorObject","dart.collection#_source","handlesValue","stack_zone_specification.dart#_captured_R_3","remote_listener.dart#_captured_channel_1","seen","lazy_chain.dart#_inner","intersection_selector.dart#_selector1","source_maps.parser#_consumeNewSegment","dart.convert#_urlSafe","input","subscription_stream.dart#_captured_stackTrace_2","isRunning","trace.dart#_captured_level_1","impl.dart#_selector","stream_queue.dart#_pause","dart.core#_isScheme","parsed_path.dart#_captured_this_0","declarer.dart#_captured_this_0","stream_completer.dart#_isSourceStreamSet","stream_channel_controller.dart#_local","length","separator","stack_zone_specification.dart#_captured_T_3","subscription_stream.dart#_captured_handleError_0","dart.async#_setChained","expanded.dart#_yellow","equals_matcher.dart#_captured_location_2","cleanupSlots","equals_matcher.dart#_captured_depth_3","suite.dart#_jsTrace","dart.async#_captured_dispatch_1","dart.collection#_end","equals_matcher.dart#_captured_matcher_0","dart.collection#_modificationCount","dart.convert#_processed","pool.dart#_timer","dart.core#_writeString","metadata.dart#_captured_platform_1","string_scanner.dart#_fail","isClosed","keys","isPaused","test_core#_captured_engine_0","declarer.dart#_setUps","expanded.dart#_sink","dart.collection#_grow","text","live_test_controller.dart#_onErrorController","dart.core#_text","dart._internal#_captured_this_0","handlesError","dart.core#_contents","dart.async#_captured_milliseconds_1","source_map_stack_trace.dart#_captured_sdkLib_3","dart.core#_initializeText","chain.dart#_captured_trace_0","rti#_evalCache","equals_matcher.dart#_limit","dart.async#_toggleEventId","live_suite_controller.dart#_active","stack_zone_specification.dart#_createNode","toSpec","userInfo","excludeTags","dart.core#_separatorIndices","test.dart#_captured_completer_1","rti#_is","dart.async#_isUsed","highlighter.dart#_paddingAfterSidebar","code","sink","metadata.dart#_captured_skipReason_7","stream_sink_completer.dart#_destinationSink","future_group.dart#_values","suite.dart#_metadata","engine.dart#_addLoadSuite","invoker.dart#_captured_message_1","values","_js_helper#_nativeRegExp","validator.dart#_isDefined","stream_queue.dart#_isDone","_js_helper#_isDotAll","offset","putIntoObject","copies","dart.async#_runBinary","_js_helper#_start","stream_queue.dart#_source","year","stream_queue.dart#_requestQueue","$le","$indexSet","$index","$xor","$or","$eq","$mod","$shr","$and","$ge","$gt","$lt","$mul","$not","$shl","$div","$sub","$add","$negate","$tdiv","checkString","instanceTypeName","constructorNameFallback","isJsArray","getIndex","selfFieldName","receiverFieldName","_rtiEval","extractFunctionTypeObjectFrom","rawRtiToJsConstructorName","isGenericFunctionTypeParameter","isDartFunctionType","isDartFutureOrType","isNotIdentical","_instanceFunctionType","instanceOf","invoke","setDispatchProperty","propertyGet","regExpGetGlobalNative","stringReplaceJS","checkNull","regExpGetNative","_getFutureOrArgument","_lookupFutureRti","_setPrecomputed1","_getBindCache","_setBindCache","_getGenericFunctionBase","_getKind","_lookupStarRti","_canonicalRecipeOfStar","_Universe._lookupStarRti","_lookupQuestionRti","_canonicalRecipeOfQuestion","_Universe._lookupQuestionRti","_lookupFutureOrRti","_canonicalRecipeOfFutureOr","_Universe._lookupFutureOrRti","_getInterfaceName","_getBindingBase","_getReturnType","_getGenericFunctionParameterIndex","asString","allocate","_setRequiredPositional","_setOptionalPositional","_setOptionalNamed","_setCachedRuntimeType","_setTypeCheckFunction","_setAsCheckFunction","_getPrimary","_setSpecializedTestResource","_setIsTestFunction","isLegacySubtype","_getSpecializedTestResource","_getStarArgument","_getQuestionArgument","_lookupErasedRti","_getEvalCache","_setEvalCache","_cacheSet","_createTerminalRti","_setKind","_setCanonicalRecipe","_createUnaryRti","_setPrimary","_createGenericFunctionParameterRti","_canonicalRecipeOfInterface","_createInterfaceRti","_setRest","_canonicalRecipeOfBinding","_createBindingRti","_canonicalRecipeOfFunction","_canonicalRecipeOfFunctionParameters","_createFunctionRti","_canonicalRecipeOfGenericFunction","_createGenericFunctionRti","charCodeAt","toGenericFunctionParameter","_lookupDynamicRti","_lookupVoidRti","pushStackFrame","push","setPosition","handleTypeArguments","collectArray","arraySplice","handleFunctionArguments","handleOptionalGroup","handleNamedGroup","collectNamed","isDigit","evalTypeVariable","_lookupNeverRti","_lookupAnyRti","_castToRti","stringLessThan","functionParametersEqual","lookupInterceptorByConstructor","cacheInterceptorOnConstructor","_future","_setValue","_isComplete","_setPendingComplete","_mayComplete","_mayAddListener","_chainSource","_setChained","_hasError","_error","_zone","_removeListeners","_cloneResult","_setErrorObject","_scheduleImmediate","_leave","_createPeriodicTimer","printToConsole","es6","tryParse","objectToHumanReadableString","makeListFixedLength","makeFixedListUnmodifiable","_stringFromJSArray","_stringFromUint8List","_writeOne","_startsWithData","_checkLength","_internal","_stringOrNullLength","_writeString","_isZoneIDChar","_isRegNameChar","_isGeneralDelimiter","_isSchemeCharacter","_isUnreservedChar","fromString","_lineStarts","fromList","_incomingConnections","_outgoingConnections","_names","_requestedResources","_onReleaseCallbacks","_onReleaseCompleters","_closeMemo","_completer","AsyncMemoizer._completer","factor","_group","_values","FutureGroup._completer","_suiteController","_onTestStartedGroup","_state","_subscriptions","StreamGroup._subscriptions","_passedGroup","_skippedGroup","_failedGroup","_active","_addedSuites","_onSuiteAddedController","Engine._onSuiteAddedController","_liveSuites","_onSuiteStartedController","Engine._onSuiteStartedController","_restarted","_activeLoadTests","_sets","_errors","LiveTestController.completer","_onStateChangeController","LiveTestController._onStateChangeController","_onErrorController","LiveTestController._onErrorController","_onMessageController","LiveTestController._onMessageController","serializeSuite","_closable","_out","myInlinedMethod","_lineStart","_columnStart","_maps","_mappings","_setUps","_tearDowns","_setUpAlls","_timeout","_tearDownAlls","_entries","_soloEntries","_isTextAtEndOfContext","_chains","_createKey","_currentSpec","_createNode","withGuarantees","_child","_onCompleteGroup","_onCloseCompleter","LiveSuiteController._onCloseCompleter","_onTestStartedController","LiveSuiteController._onTestStartedController","_passed","_skipped","_failed","_toListGrowable","_mainController","_controllers","_pendingIds","_closedIds","Window.onMessage","jsify","listToString","_handleIEtoString","_codeUnitAt","_currentExpansion","_types","_getBucket","_isMultiLine","_isUnicode","_isTrailSurrogate","_rtiBind","_addListener","_isFiring","_setRemoveAfterFiring","_isEmpty","_isAddingStream","_expectsEvent","_hasOneListener","_errorTest","_onError","thenAwait","_setError","_isPendingComplete","_clearPendingComplete","_whenCompleteAction","_onValue","_isInitialState","_mayAddEvent","_isCanceled","_isPaused","_isClosed","_isInputPaused","_hasPending","_inCallback","_waitsForCancel","_eventScheduled","_isScheduled","_rethrow","_hasTableEntry","identityHashCode","checkValidIndex","_grow","_checkModification","_isUpgraded","parseHexByte","withBufferSize","unary-","_microseconds","_checkType","_getFromObject","_setOnObject","_now","_isWindows","_toFilePath","_initializeText","_writeAuthority","_isPackage","convertDartToNative_SerializedScriptValue","_canceled","fromMillisecondsSinceEpoch","isJavaScriptSimpleObject","_isSourceStreamSet","_setSourceStream","_NextRequest._completer","_pause","_close","_setEmpty","_scanOr","_scanAnd","_scanIdentifier","_setBase","StringDescription.add","addStateInfo","_indent","reset","_onResourceReleased","_consumeValue","glyphs","_paddingAfterSidebar","_normalizeContext","_buffer","Highlighter._","dataFromString","_disabled","_doneCompleter","_GuaranteeSink._doneCompleter","_inAddStream","MessageEvent.data","_prefix","_solo","Declarer._solo","Invoker._onCloseCompleter","_closableKey","_outstandingCallbackZones","_counterKey","_printsOnFailure","_AsyncCounter._completer","_guardIfGuarded","_print","_run","jsonDecode","_except","_only","_MultiChannel.stream","_eventQueue","_requestQueue","ascii","_sink","_listen","_streamCompleter","_stream","_sinkCompleter","markGrowable","_timeString","_local","_channelNames","watch","ExpandedReporter.watch","_stopwatch","ExpandedReporter._stopwatch","_initTicker","Engine.onTestStarted","provokeCallErrorOnNull","provokeCallErrorOnUndefined","provokePropertyErrorOnNull","provokePropertyErrorOnUndefined"],"mappings":"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","x_org_dartlang_dart2js":{"minified_names":{"global":"main_closure,2397,internalBootstrapBrowserTest,535,Closure_fromTearOff,2398,StaticClosure,2399,BoundClosure,2400,Closure_functionCounter,2401,Closure_forwardCallTo,2402,Closure__computeSignatureFunctionNewRti,2403,_checkStringNullable,181,wrapException,42,CyclicInitializationError,2404,toStringWrapper,43,NullThrownError,2405,S,12,argumentErrorValue,40,ArgumentError,395,Error_safeToString,2406,_isBool,168,Error__objectToString,2407,Closure,2408,Primitives_objectTypeName,2409,Primitives__objectTypeNameNewRti,2410,Object,2411,instanceType,145,_rtiToString,184,Primitives__saneNativeClassName,2412,assertHelper,79,_unminifyOrTag,186,Rti__getInterfaceTypeArguments,2413,_rtiArrayToString,182,_functionRtiToString,90,Rti__getGenericFunctionBounds,2414,ioore,37,diagnoseIndexError,38,_isInt,173,_checkIntNullable,175,iae,36,IndexError$,2415,RangeError$value,2416,_checkNumNullable,178,RangeError,398,IndexError,404,setRuntimeTypeInfo,83,isTopType,243,Rti__getFunctionParameters,2417,ArgumentError$value,2416,_arrayInstanceType,147,UnsupportedError$,2415,throwExpression,44,UnsupportedError,405,unmangleGlobalNameIfPreservedAnyways,246,assertTest,77,AssertionError$,2415,AssertionError,394,TypeErrorImplementation$,2415,TypeErrorImplementation,75,_typeDescription,76,extractFunctionTypeObjectFromInternal,74,runtimeTypeToString,86,_runtimeTypeToString,87,unminifyOrTag,10,_joinArguments,92,_functionRtiToString0,90,extractKeys,245,JSArray_JSArray$markFixed,2418,JSArray,2419,JSArray_markFixedList,2420,StringBuffer,2421,_checkBoolNullable,170,getIsolateAffinityTag,82,IterableBase_iterableToFullString,2422,_isToStringVisiting,357,_toStringVisiting,2423,StringBuffer__writeAll,2424,IterableElementError_noElement,2425,StateError,407,ArrayIterator,2426,throwConcurrentModificationError,45,ConcurrentModificationError$,2415,ConcurrentModificationError,408,ListIterator,2427,ListMixin,2428,_checkValidIndex,124,Iterable,2429,initNativeDispatchFlag,2430,initNativeDispatch,104,UnimplementedError$,2415,lookupAndCacheInterceptor,99,getTagFunction,2431,dispatchRecordsForInstanceTags,2432,interceptorsForUncacheableTags,2433,alternateTagFunction,2434,makeLeafDispatchRecord,102,patchInteriorProto,101,makeDispatchRecord,248,JavaScriptIndexingBehavior,2435,UnimplementedError,406,initNativeDispatchContinue,105,initHooks,107,prototypeForTagFunction,2436,makeDefaultDispatchRecord,103,applyHooksTransformer,108,initHooks_closure,2437,initHooks_closure0,2437,initHooks_closure1,2437,_TypeError__TypeError$forType,2438,_TypeError,2439,_Error_compose,2440,_CastError__CastError$forType,2438,_CastError,2441,instanceOrFunctionType,144,_TypeError$fromMessage,2442,Rti__isUnionOfFunctionType,2443,closureFunctionType,143,getTypeFromTypesTable,151,_Universe_eval,2444,_Universe__parseRecipe,2445,_Parser_create,2446,_Parser_parse,2447,_Parser_handleDigit,2448,_Parser_handleIdentifier,2449,_Parser_toType,2450,_Universe__lookupGenericFunctionParameterRti,2451,_Universe__lookupTerminalRti,2452,_Parser_toTypes,2453,_Universe__lookupInterfaceRti,2454,_Universe__lookupGenericFunctionRti,2455,_Universe__lookupBindingRti,2456,_Parser_handleExtendedOperations,2457,assertThrow,78,_Universe__lookupUnaryRti,2458,_FunctionParameters,2459,_Universe__lookupFunctionRti,2460,_Parser_toTypesNamed,2461,_Universe__canonicalRecipeJoin,2462,_Universe__canonicalRecipeJoinNamed,2463,Rti,2464,_Universe__finishRti,2465,_generalTypeCheckImplementation,159,_generalAsCheckImplementation,158,_installSpecializedIsTest,154,_generalIsTestImplementation,156,_isTop,166,_asTop,167,int,2466,double,2467,_isNum,176,num,2468,String,2469,_isString,179,bool,2470,isLegacyTopType,242,_isTestViaProperty,157,_AssertionError,2471,Rti__getBindingArguments,2472,_Parser_indexToType,2473,_Universe_findRule,2474,Rti__getCanonicalRecipe,2475,_Universe_evalInEnvironment,2476,_CastError$fromMessage,2442,_isSubtype,233,Rti__getFutureFromFutureOr,2477,typesEqual,240,_isFunctionSubtype,236,_isInterfaceSubtype,237,typeEqual,238,namedTypesEqual,241,Future,272,_Universe_bind,2478,_instanceTypeFromConstructor,149,_instanceTypeFromConstructorMiss,150,_Universe_findErasedType,2479,BoundClosure_evalRecipeIntercepted,2480,BoundClosure_evalRecipe,2481,Closure_forwardInterceptedCallTo,2482,Closure_cspForwardCall,2483,BoundClosure_selfFieldNameCache,2484,BoundClosure_computeFieldNamed,2485,BoundClosure_selfOf,2486,BoundClosure_receiverFieldNameCache,2487,Closure_cspForwardInterceptedCall,2488,BoundClosure_receiverOf,2489,RuntimeError$,2415,RuntimeError,81,getRuntimeTypeInfo,84,substitute,95,invokeOn,97,internalBootstrapBrowserTest_closure,2490,RemoteListener_start,2491,postMessageChannel,631,StreamChannel,2257,_ControllerStream,2492,_instanceType,148,_Future,265,Zone__current,2493,Stream_length_closure,1045,Stream_length_closure0,1045,Null,2494,Stream,2495,AsyncError,2496,_Future__propagateToListeners,2497,_Future__propagateToListeners_handleWhenCompleteCallback,2498,_Future__propagateToListeners_handleValueCallback,2499,_Future__propagateToListeners_handleError,2500,_Future__chainCoreFuture,2501,_Future__prependListeners_closure,2502,boolConversionCheck,73,unwrapException,51,getTraceFromException,52,ExceptionAndStackTrace,2503,_StackTrace,2504,unwrapException_saveStackTrace,2505,JsNoSuchMethodError$,2415,NullError$,2415,UnknownJsTypeError,2506,StackOverflowError,2507,TypeErrorDecoder_extractPattern,2508,quoteStringForRegExp,114,TypeErrorDecoder,2509,TypeErrorDecoder_provokePropertyErrorOn,2510,TypeErrorDecoder_provokeCallErrorOn,2511,NullError,49,JsNoSuchMethodError,50,_Future__propagateToListeners_handleWhenCompleteCallback_closure,2512,_registerErrorHandler,297,_FutureListener,2513,_rootScheduleMicrotask,331,_scheduleAsyncCallback,300,_RootZone_bindCallback_closure,1244,_RootZone_bindCallbackGuarded_closure,2514,_rootRun,324,_rootHandleUncaughtError,323,_rootHandleUncaughtError_closure,2515,_schedulePriorityAsyncCallback,301,_nextCallback,2516,_lastPriorityCallback,2517,_lastCallback,2518,_AsyncCallbackEntry,2519,Zone__enter,2520,_isInCallbackLoop,2521,_microtaskLoop,298,_AsyncRun__initializeScheduleImmediate,2522,_AsyncRun__initializeScheduleImmediate_internalCallback,2523,convertDartClosureToJS,59,_AsyncRun__initializeScheduleImmediate_closure,2524,Timer__createTimer,2525,Duration_toString_twoDigits,2526,Duration,392,Duration_toString_sixDigits,2527,_TimerImpl$,2415,_TimerImpl,261,_TimerImpl_internalCallback,2528,_AsyncRun__scheduleImmediateWithSetImmediate_internalCallback,2529,_AsyncRun__scheduleImmediateJsOverride_internalCallback,2530,invokeClosure,57,_Exception,2531,_rootRunBinary,326,_rootRunUnary,325,_Future__addListener_closure,2532,_BufferingStreamSubscription$,2415,_PendingEvents,2533,_BufferingStreamSubscription,310,ArgumentError$,2415,_Future__chainForeignFuture,2534,_Future__chainForeignFuture_closure,2535,_Future__chainForeignFuture_closure0,2535,_Future__chainForeignFuture_closure1,2535,scheduleMicrotask,302,get$scheduleMicrotask,302,_StreamControllerLifecycle,2536,StreamController,307,StreamConsumer,2537,Stream_pipe_closure,2538,_GuaranteeSink,2539,StreamChannelController$,2415,_EventStream,2540,postMessageChannel_closure,2541,postMessageChannel_closure0,2541,LinkedHashMap_LinkedHashMap$_literal,2542,_convertDataTree,466,_EventStreamSubscription$,2415,_EventStreamSubscription_closure,2543,_wrapZone,473,_EventStreamSubscription,472,_RootZone_bindUnaryCallbackGuarded_closure,1247,_convertDataTree__convert,2544,_IdentityHashMap,2545,MapBase_mapToString,2546,MapBase_mapToString_closure,2547,MapMixin,2548,_HashMap__getTableEntry,2549,Primitives_objectHashCode,53,objectHashCode,53,_HashMapKeyIterable,2550,IterableBase_iterableToShortString,2551,_iterablePartsToStrings,358,RangeError_checkNotNegative,2552,RangeError$range,2553,_HashMapKeyIterator,2554,MappedIterable_MappedIterable,2415,MappedIterator,2555,Iterator,2556,EfficientLengthMappedIterable,2557,MappedIterable,3,MappedListIterable,2558,ListIterable,2559,_HashMap__newHashTable,2560,_HashMap__setTableEntry,2561,LinkedHashMap,346,JsLinkedHashMap,2562,fillLiteralMap,54,LinkedHashMapKeyIterable,2563,LinkedHashMapKeyIterator,870,LinkedHashMapCell,2564,postMessageChannel__closure,2565,postMessageChannel__closure0,2565,postMessageChannel__closure1,2565,_StructuredCloneDart2Js,2566,DateTime,2567,_StructuredClone_walk_closure,2568,_StructuredClone_walk_closure0,2568,_AcceptStructuredCloneDart2Js,2569,StateError$,2415,StreamSink,2570,StreamSubscription,2571,promiseToFuture,467,LinkedHashMap_LinkedHashMap$_empty,2572,_AcceptStructuredClone_walk_closure,2573,Primitives_getYear,2574,DateTime__fourDigits,2575,Primitives_getMonth,2576,DateTime__twoDigits,2577,Primitives_getDay,2578,Primitives_getHours,2579,Primitives_getMinutes,2580,Primitives_getSeconds,2581,Primitives_getMilliseconds,2582,DateTime__threeDigits,2583,Primitives_lazyAsJsDate,2584,_checkDoubleNullable,172,_AsyncCompleter,2585,promiseToFuture_closure,2586,promiseToFuture_closure0,2586,_Future__asyncCompleteError_closure,2587,_Future__asyncComplete_closure,2588,_Future__chainFuture_closure,2589,Stream_firstWhere_closure,1051,Stream_firstWhere_closure0,1051,_completeWithErrorCallback,287,Stream_firstWhere__closure,2590,Stream_firstWhere__closure0,2590,_cancelAndErrorClosure,317,_runUserCode,315,_cancelAndErrorClosure_closure,2591,_cancelAndError,316,_cancelAndError_closure,2592,_Future$zoneValue,2593,_cancelAndValue,318,_cancelAndValue_closure,2594,StreamChannelController,588,StreamController_StreamController,2415,_StreamSinkWrapper,2595,GuaranteeChannel$,2415,GuaranteeChannel,634,GuaranteeChannel_closure,2596,_StreamImplEvents,2597,_StreamControllerAddStreamState,1059,_SyncCompleter,2598,_GuaranteeSink_addStream_closure,2599,_GuaranteeSink__addError_closure,2600,GuaranteeChannel__closure,2601,_SyncStreamController,2602,_AsyncStreamController,2603,_EventDispatch,2604,_PendingEvents_schedule_closure,2605,_BufferingStreamSubscription__sendDone_sendDone,2606,_ControllerSubscription,1071,_StreamController__subscribe_closure,2607,_StreamController__recordCancel_complete,2608,_AddStreamState_cancel_closure,2609,_runGuarded,308,_DelayedError,2610,_BufferingStreamSubscription__sendError_sendError,2611,_DelayedData,2612,_MultiChannel$,2415,RemoteListener_start_closure,2613,_ZoneSpecification$,2415,Stream_Stream$fromIterable,2614,RemoteListener_start_closure0,2613,RemoteListener_start_closure1,2613,SuiteChannelManager,478,LinkedHashSet_LinkedHashSet$_empty,2572,runZoned,339,Map,2615,_runZoned,340,runZoned_closure,2616,_parentDelegate,322,_RootZone__rootDelegate,2617,_ZoneDelegate,2618,_rootFork,337,printToZone,2619,HashMap_HashMap$from,2620,_CustomZone,338,_ZoneFunction,2621,printString,247,_CustomZone_bindUnaryCallbackGuarded_closure,1205,_CustomZone_bindCallbackGuarded_closure,2622,_CustomZone_bindCallback_closure,1200,_TimerImpl$periodic,2623,_TimerImpl$periodic_closure,2624,_CustomZone_bindUnaryCallback_closure,1202,HashMap_HashMap,2415,_HashMap,2625,HashMap_HashMap$from_closure,2626,_LinkedHashSet,2627,_LinkedHashSetIterator,353,LinkedHashSet_LinkedHashSet$_literal,2542,RemoteListener_start__closure,2628,StackTraceFormatter,2236,RemoteListener_start___closure,2629,RemoteListener_start___closure0,2629,RemoteListener__sendError,2630,RemoteException_serialize,2631,TestFailure,2632,Chain_Chain$forTrace,2633,Chain_toString_closure,2634,Chain_toString_closure0,2634,instantiate1,8,checkTypeBound,160,checkNum,41,Chain_toString__closure,2635,Instantiation1,9,createRuntimeType,152,_Type,2636,instantiatedGenericFunctionType,134,_instantiate,135,_instantiateArray,139,_instantiateFunctionParameters,141,_instantiateNamed,140,Chain_toString__closure0,2635,getRuntimeType,93,Chain,2637,List_List$unmodifiable,2638,LazyChain,2639,Chain_Chain$forTrace_closure,2640,Chain_Chain$parse,2447,Chain_Chain$parse_closure,2641,Trace_Trace$parse,2447,Chain_Chain$parse_closure0,2641,Trace_toString_closure,2642,Trace_toString_closure0,2642,UnparsedFrame,630,Trace$parseFriendly,2643,WhereIterable,2644,Trace$parseFriendly_closure,2645,Trace$parseFriendly_closure0,2645,Trace,488,_StringStackTrace,2646,WhereIterator,2647,Frame_Frame$parseFriendly,2643,_parseUri,616,ParsedPath_ParsedPath$parse,2447,Context_split_closure,2648,List_List$from,2620,List,2649,ParsedPath,2650,List_List$filled,2651,ParsedPath_normalize_closure,2652,List_List$generate,2653,stringReplaceAllUnchecked,115,stringReplaceAllUncheckedString,116,JSSyntaxRegExp,2654,escapeReplacement,112,JSSyntaxRegExp_makeNative,2655,FormatException$,2415,FormatException,409,WindowsStyle,2366,RegExp_RegExp,2415,isDriveLetter,602,_Uri__uriDecode,2656,StringMatch,2657,CodeUnits,2658,_Uri__hexCharPairToByte,2659,Utf8Decoder,2660,UnmodifiableListMixin,2661,Utf8Decoder__convertIntercepted,2662,RangeError_checkValidRange,2663,_scanOneByteCharacters,372,String_String$fromCharCodes,2664,_Utf8Decoder,2665,Primitives_stringFromCharCode,2666,Primitives_stringFromCharCodes,2667,Primitives_stringFromNativeUint8List,2668,String__stringFromIterable,2669,Primitives_stringFromCodePoints,2670,Primitives__fromCharCodeApply,2671,Utf8Decoder__convertInterceptedUint8List,2672,Utf8Decoder__useTextDecoderChecked,2673,Utf8Decoder__unsafe,2674,Utf8Decoder__useTextDecoderUnchecked,2675,Utf8Decoder__makeDecoder,2676,RangeError_checkValueInInterval,2677,stringReplaceFirstUnchecked,120,stringReplaceRangeUnchecked,121,stringReplaceFirstRE,113,_StringAllMatchesIterable,2678,_StringAllMatchesIterator,2679,_MatchImplementation$,2415,_MatchImplementation,110,isAlphabetic,601,_AllMatchesIterable,2680,_AllMatchesIterator,2681,IterableElementError_tooFew,2682,JSArray_JSArray$fixed,2683,UrlStyle,2368,Context,615,current,621,get$current,621,PathException$,2415,_validateArgList,617,Context_join_closure,2684,Context_joinAll_closure,2685,SubListIterable$,2415,_validateArgList_closure,2686,SubListIterable,2,PathException,559,Uri_base,2687,_current,2493,set$_current,2493,_currentUriBase,2688,Primitives_currentUri,2689,Uri_parse,2447,UriData__parse,2690,_scan,465,_SimpleUri,2691,_Uri__Uri$notSimple,2692,int_parse,2447,Primitives_parseInt,2693,_Uri__defaultPort,2694,_Uri__toWindowsFilePath,2695,_Uri__checkNonWindowsPathReservedCharacters,2696,_Uri__checkNonWindowsPathReservedCharacters_closure,2697,_Uri__checkWindowsDriveLetter,2698,_Uri__checkWindowsPathReservedCharacters,2699,String_String$fromCharCode,2700,_Uri__removeDotSegments,2701,_Uri__makePort,2702,_Uri__normalizeRelativePath,2703,_Uri,420,_Uri__mayContainDotSegments,2704,_Uri__escapeScheme,2705,_Uri__isAlphabeticCharacter,2706,_Uri__makeScheme,2707,_Uri__fail,2708,_Uri__makeUserInfo,2709,_Uri__makeHost,2710,_Uri__Uri$notSimple_closure,2711,_Uri__makePath,2712,_Uri__makeQuery,2713,_Uri__makeFragment,2714,_Uri__normalizeOrSubstring,2715,_Uri__normalize,2716,_Uri__normalizeEscape,2717,_Uri__escapeChar,2718,hexDigitValue,1,_Uri__makePath_closure,2719,_Uri__normalizePath,2720,_Uri__uriEncode,2721,Codec,2722,_Utf8Encoder,2723,_checkValidRange,125,diagnoseRangeError,39,_Uri__checkZoneID,2724,_Uri__normalizeZoneID,2725,Uri_parseIPv6Address,2726,_Uri__normalizeRegName,2727,Uri_parseIPv6Address_error,2728,Uri_parseIPv6Address_parseHex,2729,Uri__parseIPv4Address,2730,Uri__parseIPv4Address_error,2731,_Uri__canonicalizeScheme,2732,_createTables,464,_createTables_closure,2733,_createTables_build,2734,_createTables_setChars,2735,_createTables_setRange,2736,_DataUri,2737,UriData,2738,Base64Codec__checkPadding,2739,_ensureNativeList,122,NativeInt8List__create1,2740,Style__getPlatformStyle,2741,_Uri__Uri,2415,PosixStyle,2364,Frame_Frame$parseFriendly_closure,2742,Frame__catchFormatException,2743,UriData__writeUri,2744,UriData__uriEncodeBytes,2745,Frame,2746,WindowsStyle_absolutePathToUri_closure,2747,Context_Context,2415,UriData__validateMimeType,2748,JSString__skipLeadingWhitespace,2749,JSString__skipTrailingWhitespace,2750,JSString__isWhitespace,2751,Trace$parseV8,2752,Trace$parseJSCore,2753,Trace$parseFirefox,2754,Trace__parseVM,2755,Trace__parseVM_closure,2756,Frame_Frame$parseVM,2757,Frame_Frame$parseVM_closure,2758,ExpandIterable,2759,Chain_toTrace_closure,2760,ExpandIterator,782,Trace$parseFirefox_closure,2761,Trace$parseFirefox_closure0,2761,Frame_Frame$parseFirefox,2754,Frame_Frame$parseFirefox_closure,2762,Frame__uriOrPathToUri,2763,_Uri__Uri$file,2764,_Uri__makeWindowsFileUrl,2765,_Uri__makeFileUri,2766,Trace$parseJSCore_closure,2767,Trace$parseJSCore_closure0,2767,Frame_Frame$parseV8,2752,Frame_Frame$parseV8_closure,2768,Frame_Frame$parseV8_closure_parseLocation,2769,Trace$parseV8_closure,2770,Trace$parseV8_closure0,2770,SkipWhileIterable,2771,SkipWhileIterator,2772,stringContainsUnchecked,111,StackTrace_current,621,StackZoneSpecification_chainFor_closure,2773,_Node,2774,LazyTrace,2775,StackZoneSpecification_chainFor_closure0,2773,Trace_Trace$from,2620,Trace_Trace$from_closure,2776,LazyChain_toTrace_closure,2777,Primitives_getProperty,2778,parseJsonExtended,553,mapStackTrace,487,StackTraceFormatter_formatStackTrace_closure,2779,LazyChain_foldFrames_closure,2780,Chain_foldFrames_closure,2781,Chain_foldFrames_closure0,2781,IterableElementError_tooMany,2782,LazyTrace_foldFrames_closure,2783,Trace_foldFrames_closure,2784,ReversedListIterable,2785,Trace_foldFrames_closure0,2784,mapStackTrace_closure,2786,mapStackTrace_closure0,2786,mapStackTrace_closure1,2786,_prettifyMember,489,_prettifyMember_closure,2787,_prettifyMember_closure0,2787,stringReplaceAllFuncUnchecked,118,_stringIdentity,117,MappingBundle$fromJson,2788,parseJson,554,ArgumentError$notNull,2789,SourceLocation$,2415,SourceMapSpan,1872,findLineStart,605,countCodeUnits,603,Highlighter__lastLineLength,2790,SourceSpanWithContext$,2415,Highlighter__normalizeNewlines,2791,Highlighter__normalizeTrailingNewline,2792,Highlighter__normalizeEndOfLine,2793,Highlighter,1957,_glyphs,2794,Highlighter__writeSidebar_closure,2795,Highlighter__writeLastLine_closure,2796,Highlighter__writeLastLine_closure0,2796,Highlighter__writeLastLine_closure1,2796,Highlighter__writeIntermediateLines_closure,2797,Highlighter__writeFirstLine_closure,2798,Highlighter__writeFirstLine_closure0,2798,Highlighter__writeFirstLine_closure1,2798,Highlighter__writeFirstLine_closure2,2798,SourceSpanWithContext,560,RangeError$,2415,SourceLocation,523,SingleMapping__findColumn_closure,2799,binarySearch,504,SingleMapping__findLine_closure,2800,JsLinkedHashMap_values_closure,863,MultiSectionMapping$fromJson,2788,SingleMapping$fromJson,2788,SingleMapping,2801,SourceFile,2802,_MappingTokenizer,2803,TargetLineEntry,2804,decodeVlq,534,TargetEntry,2805,SingleMapping$fromJson_closure,2806,pow,471,closure,2807,MultiSectionMapping,2808,MappingBundle,2809,_parseJson,364,_convertJsonToDartLazy,365,_JsonMap,2810,_JsonMapKeyIterable,2811,RemoteListener__sendLoadException,2812,StreamQueue,2813,QueueList$,2415,ListQueue$,2415,_CompleterStream,2814,_RestRequest,2815,StreamCompleter,2816,RemoteListener_start____closure,2817,_asBoolNullable,169,Metadata$deserialize,2818,LinkedHashSet_LinkedHashSet$from,2620,Declarer$,2415,RemoteListener__deserializeSet,2819,Runtime_Runtime$deserialize,2818,_asStringNullable,180,OperatingSystem_find,2820,SuitePlatform$,2415,RemoteListener_start____closure0,2817,Suite,2821,Suite__filterGroup,2822,_asyncStartSync,266,_asyncAwait,267,_asyncReturn,268,_asyncRethrow,269,_wrapJsFunctionForAsync,271,_makeAsyncAwaitCompleter,263,Symbol,2823,_AddStreamState_makeErrorHandler,2824,_AddStreamState_makeErrorHandler_closure,2825,_ListQueueIterator,363,ListQueue,362,QueueList,607,Result,2826,_wrapJsFunctionForAsync_closure,2827,_StreamIterator,2828,_awaitOnObject,270,_awaitOnObject_closure,2829,_awaitOnObject_closure0,2829,_AsyncAwaitCompleter,2830,RemoteListener_start_____closure,2831,Invoker_guard,2832,Invoker_guard_closure,2833,Invoker_guard__closure,2834,RemoteListener,2835,RemoteListener__serializeGroup_closure,2836,Group,490,RemoteListener__serializeTest_closure,2837,VirtualChannel,2838,_EmptyStream,2839,NullStreamSink,2840,_MultiChannel_virtualChannel_closure,2071,_MultiChannel_virtualChannel_closure0,2071,MultiChannel,2841,_DoneStreamSubscription,949,NullStreamSink_addStream_closure,2842,_LinkedHashSet__newHashTable,2560,_LinkedHashSetCell,2843,_asIntNullable,174,RemoteListener__runLiveTest_closure,2844,_BroadcastStream,2845,RemoteListener__runLiveTest_closure0,2844,RemoteListener__runLiveTest_closure1,2844,RemoteListener__runLiveTest_closure2,2844,RemoteListener__runLiveTest_closure3,2844,RemoteListener__runLiveTest__closure,2846,Invoker,2847,LiveTestController$,2415,_BroadcastSubscription,950,State,2848,Invoker__onRun_closure,2849,_AsyncCounter,2850,Chain_capture,2851,Expando__keyCount,2852,StackZoneSpecification,2853,Expando,570,Chain_capture_closure,1968,Primitives_setProperty,2854,StackZoneSpecification__currentTrace_closure,2855,StackZoneSpecification__registerBinaryCallback_closure,2025,StackZoneSpecification__registerBinaryCallback__closure,2027,StackZoneSpecification__registerUnaryCallback_closure,2021,StackZoneSpecification__registerUnaryCallback__closure,2023,StackZoneSpecification__registerCallback_closure,2019,Invoker__onRun__closure,2856,Invoker__onRun___closure,2857,Invoker__onRun___closure0,2857,Message,2858,Invoker__onRun____closure,2859,Future_Future,2415,Future_Future_closure,2860,Timer_Timer,2415,errorsDontStopTest,525,errorsDontStopTest_closure,2861,errorsDontStopTest_closure0,2861,Invoker_waitForOutstandingCallbacks_closure,2862,Invoker_waitForOutstandingCallbacks_closure0,2862,Future_Future$sync,2863,ClosedException$,2415,ClosedException,635,Invoker_heartbeat_closure,2864,Invoker_heartbeat_message,2865,Invoker_heartbeat__closure,2866,TimeoutException,2867,Timeout,2868,Invoker__handleError_closure,2869,Invoker__handleError_closure0,2869,print,412,get$print,412,Chain_Chain$current,621,Chain_Chain$current_closure,2870,LiveTestController,524,_SyncBroadcastStreamController,2871,_LiveTest,2872,_SyncBroadcastStreamController__sendError_closure,974,_AddStreamState,1058,_SyncBroadcastStreamController__sendDone_closure,976,_SyncBroadcastStreamController__sendData_closure,972,_BroadcastStreamController,2873,Metadata_serialize_closure,2874,Metadata_serialize_closure0,2874,MapEntry,2875,_LinkedHashSetIterator$,2415,PlatformSelector,2876,Group_forPlatform_closure,2877,Group$,2415,GroupEntry,2878,Group__map_closure,2879,Group__map_closure0,2879,Metadata_forPlatform_closure,2880,Metadata_Metadata,2415,Metadata_Metadata__unresolved,2881,LinkedHashMap_LinkedHashMap$from,2620,Metadata$_,2882,Metadata_Metadata_closure,2883,Metadata_merge_closure,2884,mergeMaps,506,Metadata_merge_closure0,2884,Set,2885,mergeMaps_closure,1723,UnmodifiableMapView,2886,Metadata,493,UnmodifiableSetView,533,ConstantMap_map_closure,806,ConstantMap__throwUnmodifiable,2887,_ConstantMapKeyIterable,2888,ConstantStringMap,2889,DelegatingSet,2890,Metadata__validateTags_closure,2891,Metadata__validateTags_closure0,2891,pluralize,593,toSentence,592,LinkedHashMap_LinkedHashMap,2415,LinkedHashMap_LinkedHashMap$from_closure,2892,PlatformSelector_evaluate_closure,2893,SuitePlatform,530,OperatingSystem_find_closure,2894,OperatingSystem_find_closure0,2894,Runtime_Runtime$deserialize_closure,2895,Runtime,2896,Declarer_build_closure,2897,LocalTest,2898,Declarer__tearDownAll_closure,2899,Declarer__tearDownAll__closure,2900,Declarer__tearDownAll___closure,2901,Declarer,561,Duration$,2415,LinkedHashSet_LinkedHashSet,2415,PlatformSelector$parse,2447,Metadata__deserializeTimeout,2902,Metadata$deserialize_closure,2903,Stream_last_closure,1049,Stream_last_closure0,1049,Stream_first_closure,1047,Stream_first_closure0,1047,BooleanSelectorImpl,2904,Parser,2185,Scanner,2905,SpanScanner$,2415,AndNode,2906,IntersectionSelector,2907,OrNode,2908,ConditionalNode,2909,Evaluator,2910,SourceSpanFormatException$,2415,SourceSpanFormatException,538,Token,2911,_SpanScannerState,2912,IdentifierToken,2913,validateErrorArgs,606,StringScannerException$,2415,StringScannerException,527,_FileSpan$,2415,SourceSpanMixin,2914,_FileSpan,509,FileLocation$_,2882,FileLocation,2915,NotNode,2916,VariableNode,2917,_expandSafe,564,SpanScanner,474,_asNumNullable,177,PlatformSelector$parse_closure,2918,PlatformSelector__wrapFormatException,2919,_CompleterSink,2920,_CompleterSink__setDestinationSink_closure,2921,StreamSinkCompleter,2922,_EventRequest,2923,SubscriptionStream,1612,_CancelOnErrorSubscriptionWrapper,2924,_CancelOnErrorSubscriptionWrapper_onError_closure,2925,_CancelOnErrorSubscriptionWrapper_onError__closure,2926,StreamQueue__ensureListening_closure,1619,StreamQueue__ensureListening_closure0,1619,StreamQueue__ensureListening_closure1,1619,ErrorResult,2927,ValueResult,2928,EventSink,2929,_NextRequest,2930,Completer,469,LinkedHashSet,349,fillLiteralSet,56,_GeneratedStreamImpl,2931,Stream_Stream$fromIterable_closure,1042,_IterablePendingEvents,1041,_ZoneSpecification,320,_MultiChannel,620,_MultiChannel_closure,2067,_MultiChannel_closure0,2067,_MultiChannel_closure1,2067,_MultiChannel__closure,2069,JSStackTraceMapper_deserialize,2818,PackageRootResolver,2932,asUri,598,ensureTrailingSlash,599,JSStackTraceMapper__deserializePackageConfigMap,2933,PackageConfigResolver__normalizeMap,2934,PackageConfigResolver,2935,JSStackTraceMapper,2936,Map_castFrom,2937,CastMap,2938,CastIterable_CastIterable,2415,CastIterator,2939,EfficientLengthIterable,2940,_EfficientLengthCastIterable,2941,CastIterable,0,CastMap_forEach_closure,747,PackageConfigResolver__normalizeMap_closure,2942,mapMap,505,mapMap_closure,1721,mapMap_closure0,1721,JSStackTraceMapper__deserializePackageConfigMap_closure,2943,StreamChannelCompleter,2256,_StreamChannel,2944,main_closure0,2397,group,587,get$group,587,_declarer,584,Metadata$parse,2447,Trace_Trace$current,621,Declarer_group_closure,2945,Trace_Trace$current_closure,2946,Metadata_validatePlatformSelectors_closure,2947,PlatformSelector_validate_closure,2948,PlatformSelector_validate__closure,2949,Validator,2950,Metadata__parseOnPlatform,2951,Metadata__parseTags,2952,_globalDeclarer,2953,_declarer_closure,2954,RunnerSuiteController,2955,_AsyncBroadcastStreamController,2956,AsyncMemoizer,2957,RunnerSuite,2958,Engine$,2415,Stopwatch__frequency,2959,Primitives_initTicker,2960,Primitives_timerFrequency,2961,ExpandedReporter,2962,Stopwatch,2320,PrintSink,2963,Stream_Stream$fromFuture,2964,_declarer__closure,2965,Future_Future$error,2966,UnmodifiableListView,2967,Primitives_timerTicks,2968,UnionSet,2969,UnionSet_length_closure,1739,IterableSet,2970,UnionSet__iterable_closure,1741,ExpandedReporter__onTestStarted_closure,2971,ExpandedReporter__onTestStarted_closure0,2971,ExpandedReporter__onTestStarted_closure1,2971,indent,591,prefixLines,594,Engine_run_closure,2972,Engine_run_closure0,2972,Pool_close_closure,2973,FutureGroup,499,_ListQueueIterator$,2415,FutureGroup_add_closure,1573,FutureGroup_add_closure0,1573,Engine_run__closure,2286,LiveSuiteController$,2415,Engine_run___closure,2974,Engine_run____closure,2975,Pool__onResourceReleaseAllowed_closure,2976,Pool__runOnRelease_closure,2977,Pool__runOnRelease_closure0,2977,PoolResource,2978,LiveSuiteController_close_closure,2979,RunnerSuiteController__close_closure,2980,Engine__runSkippedTest_closure,2981,Engine__runSkippedTest_closure0,2981,Engine__runSkippedTest_closure1,2981,Engine__runLiveTest_closure,2982,Engine__runLiveTest_closure0,2982,Future_Future$microtask,2983,Engine__runLiveTest_closure1,2982,Future_Future$microtask_closure,2984,LiveSuiteController_reportLiveTest_closure,2985,QueueList__nextPowerOf2,2986,StreamGroup_add_closure,1602,StreamGroup_add_closure0,1602,StreamGroup__listenToStream_closure,2987,LiveSuiteController,595,_LiveSuite,2988,LiveSuiteController_closure,2989,LiveSuiteController_closure0,2989,Stream_Stream$fromFuture_closure,1039,Stream_Stream$fromFuture_closure0,1039,Future_wait,2990,Engine_success_closure,2991,Future_wait_handleError,2992,Future_wait_closure,984,Primitives_initTicker_closure,2993,StreamGroup,2994,UnionSetController$,2415,Pool$,2415,Engine,498,StreamGroup__onCancelBroadcast_closure,1606,StreamGroup__onListen_closure,1604,Engine_closure,2995,Engine_closure0,2995,Pool,485,UnionSetController,507,closure0,2807,_macOSDirectories,2996,SuiteConfiguration__list,2997,UnmodifiableSetView$,2415,SuiteConfiguration__map,2998,SuiteConfiguration,2999,main__closure,3000,test,586,get$test,586,Declarer_test_closure,3001,Declarer_test__closure,3002,Declarer_test___closure,3003,Declarer__runSetUps_closure,3004,Future_forEach,3005,Future_forEach_closure,3006,Future_doWhile,3007,Future_doWhile_closure,3008,method1,550,method2,551,expect,539,get$expect,539,_expect,540,wrapMatcher,609,_expect_closure,3009,_expect_closure0,3009,fail,544,StringDescription,3010,formatFailure,545,Matcher,3011,prettyPrint,546,prettyPrint__prettyPrint,3012,prettyPrint__prettyPrint_pp,3013,_typeName,622,prettyPrint__prettyPrint_closure,3014,prettyPrint__prettyPrint_closure0,3014,prettyPrint__prettyPrint_closure1,3014,escape,612,escape_closure,3015,_getHexLiteral,613,Runes,3016,_combineSurrogatePair,413,RuneIterator,3017,_Predicate,3018,wrapMatcher_closure,3019,_StringEqualsMatcher,3020,_DeepMatcher,3021,JsLinkedHashMap_addAll_closure,865,_DeepMatcher__compareSets_closure,3022,TypeMatcher,3023,FeatureMatcher,3024,_StringEqualsMatcher__writeTrailing,3025,_StringEqualsMatcher__writeLeading,3026,x,3027,_Utils_objectAssign,3028,JS_CONST,3029,Interceptor,3030,JSBool,3031,JSNull,3032,JSObject,3033,JavaScriptObject,3034,PlainJavaScriptObject,3035,UnknownJavaScriptObject,3036,Function,3037,JavaScriptFunction,3038,JSUnmodifiableArray,3039,JSNumber,3040,JSInt,3041,JSDouble,3042,Pattern,3043,JSString,3044,_CastIterableBase,3045,EmptyIterator,3046,FixedLengthListMixin,3047,UnmodifiableListBase,3048,ConstantMap,3049,Instantiation,815,TypeErrorDecoder_noSuchMethodPattern,3050,TypeErrorDecoder_notClosurePattern,3051,TypeErrorDecoder_nullCallPattern,3052,TypeErrorDecoder_nullLiteralCallPattern,3053,TypeErrorDecoder_undefinedCallPattern,3054,TypeErrorDecoder_undefinedLiteralCallPattern,3055,TypeErrorDecoder_nullPropertyPattern,3056,TypeErrorDecoder_nullLiteralPropertyPattern,3057,TypeErrorDecoder_undefinedPropertyPattern,3058,TypeErrorDecoder_undefinedLiteralPropertyPattern,3059,NoSuchMethodError,3060,StackTrace,3061,TearOffClosure,3062,RegExp,382,RegExpMatch,3063,Match,3064,NativeByteBuffer,3065,ByteBuffer,3066,NativeTypedData,3067,NativeByteData,3068,NativeTypedArray,3069,NativeTypedArrayOfDouble,3070,NativeTypedArrayOfInt,3071,NativeFloat32List,3072,NativeFloat64List,3073,NativeInt16List,3074,NativeInt32List,3075,NativeInt8List,3076,NativeUint16List,3077,Uint32List,3078,NativeUint32List,3079,NativeUint8ClampedList,3080,NativeUint8List,418,Uint8List,3081,Type,3082,_Error,3083,Timer,319,Sink,3084,Exception,58,_Completer,3085,StreamTransformer,3086,StreamTransformerBase,3087,_StreamController,3088,_SyncStreamControllerDispatch,3089,_AsyncStreamControllerDispatch,3090,_StreamImpl,3091,_DelayedEvent,3092,_DelayedDone,3093,Error,3094,ZoneSpecification,3095,ZoneDelegate,3096,Zone,3097,_Zone,3098,_RootZone__rootMap,3099,_RootZone,3100,IterableBase,3101,ListBase,3102,MapBase,3103,_UnmodifiableMapMixin,3104,MapView,3105,Queue,3106,SetMixin,3107,SetBase,3108,_SetBase,3109,AsciiCodec,3110,_UnicodeSubsetEncoder,3111,AsciiEncoder,3112,Base64Codec,3113,Base64Encoder,3114,_FusedCodec,3115,Converter,3116,Encoding,3117,JsonCodec,3118,JsonDecoder,3119,Utf8Codec,3120,Utf8Encoder,3121,Utf8Decoder__decoder,3122,OutOfMemoryError,3123,StringSink,3124,Uri,3125,_Uri__isWindowsCached,3126,_Uri__needsNoEncoding,3127,AbortPaymentEvent,3128,AnimationEvent,3129,AnimationPlaybackEvent,3130,ApplicationCacheErrorEvent,3131,BackgroundFetchClickEvent,3132,BackgroundFetchEvent,3133,BackgroundFetchFailEvent,3134,BackgroundFetchedEvent,3135,BeforeInstallPromptEvent,3136,BeforeUnloadEvent,3137,Blob,3138,BlobEvent,3139,CanMakePaymentEvent,3140,ClipboardEvent,3141,CloseEvent,3142,CompositionEvent,3143,CustomEvent,3144,DeviceMotionEvent,3145,DeviceOrientationEvent,3146,DomError,3147,DomException,3148,ErrorEvent,3149,Event,3150,EventTarget,3151,ExtendableEvent,3152,ExtendableMessageEvent,3153,FetchEvent,3154,File,3155,FocusEvent,3156,FontFaceSetLoadEvent,3157,ForeignFetchEvent,3158,GamepadEvent,3159,HashChangeEvent,3160,InstallEvent,3161,KeyboardEvent,3162,Location,3163,MediaEncryptedEvent,3164,MediaError,3165,MediaKeyMessageEvent,3166,MediaQueryListEvent,3167,MediaStreamEvent,3168,MediaStreamTrackEvent,3169,MessageEvent,3170,MessagePort,3171,MidiConnectionEvent,3172,MidiMessageEvent,3173,MouseEvent,3174,MutationEvent,3175,NavigatorUserMediaError,3176,NotificationEvent,3177,OverconstrainedError,3178,PageTransitionEvent,3179,PaymentRequestEvent,3180,PaymentRequestUpdateEvent,3181,PointerEvent,3182,PopStateEvent,3183,PositionError,3184,PresentationConnectionAvailableEvent,3185,PresentationConnectionCloseEvent,3186,ProgressEvent,3187,PromiseRejectionEvent,3188,PushEvent,3189,RtcDataChannelEvent,3190,RtcDtmfToneChangeEvent,3191,RtcPeerConnectionIceEvent,3192,RtcTrackEvent,3193,SecurityPolicyViolationEvent,3194,SensorErrorEvent,3195,SpeechRecognitionError,3196,SpeechRecognitionEvent,3197,SpeechSynthesisEvent,3198,StorageEvent,3199,SyncEvent,3200,TextEvent,3201,TouchEvent,3202,TrackEvent,3203,TransitionEvent,3204,UIEvent,3205,VRDeviceEvent,3206,VRDisplayEvent,3207,VRSessionEvent,3208,WheelEvent,3209,Window,3210,_MojoInterfaceRequestEvent,3211,_ResourceProgressEvent,3212,_USBConnectionEvent,3213,EventStreamProvider,3214,_StructuredClone,3215,_AcceptStructuredClone,3216,VersionChangeEvent,3217,ByteData,3218,Int8List,3219,Uint8ClampedList,3220,Int16List,3221,Uint16List,3222,Int32List,3223,Float32List,3224,Float64List,3225,AudioProcessingEvent,3226,OfflineAudioCompletionEvent,3227,ContextEvent,3228,SqlError,3229,DelegatingSink,3230,DelegatingStreamSubscription,3231,_StreamGroupState,3232,BooleanSelector,3233,All,3234,Node,3235,Visitor,3236,None,3237,TokenType,3238,RecursiveVisitor,3239,EmptyUnmodifiableSet,3240,UnmodifiableSetMixin,3241,_DelegatingIterableBase,3242,DelegatingIterable,3243,_IsTrue,3244,Description,3245,SyncPackageResolver,3246,_PathDirection,3247,_PathRelation,3248,InternalStyle,3249,Style,3250,Mapping,3251,_TokenKind,3252,FileSpan,3253,SourceLocationMixin,3254,SourceSpan,3255,SourceSpanBase,1948,SourceSpanException,3256,Frame__uriRegExp,3257,Frame__windowsRegExp,3258,StackZoneSpecification_disableKey,3259,StreamChannelMixin,3260,LineScannerState,3261,StringScanner,3262,AsciiGlyphSet,3263,UnicodeGlyphSet,3264,LiveTest,3265,MessageType,3266,Metadata_empty,3267,OperatingSystem,3268,Status,3269,Result0,2826,Test,3270,StackTraceMapper,3271,LiveSuite,3272,RuntimeSelection,3273,SuiteConfiguration_empty,3267,_NativeTypedArrayOfDouble_NativeTypedArray_ListMixin,3274,_NativeTypedArrayOfDouble_NativeTypedArray_ListMixin_FixedLengthListMixin,3275,_NativeTypedArrayOfInt_NativeTypedArray_ListMixin,3276,_NativeTypedArrayOfInt_NativeTypedArray_ListMixin_FixedLengthListMixin,3277,_ListBase_Object_ListMixin,3278,_SetBase_Object_SetMixin,3279,_UnmodifiableMapView_MapView__UnmodifiableMapMixin,3280,_QueueList_Object_ListMixin,3281,_UnionSet_SetBase_UnmodifiableSetMixin,3282,_UnmodifiableSetView_DelegatingSet_UnmodifiableSetMixin,3283,_IterableSet_SetMixin_UnmodifiableSetMixin,3284,main,552,getNativeInterceptor,249,isJsIndexable,11,Primitives_dateNow,3285,closureFromTearOff,66,throwCyclicInit,80,getRuntimeTypeArguments,85,computeSignature,96,defineProperty,98,findType,133,typeLiteral,153,_asDoubleNullable,171,_Universe_addRules,3286,_Universe_addErasedTypes,3287,_AsyncRun__scheduleImmediateJsOverride,3288,_AsyncRun__scheduleImmediateWithSetImmediate,3289,_AsyncRun__scheduleImmediateWithTimer,3290,Future__kTrue,3291,_startMicrotaskLoop,299,StreamIterator_StreamIterator,2415,_nullDataHandler,312,_nullErrorHandler,313,_nullDoneHandler,314,_rootRegisterCallback,327,_rootRegisterUnaryCallback,328,_rootRegisterBinaryCallback,329,_rootErrorCallback,330,_rootCreateTimer,332,_rootCreatePeriodicTimer,333,_rootPrint,335,_printToZone,336,Uri_decodeComponent,3292,_escapeString,623,main0,552,max,470,DART_CLOSURE_PROPERTY_NAME,2333,JS_INTEROP_INTERCEPTOR_TAG,2334,_AsyncRun__scheduleImmediateClosure,3293,Future__nullFuture,3294,_Base64Decoder__inverseAlphabet,3295,_hasErrorStackProperty,2352,_scannerTables,2353,_whitespaceAndSingleLineComments,2354,_multiLineCommentBody,2355,_hyphenatedIdentifier,2356,_dart2DynamicArgs,2357,_escapeRegExp,2358,windows,2359,url,2360,context,2361,get$context,2361,Style_posix,3296,Style_windows,2359,Style_url,2360,Style_platform,3297,_digits,2370,MAX_INT32,2371,MIN_INT32,2372,_specKey,2373,_vmFrame,2374,_v8Frame,2375,_v8UrlLocation,2376,_v8EvalLocation,2377,_firefoxSafariFrame,2378,_friendlyFrame,2379,_asyncBody,2380,_initialDot,2381,_terseRegExp,2385,_v8Trace,2386,_v8TraceLine,2387,_firefoxSafariTrace,2388,_friendlyTrace,2389,_universalValidVariables,2391,_currentKey,2392,_currentKey0,2392,currentOSGuess,2393,_hyphenatedIdentifier0,2356,anchoredHyphenatedIdentifier,2394,$get$DART_CLOSURE_PROPERTY_NAME,2333,$get$JS_INTEROP_INTERCEPTOR_TAG,2334,$get$TypeErrorDecoder_noSuchMethodPattern,3050,$get$TypeErrorDecoder_notClosurePattern,3051,$get$TypeErrorDecoder_nullCallPattern,3052,$get$TypeErrorDecoder_nullLiteralCallPattern,3053,$get$TypeErrorDecoder_undefinedCallPattern,3054,$get$TypeErrorDecoder_undefinedLiteralCallPattern,3055,$get$TypeErrorDecoder_nullPropertyPattern,3056,$get$TypeErrorDecoder_nullLiteralPropertyPattern,3057,$get$TypeErrorDecoder_undefinedPropertyPattern,3058,$get$TypeErrorDecoder_undefinedLiteralPropertyPattern,3059,$get$_AsyncRun__scheduleImmediateClosure,3293,$get$Future__nullFuture,3294,$get$_currentKey,2392,$get$_RootZone__rootMap,3099,$get$_currentKey0,2392,$get$_specKey,2373,$get$context,2361,$get$Style_url,2360,$get$Style_windows,2359,$get$Utf8Decoder__decoder,3122,$get$Style_platform,3297,$get$_Uri__isWindowsCached,3126,$get$_Uri__needsNoEncoding,3127,$get$_scannerTables,2353,$get$_Base64Decoder__inverseAlphabet,3295,$get$Style_posix,3296,$get$_friendlyFrame,2379,$get$_v8Trace,2386,$get$_firefoxSafariTrace,2388,$get$_friendlyTrace,2389,$get$_vmFrame,2374,$get$_asyncBody,2380,$get$_firefoxSafariFrame,2378,$get$_initialDot,2381,$get$Frame__uriRegExp,3257,$get$Frame__windowsRegExp,3258,$get$windows,2359,$get$_v8Frame,2375,$get$_v8EvalLocation,2377,$get$_v8UrlLocation,2376,$get$_v8TraceLine,2387,$get$_hasErrorStackProperty,2352,$get$_terseRegExp,2385,$get$url,2360,$get$_digits,2370,$get$MIN_INT32,2372,$get$MAX_INT32,2371,$get$StackZoneSpecification_disableKey,3259,$get$anchoredHyphenatedIdentifier,2394,$get$_hyphenatedIdentifier,2356,$get$_hyphenatedIdentifier0,2356,$get$_whitespaceAndSingleLineComments,2354,$get$_multiLineCommentBody,2355,$get$_universalValidVariables,2391,$get$SuiteConfiguration_empty,3267,$get$currentOSGuess,2393,$get$Metadata_empty,3267,$get$_escapeRegExp,2358,$get$_dart2DynamicArgs,2357,getInterceptor$,3298,getInterceptor$asx,3299,async___startMicrotaskLoop$closure,3300,async__AsyncRun__scheduleImmediateJsOverride$closure,3301,async__AsyncRun__scheduleImmediateWithSetImmediate$closure,3302,async__AsyncRun__scheduleImmediateWithTimer$closure,3303,async___nullDoneHandler$closure,3304,async___nullErrorHandler$closure,3305,async___nullDataHandler$closure,3306,getInterceptor$ax,3307,async___printToZone$closure,3308,math__max$closure,3309,getInterceptor$s,3310,core_Uri_decodeComponent$closure,3311,main_test__main$closure,3312,_js_helper_Primitives_dateNow$closure,3313,async_Future__kTrue$closure,3314,pretty_print___escapeString$closure,3315,util___getHexLiteral$closure,3316,getInterceptor$x,3317,getInterceptor$ansx,3318,getInterceptor$n,3319,async___rootHandleUncaughtError$closure,3320,async___rootRun$closure,3321,async___rootRunUnary$closure,3322,async___rootRunBinary$closure,3323,async___rootRegisterCallback$closure,3324,async___rootRegisterUnaryCallback$closure,3325,async___rootRegisterBinaryCallback$closure,3326,async___rootErrorCallback$closure,3327,async___rootScheduleMicrotask$closure,3328,async___rootCreateTimer$closure,3329,async___rootCreatePeriodicTimer$closure,3330,async___rootPrint$closure,3331,async___rootFork$closure,3332","instance":"K1,3333,$this,3334,_box_0,3335,matcher,3336,future,3337,get$future,3337,V1,3338,listener,3339,frame,3340,expectedElement,3341,getMain,3342,value,2416,location,3343,get$location,3343,channel,3344,get$channel,3344,depth,3345,controller,3346,super$StringScanner$matches,3347,beforeLoad,3348,f,3349,line,3350,get$line,3350,printZone,3351,R,3352,end,3353,get$end,3353,transform,3354,result,3355,selector,3356,handleError,3357,get$handleError,3357,body,3358,elements,3359,x,3360,suite,3361,get$suite,3361,T,3362,index,3363,predicate,610,error,2966,get$error,2966,validVariables,3364,terse,3365,super$EventTarget$addEventListener,3366,_TimerImpl$2,2415,stackTrace,3367,_BufferingStreamSubscription$4,2415,_EventStreamSubscription$4,2415,LinkedHashMapKeyIterator$2,2415,timeout,3368,DateTime$_withValue$2$isUtc,3369,_Future$zoneValue$2,2593,StreamChannelController$2$allowForeignErrors$sync,2415,GuaranteeChannel$3$allowSinkErrors,2415,message,3370,get$message,3370,_Future$immediate$1,3371,_CustomZone$3,2415,performance,3372,trace,3373,div,3374,_TimerImpl$periodic$2,2623,level,3375,span,3376,get$span,3376,_LinkedHashSetIterator$2,2415,registered,3377,Instantiation$1,2415,_MatchImplementation$2,2415,SubListIterable$3,2415,super$Iterable$where,3378,SourceSpanBase$3,2415,SourceSpanWithContext$4,2415,SourceLocation$4$column$line$sourceUrl,2415,super$JavaScriptObject$toString,3379,SingleMapping$fromJson$2$mapUrl,2788,callback,3380,SourceFile$decoded$2$url,3381,test,586,get$test,586,MultiSectionMapping$fromJson$3$mapUrl,2788,groups,3382,get$groups,3382,liveTest,3383,get$liveTest,3383,engine,3384,MappingBundle$fromJson$2$mapUrl,2788,_StreamControllerAddStreamState$4,2415,_DoneStreamSubscription$1,2415,Invoker$_$4$groups$guarded,2882,chain,3385,LiveTestController$5$groups,2415,_BroadcastSubscription$5,2415,Metadata$_$10$chainStackTraces$forTag$onPlatform$retry$skip$skipReason$tags$testOn$timeout$verboseTrace,2882,completer,3386,longest,3387,SuitePlatform$3$inGoogle$os,2415,FileLocation$_$2,2882,_FileSpan$3,2415,StringScanner$3$position$sourceUrl,2415,_box_1,3388,SubscriptionStream$1,2415,super$Iterable$skipWhile,3389,fn,3390,$call$body$Engine_run__closure,3391,oldPredicate,3392,ListQueue$1,2415,counter,3393,QueueList$1,2415,hasError,3394,_MultiChannel$1,2415,loadResource,3395,StreamChannelCompleter$0,2415,super$TypeMatcher$describe,3396,id,3397,Metadata$parse$8$chainStackTraces$onPlatform$retry$skip$tags$testOn$timeout$verboseTrace,2447,milliseconds,3398,super$TypeMatcher$matches,3347,originalSource,3399,Stopwatch$0,2415,start,2491,get$start,2491,stream,3400,get$stream,3400,ExpandedReporter$_$5$color$printPath$printPlatform,2882,_Future$immediateError$2,3401,outstandingCallbacksForBody,3402,sourceResult,3403,K,3404,serializedOnPlatform,3405,V,3406,LiveSuiteController$1,2415,StreamGroup$broadcast$0,3407,onData,3408,get$onData,3408,Engine$3$concurrency$coverage$maxSuites,2415,Pool$2$timeout,2415,UnionSetController$1$disjoint,2415,target,3409,StringDescription$1,2415,sourceMap,3410,invoker,3411,minified,3412,zone,3413,sdkRoot,3414,streamConsumer,3415,e,3416,platform,3297,s,3417,sdkLib,3418,super$_BroadcastStreamController$_addEventError,3419,column,3420,get$column,3420,cleanUp,3421,eagerError,3422,iterator,3423,get$iterator,3423,identifier,3424,port,3425,get$port,3425,action,3426,node,3427,T1,3428,T2,3429,withResource$body$Pool,3430,portSubscription,3431,serialized,3432,doneSignal,3433,arg1,3434,pos,3435,arg2,3436,dispatch,3437,getTag,3438,testOn,3439,getUnknownTag,3440,skip,3441,get$skip,3441,verboseTrace,3442,get$verboseTrace,3442,prototypeForTag,3443,chainStackTraces,3444,get$chainStackTraces,3444,argumentError,3445,super$SourceSpanMixin$$eq,3446,retry,3447,get$retry,3447,arg,3448,skipReason,3449,_convertedObjects,3450,onPlatform,3451,uri,3452,get$uri,3452,portStart,3453,skipped,3454,get$skipped,3454,textInside,3455,maxItems,3456,maxLineLength,3457,original,3458,get$original,3458,_runGroup$body$Engine,3459,host,3460,get$host,3460,_prettyPrint,3461,_runLiveTest$body$Engine,3462,indent,3463,_runSkippedTest$body$Engine,3464,computation,3465,orElse,3466,countSuccess,3467,K2,3468,$protected,3469,spec,3470,pp,3471,super$DelegatingStreamSubscription$onError,3472,object,3473,ex,3474,subscription,3475,super$DelegatingStreamSubscription$cancel,3476,bodyFunction,3477,tables,3478,data,3479,get$data,3479,_foreign,3480,set$_foreign,3480,_disabled,3481,get$_disabled,3481,test$9$onPlatform$retry$skip$solo$tags$testOn$timeout,586,_onTestStarted,3482,get$_onTestStarted,3482,newDartList$1,3483,configure$1$mapper,3484,elapsedMicroseconds,3485,get$elapsedMicroseconds,3485,_captured_argumentError_0,3486,_platform_selector$_captured_this_0,3487,_completeWithValue,3488,get$_completeWithValue,3488,_parser$_captured_this_0,3489,_isScheduled,3490,get$_isScheduled,3490,hashMapCellKey,3491,_captured_future_1,3492,_closeChannel,3493,get$_closeChannel,3493,encode$1,3494,_error,3495,get$_error,3495,_core$_start,3496,onClose,3497,get$onClose,3497,_captured_callback_1,3498,_completeError,3499,get$_completeError,3499,onData$1,3408,_captured_doneSignal_2,3500,_captured_result_2,3501,configure$3$except$mapper$only,3484,separators,3502,set$separators,3502,_async_memoizer$_completer,3503,_counterKey,3504,_captured_V1_2,3505,prettyUri,3506,get$prettyUri,3506,_captured_serializedOnPlatform_0,3507,_compareSets,3508,get$_compareSets,3508,fold$1$2,3509,getRoot,3510,get$getRoot,3510,_newSet$0,3511,_captured_stackTrace_3,3512,_isPort$1,3513,catchError$1,3514,*,3515,get$*,3515,_and$0,3516,_captured_verboseTrace_4,3517,_scanOperator$1,3518,_writeFirstLine$1,3519,_handleUncaughtError,3520,get$_handleUncaughtError,3520,set$_handleUncaughtError,3520,_failedGroup,3521,_kind,3522,isOdd,3523,get$isOdd,3523,_findLine,3524,get$_findLine,3524,_captured_V_3,3525,_currentNode,3526,set$_currentNode,3526,_onSuiteStartedController,3527,_captured_f_0,3528,_requestedResources,3529,indexOf$2,3530,_precomputed4,3531,_consumeValue$0,3532,replaceAll$2,3533,_completer,3534,tags,3535,_captured_sdkRoot_3,3536,_previous,3537,needsSeparatorPattern,3538,_run,3539,get$_run,3539,set$_run,3539,replace$1$path,3540,_collection$_add,3541,get$_collection$_add,3541,_shlPositive$1,3542,_ensureController,3543,get$_ensureController,3543,_location,3544,get$_location,3544,_mayAddListener,3545,get$_mayAddListener,3545,_captured_terse_2,3546,_preGrow,3547,get$_preGrow,3547,evaluate$1,3548,_base,3549,_isWithinOrEqualsFast,3550,get$_isWithinOrEqualsFast,3550,_modified$0,3551,shouldBeDone,3552,get$shouldBeDone,3552,isBlink,3553,_currentCodePoint,3554,_addResult,3555,get$_addResult,3555,_source_map_stack_trace$_box_0,3556,typedMatches$2,3557,moveNext$0,3558,_execAnchored$2,3559,duration,3560,_onSinkDisconnected$0,3561,isCompleted,3562,get$isCompleted,3562,query,3563,get$query,3563,visitVariable$1,3564,bindCallback,3565,get$bindCallback,3565,_currentTrace,3566,get$_currentTrace,3566,sourceRoot,3567,take,3568,get$take,3568,_progressLine$2$suffix,3569,listenerHasError,3570,liveTests,3571,get$liveTests,3571,createPeriodicTimer,3572,_live_suite_controller$_onCloseCompleter,3573,_remote_listener$_captured_controller_0,3574,_onCancel$0,3575,pathsEqual,3576,get$pathsEqual,3576,distance,3577,get$distance,3577,_core$_position,3578,asStream$0,3579,abs$0,3580,verticalLine,1935,get$verticalLine,1935,listenerValueOrError,3581,_decrementPauseCount$0,3582,_html_common$_captured_this_1,3583,hasTrailingSeparator,3584,get$hasTrailingSeparator,3584,_stack_trace_formatter$_captured_this_0,3585,_declarer$_name,3586,_stack_zone_specification$_registerBinaryCallback$4,3587,_tail,3588,asUint8List$2,3589,isScaffoldAll,3590,_captured_test_1,3591,isWithin$2,3592,_platform_selector$_captured_validVariables_0,3593,_functions$_box_0,3594,_passed,3595,addTearDown$1,3596,_iterator,3597,hashMapCellValue,3598,_captured_K1_1,3599,lastSpan,3600,get$lastSpan,3600,_environment,3601,registerCallback$1$1,3602,handleUncaughtError$3,3603,_stack_zone_specification$_captured_this_1,3604,allMatches$2,3605,_position,3606,_expr,3607,_data,3608,_suiteChannel,3609,_captured_suite_1,3610,onListen,3611,_recursiveMatch$4,3612,_writeSidebar$2$end$line,3613,_onCancelBroadcast$0,3614,__internal$_iterable,3615,_buffer,3616,_flush$0,3617,_captured_identifier_0,3618,_invoker$_print$1,3619,handleUncaughtError,3603,get$handleUncaughtError,3603,scan,3620,get$scan,3620,onCancel,3621,_schedule$0,3622,_metadata,3623,_colorize$1,3624,_captured_sdkRoot_2,3625,_target,3626,_multiline,3627,_paddingBeforeSidebar,3628,_startIndex,3629,get$_startIndex,3629,_specializedTestResource,3630,_isInt32$1,3631,_contains,3632,get$_contains,3632,_handleError$3,3633,_modified,3551,get$_modified,3551,_runPool,3634,_setPendingComplete$0,3635,_simpleExpression$0,3636,_rootRunUnary$5,3637,_cloneResult$1,3638,_trimVMChain,3639,get$_trimVMChain,3639,_live_test_controller$_run,3640,get$_live_test_controller$_run,3640,_collection$_first,3641,_serializeTimeout,3642,get$_serializeTimeout,3642,relative$1,3643,_collectTraces,3644,_span_exception$_message,3645,_onRun,3646,join,3647,get$join,3647,_stack_zone_specification$_errorCallback$5,3648,_stack_zone_specification$_registerUnaryCallback$4,3649,_closeMemo,3650,change$4$onPlatform$skip$skipReason$timeout,3651,addAll$1,3652,_isPaused,3653,get$_isPaused,3653,previous,3654,_async$_addError$2,3655,_captured_minified_4,3656,_queryStart,3657,_captured_eagerError_4,3658,_captured_T_2,3659,join$8,3647,whenComplete$1,3660,position,3661,get$position,3661,set$position,3661,_newLinkedCell$2,3662,asCurrent$1$1,3663,addDescriptionOf$1,3664,_captured_orElse_1,3665,_captured_subscription_0,3666,_count,3667,_isPort,3513,get$_isPort,3513,_eval,3668,get$_eval,3668,_addEventError,3669,get$_addEventError,3669,_optionalPositional,3670,encode,3494,get$encode,3494,_writeToList$1,3671,getRoot$1,3510,_hasPending,3672,get$_hasPending,3672,_test,3673,_runner_suite$_captured_this_0,3674,_captured_zone_0,3675,_invoker$_controller,3676,setRange$4,3677,write$1,3678,_captured_maxItems_0,3679,_isClosed,3680,_closeInnerChannel$0,3681,_closable,3682,get$_closable,3682,update,3683,get$update,3683,_newSet,3511,get$_newSet,3511,_post_message_channel$_captured_controller_0,3684,_collection$_current,3685,set$_collection$_current,3685,_thenAwait$1$2,3686,_upgrade$0,3687,_fetch,3688,get$_fetch,3688,isNewSegment,3689,where$1,3378,_semantics,3690,internalFindBucketIndex,3691,get$internalFindBucketIndex,3691,_stack_zone_specification$_registerCallback$4,3692,_cachedLine,3693,_live_suite_controller$_controller,3694,_cancel,3695,get$_cancel,3695,isPassing,3696,get$isPassing,3696,_lineStart,3697,_noColor,3698,_forEachListener$1,3699,_isDebugging,3700,fillRange$3,3701,_second,3702,removeTrailingSeparators,3703,get$removeTrailingSeparators,3703,_errorName,3704,get$_errorName,3704,_union_set_controller$_set,3705,set$_union_set_controller$_set,3705,visitAnd$1,3706,_pool$_closeMemo,3707,_chainFuture,3708,get$_chainFuture,3708,declare$1,3709,needsSeparator$1,3710,second,3711,get$second,3711,_isCanceled,3712,get$_isCanceled,3712,handleNext$1,3713,_disjoint,3714,_liveTest,3715,_ensurePendingEvents$0,3716,failed,3717,get$failed,3717,_parse$1,3718,_lastMatch,3719,replaceRange$3,3720,_carry,3721,expand$1$1,3722,_stack_zone_specification$_captured_this_0,3723,isAbsolute,3724,get$isAbsolute,3724,peek,3725,get$peek,3725,_captured_object_1,3726,_rootRegisterCallback$4,3727,_doneCompleter,3728,isValue,3729,get$isValue,3729,distance$1,3577,_defaultSplit$1,3730,_execGlobal$2,3731,_simpleExpression,3636,get$_simpleExpression,3636,_onResourceReleaseAllowed$1,3732,topLeftCorner,1932,get$topLeftCorner,1932,_shrBothPositive$1,3733,_captured_longest_0,3734,_stack_zone_specification$_registerCallback,3692,get$_stack_zone_specification$_registerCallback,3692,_captured_error_0,3735,_remove$1,3736,_string,3737,padRight$1,3738,_async$_iterator,3739,set$_async$_iterator,3739,success,3740,get$success,3740,_stack_zone_specification$_captured_stackTrace_2,3741,_pendingIds,3742,_toNonSimple,3743,get$_toNonSimple,3743,_captured_spec_6,3744,readChar$0,3745,scaleFactor,3746,__js_helper$_string,3747,_stream_group$_controller,3748,set$_stream_group$_controller,3748,_serializeGroup,3749,get$_serializeGroup,3749,microsecond,3750,get$microsecond,3750,_checkNotBuilt,3751,get$_checkNotBuilt,3751,_computeKeys$0,3752,binaryOnError,3753,_or$0,3754,_captured_computation_1,3755,_execAnchored,3559,get$_execAnchored,3559,_findBucketIndex,3756,get$_findBucketIndex,3756,release,3757,get$release,3757,_runner_suite$_close$0,3758,union,3759,get$union,3759,_iterable,3760,_setRangeFast$4,3761,_captured_countSuccess_2,3762,_map,3763,internalSet$2,3764,_checkModification$1,3765,single,3766,get$single,3766,_captured_K_2,3767,joinAll$1,3768,configure,3484,get$configure,3484,_isEmpty,3769,get$_isEmpty,3769,load,3770,get$load,3770,pipe,3771,get$pipe,3771,identicalInJs$2,3772,_asyncCompleteError,3773,get$_asyncCompleteError,3773,_lazy_trace$_trace,3774,get$_lazy_trace$_trace,3774,hashCode,3775,get$hashCode,3775,_pool,3776,onError$1,3472,decrement$0,3777,registerUnaryCallback,3778,get$registerUnaryCallback,3778,_maxAllocatedResources,3779,isComplete,3780,get$isComplete,3780,indexable,3781,hasTokens,3782,get$hasTokens,3782,_html$_onData,3783,set$_html$_onData,3783,__js_helper$_strings,3784,pathSegments,3785,get$pathSegments,3785,_green,3786,_captured_registered_1,3787,describeTypedMismatch$4,3788,_expected,3789,parse,2447,get$parse,2447,whenFalse,3790,decode$2$reviver,3791,_captured_f_1,3792,any$1,3793,convert,3794,get$convert,3794,[]=,3795,get$[]=,3795,_future_group$_completer,3796,_add$1,3797,_fetch$1,3688,matchTypeError$1,3798,_last,3799,unclosable,3800,get$unclosable,3800,replace,3540,get$replace,3540,containsKey$1,3801,_runGroup$3,3802,_queue_list$_grow$0,3803,_captured_predicate_0,3804,minute,3805,get$minute,3805,_parser$_length,3806,_setUpAllTrace,3807,codeUnitAt,3808,get$codeUnitAt,3808,modifiedObject,3809,_captured_completer_0,3810,newJsObject$0,3811,active,3812,get$active,3812,_lastProgressSuffix,3813,_captured_index_1,3814,padRight,3738,get$padRight,3738,_dedupIterable,3815,get$_dedupIterable,3815,_eval$1,3668,_live_suite_controller$_captured_this_0,3816,endsWith,3817,get$endsWith,3817,_captured_streamConsumer_0,3818,removeLast$0,3819,urls,3820,_captured_hasError_3,3821,_remote_listener$_captured_this_1,3822,_varData,3823,_name,3824,_coverage,3825,_endIndex,3826,get$_endIndex,3826,codeUnitsEqual,3827,get$codeUnitsEqual,3827,_captured_s_2,3828,toTrace,3829,get$toTrace,3829,_segmentError$2,3830,_closeGroup,3831,bindUnaryCallback,3832,get$bindUnaryCallback,3832,_collection$_length,3833,_runner_suite$_controller,3834,_js_util$_captured_T_1,3835,_delegationTarget,3836,storedCallback,3837,_solo,3838,get$_solo,3838,round$0,3839,_bind$1,3840,errorCallback$2,3841,_captured_V1_3,3842,_allowMalformed,3843,lastIndexOf,3844,get$lastIndexOf,3844,_expanded$_onError,3845,get$_expanded$_onError,3845,_setUpAll,3846,get$_setUpAll,3846,_core_matchers$_description,3847,_callback,3848,_skip,3849,dart2jsArgs,3850,cancel,3476,get$cancel,3476,skipWhile$1,3389,group$1,587,_subscription_stream$_captured_error_1,3851,_resultOrListeners,3852,relativeRootPattern,3853,_onError,3854,get$_onError,3854,_createController$0,3855,_collection$_previous,3856,_setError$2,3857,_isNearCachedLine,3858,get$_isNearCachedLine,3858,convert$3,3794,_setBase,3859,get$_setBase,3859,_compareIterables$5,3860,add$1,3861,bindUnaryCallback$2$1,3832,_listenToStream,3862,get$_listenToStream,3862,_html_common$_box_0,3863,visitNot$1,3864,upEnd,1916,get$upEnd,1916,complete,3865,get$complete,3865,cast,3866,get$cast,3866,_skippedGroup,3867,_type_matcher$_name,3868,lastIndexOf$1,3844,_errorExplanation,3869,get$_errorExplanation,3869,close$0,3870,highlight$1$color,3871,_onCancelBroadcast,3614,get$_onCancelBroadcast,3614,_mappings,3872,putIfAbsent,3873,get$putIfAbsent,3873,_captured_performance_0,3874,_completeError$2,3499,isFinite,3875,get$isFinite,3875,runSkipped,3876,get$runSkipped,3876,isUnicode,3877,get$isUnicode,3877,_upgrade,3687,get$_upgrade,3687,span$2,3376,addError$1,3878,toChain$0,3879,__js_helper$_map,3880,_captured_this_1,3881,setUpAll,3882,_noRetry,3883,spanFor$4$files$uri,3884,_errorCallback,3885,get$_errorCallback,3885,set$_errorCallback,3885,_captured_onData_0,3886,count,3887,whenComplete,3660,get$whenComplete,3660,_isComplete,3888,get$_isComplete,3888,_captured_span_2,3889,_captured_groups_2,3890,setAll$2,3891,_onValue,3892,get$_onValue,3892,setDestinationSink$1,3893,_getNext$0,3894,packageConfigMap,3895,get$packageConfigMap,3895,_captured_tables_0,3896,writeln$1,3897,registerUnaryCallback$2$2,3778,_printPlatform,3898,skip$1,3441,_trace,3899,_mayResumeInput,3900,get$_mayResumeInput,3900,invalidValue,3901,_recordPause,3902,get$_recordPause,3902,_captured_T1_3,3903,_span_scanner$_scanner,3904,_bold,3905,_file$_start,3906,noMoreLiveTests$0,3907,change,3651,get$change,3651,_unlisten$0,3908,_engine$_runCalled,3909,_string_scanner$_position,3910,removeFragment$0,3911,_released,3912,_setValue$1,3913,firstMatch$1,3914,_captured_originalSource_0,3915,union$1,3759,liveSuite,3916,get$liveSuite,3916,_next,3917,_internal,3918,_isFile,3919,get$_isFile,3919,isLoadSuite,3920,get$isLoadSuite,3920,where,3378,get$where,3378,_streamController,3921,set$_streamController,3921,unclosable$1$1,3800,_addEventListener,3922,get$_addEventListener,3922,_endOrLength,3923,resolveUri$1,3924,__js_helper$_addHashTableEntry,3925,get$__js_helper$_addHashTableEntry,3925,whenTrue,3926,serialize$0,2631,highlight$0,3871,isEmpty,3927,get$isEmpty,3927,_multiLineComment,3928,get$_multiLineComment,3928,_iterable_set$_base,3929,_checkState,3930,get$_checkState,3930,_captured_future_3,3931,addAll$4,3652,_thenAwait,3686,get$_thenAwait,3686,_inCallback,3932,get$_inCallback,3932,_expanded$_captured_this_0,3933,files,3934,splitMapJoin,3935,get$splitMapJoin,3935,visitNot,3864,get$visitNot,3864,toFilePath$0,3936,internalRemove$1,3937,toolString,3938,get$toolString,3938,toString,3379,get$toString,3379,_failClosed$0,3939,_toListFixed$0,3940,glyphOrAscii,1931,get$glyphOrAscii,1931,_captured_platform_0,3941,_lazy_trace$_captured_this_0,3942,remaining,3943,_captured_portStart_1,3944,_conditional,3945,get$_conditional,3945,_equals_matcher$_match,3946,get$_equals_matcher$_match,3946,_pathSegments,3947,set$_pathSegments,3947,firstWhere,3948,get$firstWhere,3948,floor,3949,get$floor,3949,padLeft$2,3950,_captured_R_5,3951,_trace$_captured_longest_0,3952,onMessage,3953,get$onMessage,3953,_addedSuites,3954,_captured_host_0,3955,_captured_skipped_1,3956,_expanded$_color,3957,_stack_zone_specification$_run,3958,get$_stack_zone_specification$_run,3958,change$1$onPlatform,3651,_mergePaths$2,3959,getText$2,3960,_declarer$_trace,3961,_captured_handleError_1,3962,_isHttp,3963,get$_isHttp,3963,_lastProgressPassed,3964,month,3965,get$month,3965,apply$1,3966,_captured_outstandingCallbacksForBody_1,3967,_createController,3855,get$_createController,3855,_badEventState$0,3968,_captured_validVariables_0,3969,canonicalizePart$1,3970,forEach,3005,get$forEach,3005,toRadixString$1,3971,message$2$color,3370,_asyncCompleteError$2,3773,join$2,3647,update$2,3683,_collection$_cell,3972,_simpleMerge,3973,get$_simpleMerge,3973,_runLiveTest$2,3974,_addRequest$1,3975,_removeHashTableEntry,3976,get$_removeHashTableEntry,3976,_onResourceReleaseAllowed,3732,get$_onResourceReleaseAllowed,3732,validate$1,3977,_queue_list$_table,3978,set$_queue_list$_table,3978,_future_group$_pending,3979,matchesErrorTest,3980,get$matchesErrorTest,3980,_removeListener,3981,get$_removeListener,3981,hasErrorTest,3982,get$hasErrorTest,3982,_expanded$_onDone$1,3983,_onPause$0,3984,packageConfigUri,3985,_lastProgressSkipped,3986,_engine$_box_0,3987,_check,3988,isRelative$1,3989,_captured_selector_0,3990,_retry,3991,_input,3992,addEventListener$3,3366,nextIteration,3993,_timeString$1,3994,pointSpan$0,3995,variableName,3996,_schemeCache,3997,insert,3998,get$insert,3998,day,3999,get$day,3999,_lazy_trace$_captured_predicate_1,4000,putIntoMap$3,4001,_live_test_controller$_state,4002,lines,4003,get$lines,4003,_recordCancel$1,4004,_sendError$2,4005,_newHashTable,4006,get$_newHashTable,4006,removeFirst$0,4007,_runOnRelease$1,4008,_findColumn,4009,get$_findColumn,4009,_removeListeners$0,4010,trim,4011,get$trim,4011,_stream_queue$_close$0,4012,_queue_list$_head,4013,indexOf$1,3530,__js_helper$_index,4014,isDartVM,4015,_stream_sink_completer$_sink,4016,get$_stream_sink_completer$_sink,4016,_flush,3617,get$_flush,3617,virtualChannel$0,4017,listeners,4018,_host,4019,_stream_queue$_subscription,4020,set$_stream_queue$_subscription,4020,_addRequest,3975,get$_addRequest,3975,bindCallbackGuarded,4021,get$bindCallbackGuarded,4021,handleError$1,3357,containsSeparator$1,4022,inMinutes,4023,get$inMinutes,4023,endColumn,4024,_streamCompleter,4025,right,4026,setRange$3,3677,hasAbsolutePath,4027,get$hasAbsolutePath,4027,_mergePaths,3959,get$_mergePaths,3959,_re,4028,varData,4029,expand$1,3722,onComplete,4030,get$onComplete,4030,_get,4031,get$_get,4031,toUri,4032,get$toUri,4032,_fragmentStart,4033,_outgoingConnections,4034,hasPort,4035,get$hasPort,4035,_collection$_modified,4036,get$_collection$_modified,4036,runtime,4037,getLine,4038,get$getLine,4038,_countTabs$1,4039,_nativeAnchoredRegExp,4040,_waitsForCancel,4041,get$_waitsForCancel,4041,file,2764,run$1$1,4042,_captured_ex_0,4043,errorZone,4044,get$errorZone,4044,foundResult,4045,relative$2$from,3643,_onSuiteAddedController,4046,_captured_future_2,4047,run$0,4042,virtualChannel,4017,get$virtualChannel,4017,_setSourceStream$1,4048,_incomingConnections,4049,_setUpAlls,4050,getColumn$1,4051,_element,4052,_errorTest,4053,get$_errorTest,4053,_argumentsExpr,4054,schedule$1,4055,_collection$_captured_result_0,4056,_sinkCompleter,4057,_eventScheduled,4058,get$_eventScheduled,4058,_writeTrailingLines,4059,get$_writeTrailingLines,4059,removeTrailingSeparators$0,3703,rootLength$2$withDrive,4060,_live_suite_controller$_captured_liveTest_1,4061,normalize$1,4062,_closableKey,4063,_live_test_controller$_controller,4064,isSync,4065,_parent,4066,source,4067,scheduleMicrotask,302,get$scheduleMicrotask,302,_engine$_runLiveTest$3$countSuccess,4068,_isPendingComplete,4069,get$_isPendingComplete,4069,message$1,3370,_captured_line_0,4070,copyList$2,4071,_writeSurrogate$2,4072,_serializeTest,4073,get$_serializeTest,4073,_fillBuffer$3,4074,toJson$0,4075,_writeLastLine,4076,get$_writeLastLine,4076,_schedule,3622,get$_schedule,3622,addOutstandingCallback,4077,get$addOutstandingCallback,4077,_codeUnitAt$1,4078,chainFor$1,4079,_serializeTimeout$1,3642,~/,4080,get$~/,4080,print$1,412,_addHashTableEntry$2,4081,$package,4082,get$$package,4082,_stack_zone_specification$_registerBinaryCallback,3587,get$_stack_zone_specification$_registerBinaryCallback,3587,isHeadless,4083,completeError,4084,get$completeError,4084,verboseChain,4085,containsSeparator,4022,get$containsSeparator,4022,_addHashTableEntry,4081,get$_addHashTableEntry,4081,_declarer$_parent,4086,_stream_group$_subscriptions,4087,listen$4$cancelOnError$onDone$onError,4088,describeMismatch$4,4089,closed,4090,get$closed,4090,_streamQueue,4091,_runSetUps$0,4092,_captured_indent_0,4093,_checkPosition$3,4094,_prefix$1,4095,_linkStreamToController,4096,get$_linkStreamToController,4096,setSourceStream,4097,get$setSourceStream,4097,targetUrl,4098,_and,3516,get$_and,3516,peek$0,3725,__js_helper$_message,4099,inMilliseconds,4100,get$inMilliseconds,4100,_async$_previous,4101,set$_async$_previous,4101,_captured__convertedObjects_0,4102,_entries,4103,_setPendingEvents,4104,get$_setPendingEvents,4104,listen$2$onDone,4088,_captured_node_2,4105,addDescriptionOf,3664,get$addDescriptionOf,3664,__internal$_length,4106,_guardIfGuarded$1,4107,scan$1,3620,_runOnRelease,4008,get$_runOnRelease,4008,done,4108,get$done,4108,_platformVariables,4109,_isOnlyWhitespace$1,4110,isJS,4111,isEof,4112,sourceLine,4113,_runSetUps,4092,get$_runSetUps,4092,matchesErrorTest$1,3980,_f,4114,isBroadcast,4115,get$isBroadcast,4115,_captured_invoker_0,4116,_remote_listener$_box_0,4117,_conditional$0,3945,_tearDowns,4118,_close,4119,get$_close,4119,endsWith$1,3817,_nextId,4120,addAll,3652,get$addAll,3652,_captured_liveTest_0,4121,_engine$_closed,4122,_writeText,4123,get$_writeText,4123,matchAsPrefix,4124,get$matchAsPrefix,4124,_guarded,4125,_lazy_trace$_inner,4126,set$_lazy_trace$_inner,4126,_runGroup,3802,get$_runGroup,3802,__js_helper$_unlinkCell$1,4127,describe,3396,get$describe,3396,setSourceStream$1,4097,_failed,4128,_stack_zone_specification$_box_0,4129,_lazy_chain$_captured_this_0,4130,_colorize,3624,get$_colorize,3624,relativePathToUri,4131,get$relativePathToUri,4131,_isChained,4132,get$_isChained,4132,newJsMap$0,4133,_allocatedResources,4134,_color,4135,_mayAddEvent,4136,get$_mayAddEvent,4136,_group$_map$1,4137,_multi_channel$_captured_this_1,4138,_computeHashCode$1,4139,_complete$1,4140,_async$_captured_result_2,4141,_ensurePendingEvents,3716,get$_ensurePendingEvents,3716,_captured_e_1,4142,_null_stream_sink$_captured_this_0,4143,_captured_printZone_0,4144,_isAddingStream,4145,get$_isAddingStream,4145,_collection$_newLinkedCell,4146,get$_collection$_newLinkedCell,4146,_shrReceiverPositive,4147,get$_shrReceiverPositive,4147,fragment,4148,get$fragment,4148,_sendData,4149,get$_sendData,4149,_pauseCount,4150,runUnary$2$2,4151,_upgradedMap,4152,get$_upgradedMap,4152,_scanner,4153,precompiledPath,4154,_html$_target,4155,_hashCodeCache,4156,runGuarded,4157,get$runGuarded,4157,_lastSpan,4158,toList,4159,get$toList,4159,_verboseTrace,4160,_whenCompleteAction,4161,get$_whenCompleteAction,4161,relativePathToUri$1,4131,replaceAllMapped$2,4162,_as,4163,_captured_counter_3,4164,_nativeGlobalRegExp,4165,allMatches,3605,get$allMatches,3605,_soloEntries,4166,_writeTrailingLines$1,4059,addSubscription,4167,_writeSurrogate,4072,get$_writeSurrogate,4072,increment$0,4168,_captured_R_4,4169,_onResourceReleased$0,4170,_strings,4171,_handle,4172,hasListener,4173,get$hasListener,4173,_ensureDoneFuture$0,4174,_stack_zone_specification$_handleUncaughtError$5,4175,_captured_printZone_1,4176,_invokerZone,4177,_captured_transform_1,4178,evaluate,3548,get$evaluate,3548,_findBucketIndex$2,3756,pause$0,4179,_compareSets$5,3508,runUnaryGuarded$1$2,4180,spanFrom,4181,get$spanFrom,4181,fold,3509,get$fold,3509,_config,4182,_runner_suite$_onClose,4183,_zone,4184,get$_zone,4184,_stream_sink_completer$_controller,4185,set$_stream_sink_completer$_controller,4185,_captured_textInside_1,4186,pipe$1,3771,[],4187,get$[],4187,_lastProgressMessage,4188,matches$2,3347,_captured_fn_2,4189,_ensureController$0,3543,lastPendingEvent,4190,inMicroseconds,4191,get$inMicroseconds,4191,joinAll,3768,get$joinAll,3768,visitConditional$1,4192,__internal$_index,4193,_stream_sink_completer$_doneCompleter,4194,inSeconds,4195,get$inSeconds,4195,_onStateChangeController,4196,_cachedRuntimeType,4197,_captured_controller_0,4198,packageResolver,4199,_captured_eagerError_2,4200,_captured_T2_4,4201,_onClose,4202,_groups,4203,_addEventError$0,3669,convertNativeToDart_AcceptStructuredClone$2$mustCopy,2104,_duration,4204,_addHashTableEntry$3,4081,_decodedChars,4205,parents,4206,parent,4207,get$parent,4207,skipWhile,3389,get$skipWhile,3389,runGuarded$1,4157,join$1,3647,_jsObject,4208,_captured_test_0,4209,_stream_group$_state,4210,startsWith$2,4211,_set,4212,get$_set,4212,absolute$1,4213,foreign,4214,get$foreign,4214,_collection$_add$1,3541,_hasError,4215,get$_hasError,4215,merge,4216,get$merge,4216,registerUnaryCallback$2$1,3778,firstWhere$2$orElse,3948,handleValue$1,4217,resolve,4218,get$resolve,4218,_message,4219,bindCallbackGuarded$1,4021,_updateRequests,4220,get$_updateRequests,4220,_delegateCache,4221,_recordCancel,4004,get$_recordCancel,4004,hasFragment,4222,get$hasFragment,4222,traces,4223,get$traces,4223,isScheduled,4224,get$isScheduled,4224,_union_set$_iterable,4225,get$_union_set$_iterable,4225,parse$0,2447,_onCloseCompleter,4226,isNotEmpty,4227,get$isNotEmpty,4227,_test$_captured_body_0,4228,hasScheme,4229,get$hasScheme,4229,_closedBeforeDone,4230,_span_exception$_span,4231,_captured_cleanUp_1,4232,_source,4233,fuse$1$1,4234,_isNearCachedLine$1,3858,_live_suite_controller$_suite,4235,_runTearDowns,4236,get$_runTearDowns,4236,rootLength,4060,get$rootLength,4060,trim$0,4011,_captured_elements_0,4237,addStream$2$cancelOnError,4238,_precomputed3,4239,_completeError$1,3499,_checkEventAllowed,4240,get$_checkEventAllowed,4240,_captured_terse_0,4241,patterns,4242,_setEmpty$0,4243,_fragment,4244,createTimer,4245,get$createTimer,4245,variables,4246,_chainFuture$1,3708,_onDebuggingController,4247,_captured_protected_0,4248,every,4249,get$every,4249,_trace$_captured_trace_0,4250,location$1,3343,perform,4251,get$perform,4251,completeError$1,4084,_captured_bodyFunction_0,4252,_allowInvalid,4253,change$1$timeout,3651,_countTabs,4039,get$_countTabs,4039,_pool$_captured_this_0,4254,outputId,4255,_onResume$0,4256,_extraUnits,4257,toUpperCase$0,4258,__js_helper$_addHashTableEntry$3,3925,_equals_matcher$_value,4259,_controller,4260,_multi_channel$_captured_this_0,4261,_group,4262,_addStreamSubscription,4263,set$_addStreamSubscription,4263,_queue_list$_add$1,4264,forEachJsField,4265,get$forEachJsField,4265,glyphOrAscii$2,1931,_writeLastLine$1,4076,_regExp,4266,__js_helper$_nums,4267,_getTableBucket,4268,get$_getTableBucket,4268,_convert$_computeKeys,4269,get$_convert$_computeKeys,4269,_mapping,4270,millisecondsSinceEpoch,4271,get$millisecondsSinceEpoch,4271,_cell,4272,_checkNotBuilt$1,3751,connectOut$1,4273,_sets,4274,_onUnpaused,4275,get$_onUnpaused,4275,_genericClosure,4276,_mapContents,4277,_captured_indent_2,4278,_innerStreamSubscription,4279,startsWith,4211,get$startsWith,4211,context,2361,get$context,2361,substring$1,4280,matchAsPrefix$2,4124,entries,4281,_multi_channel$_inner,4282,_fillBuffer,4074,get$_fillBuffer,4074,hasRun,4283,get$hasRun,4283,forEachJsField$2,4265,_stack_zone_specification$_onError,4284,elapsedTicks,4285,get$elapsedTicks,4285,_onTestStartedGroup,4286,tearDownAll,4287,_matcher,4288,_engine,4289,_onSinkDisconnected,3561,get$_onSinkDisconnected,3561,containsKey,3801,get$containsKey,3801,_captured_future_0,4290,_captured_getTag_0,4291,error$3$length$position,2966,names,4292,internalContainsKey$1,4293,_runTearDowns$0,4236,_captured_start_2,4294,_addStreamState,4295,set$_addStreamState,4295,_extractStream,4296,get$_extractStream,4296,cancel$0,3476,setState$1,4297,substring,4280,get$substring,4280,clear,4298,get$clear,4298,errorCallback$3,3841,_stop,4299,_stream_group$_closed,4300,os,4301,hasPartialInput,4302,get$hasPartialInput,4302,_getBucket,4303,get$_getBucket,4303,_timeout,4304,parts,4305,set$parts,4305,_pathDirection,4306,get$_pathDirection,4306,describeTypedMismatch,3788,get$describeTypedMismatch,3788,findSlot$1,4307,_scheduleMicrotask,4308,get$_scheduleMicrotask,4308,set$_scheduleMicrotask,4308,_loadPool,4309,_canSendDirectly,4310,get$_canSendDirectly,4310,local,4311,get$local,4311,hour,4312,get$hour,4312,packageRoot,4313,get$packageRoot,4313,_endOfFileEmitted,4314,_captured_callback_0,4315,_captured_terse_1,4316,_future_group$_closed,4317,_convert$_value,4318,readSlot$1,4319,fork,4320,get$fork,4320,elementAt$1,4321,_runUnary,4322,get$_runUnary,4322,set$_runUnary,4322,writeAll$2,4323,_captured_callback_3,4324,_captured_arg_1,4325,_progressLine$2$color,3569,writeSlot$2,4326,_async$_next,4327,set$_async$_next,4327,toChain,3879,get$toChain,3879,_hashCode,4328,_onListen,4329,get$_onListen,4329,_captured_sourceResult_2,4330,runOnce$1,4331,_reviver,4332,_invoker$_captured_this_1,4333,toList$1$growable,4159,innerStream,4334,expect$2$name,539,_thunk,4335,_writeToList,3671,get$_writeToList,3671,_ensureListening$0,4336,_chains,4337,visitConditional,4192,get$visitConditional,4192,_captured_listener_1,4338,_failClosed,3939,get$_failClosed,3939,startColumn,4339,matchTypeError,3798,get$matchTypeError,3798,status,4340,toString$0,3379,_runLiveTest,3974,get$_runLiveTest,3974,_removeAfterFiring,4341,get$_removeAfterFiring,4341,_multi_channel$_box_0,4342,_eventType,4343,_head,4344,url,2360,resume,4345,get$resume,4345,__js_helper$_removeHashTableEntry$2,4346,_removeListeners,4010,get$_removeListeners,4010,codeUnitsEqual$2,3827,_match,4347,_isFiring,4348,get$_isFiring,4348,includeTags,4349,_pathDirection$2,4306,_stack_zone_specification$_registerBinaryCallback$3$4,3587,add,3861,get$add,3861,_current,4350,set$_current,4350,_selector2,4351,toString$1$color,3379,_rti,4352,_asyncComplete,4353,get$_asyncComplete,4353,request,4354,get$request,4354,_sendData$1,4149,_gray,4355,listen$3$onDone$onError,4088,matches,3347,get$matches,3347,_stack_zone_specification$_errorCallback,3648,get$_stack_zone_specification$_errorCallback,3648,toFilePath,3936,get$toFilePath,3936,setRange,3677,get$setRange,3677,_except,4356,set$_except,4356,_engine$_subscriptions,4357,_subscription_stream$_source,4358,set$_subscription_stream$_source,4358,_sdkRoot,4359,_recordResume$1,4360,scheme,4361,get$scheme,4361,_expectedUnits,4362,_captured_column_0,4363,convertDartToNative_PrepareForStructuredClone$1,1533,_closeGap$2,4364,_highlighter$_buffer,4365,_sink$_sink,4366,$call,3391,get$$call,3391,map$2$1,4367,_parser0$_scanner,4368,_bindCache,4369,__internal$_name,4370,_only,4371,set$_only,4371,removeEventListener$3,4372,_setTableEntry,4373,get$_setTableEntry,4373,_live_test_controller$_close$0,4374,toTrace$0,3829,_queryParameters,4375,resolveUri,3924,get$resolveUri,3924,__js_helper$_length,4376,_engine$_captured_this_1,4377,_pretty_print$_box_0,4378,addMapping$1,4379,absolute,4213,get$absolute,4213,_out,4380,_captured_R_3,4381,_async$_isClosed,4382,get$_async$_isClosed,4382,flush,4383,get$flush,4383,_captured_getMain_1,4384,_onStateChange,4385,get$_onStateChange,4385,_captured_K1_2,4386,toLowerCase$0,4387,heartbeat$0,4388,_writeFirstLine,3519,get$_writeFirstLine,3519,registerBinaryCallback$3$1,4389,_method,4390,_collection$_writeToList$1,4391,contains$1,4392,_writeSidebar$1$line,3613,removeOutstandingCallback$0,4393,_functions$_captured_value_1,4394,_prependListeners,4395,get$_prependListeners,4395,_core$_data,4396,_chain$_captured_callback_0,4397,_inner,4398,_fork,4399,get$_fork,4399,set$_fork,4399,_extractStream$0,4296,catchError,3514,get$catchError,3514,_nextIndex,4400,_captured_uri_0,4401,_maps,4402,_async$_addError,3655,get$_async$_addError,3655,_bufferIndex,4403,_red,4404,_unlinkCell,4405,get$_unlinkCell,4405,forEachObjectKey,4406,get$forEachObjectKey,4406,isRootRelative$1,4407,addStream,4238,get$addStream,4238,_restarted,4408,_captured_validVariables_1,4409,_doneFuture,4410,_original,4411,_registerCallback,4412,get$_registerCallback,4412,set$_registerCallback,4412,foldFrames$2$terse,4413,normalize$0,4062,_captured_channel_3,4414,_onMessageController,4415,separatorPattern,4416,_isFirstCharacter,4417,_errorZone,4418,contains,4392,get$contains,4392,addStreamFuture,4419,_built,4420,_requiredPositional,4421,_captured_test_2,4422,_table,4423,set$_table,4423,_deleteTableEntry$2,4424,split$1,4425,padLeft,3950,get$padLeft,3950,_group$_captured_callback_0,4426,_listen$1,4427,_parser$_mapUrl,4428,validatePlatformSelectors$1,4429,_shrBothPositive,3733,get$_shrBothPositive,3733,_async$_map,4430,get$_async$_map,4430,hasEmptyPath,4431,get$hasEmptyPath,4431,sublist,4432,get$sublist,4432,_stream,4433,_invoker$_onRun$0,4434,complete$1,3865,_subscribe,4435,get$_subscribe,4435,_captured_x_0,4436,_sourceStream,4437,set$_sourceStream,4437,_completeWithValue$1,3488,_chainStackTraces,4438,_setDestinationSink$1,4439,internalFindBucketIndex$2,3691,addTearDownAll$1,4440,_live_suite_controller$_isComplete,4441,_captured_result_0,4442,_captured_expectedElement_1,4443,getColumn,4051,get$getColumn,4051,_package_config_resolver$_uri,4444,_reverseListeners$1,4445,_collection$_last,4446,findSlot,4307,get$findSlot,4307,_captured_timeout_0,4447,walk$1,4448,_userInfo,4449,formatStackTrace$2$verbose,4450,replaceRange,3720,get$replaceRange,3720,_addResult$1,3555,remove,4451,get$remove,4451,_queue_list$_add,4264,get$_queue_list$_add,4264,_captured_listener_2,4452,__js_helper$_keys,4453,_encoder,4454,runBinary,4455,get$runBinary,4455,_cancelFuture,4456,_future_group$_captured_this_0,4457,handlesComplete,4458,get$handlesComplete,4458,_trace$_box_0,4459,_captured_pos_1,4460,sublist$2,4432,_invoker$_test,4461,get$_invoker$_test,4461,_metadata$_captured_timeout_2,4462,_guarantee_channel$_box_0,4463,cancelSchedule$0,4464,sourceNameId,4465,runtimeType,4466,get$runtimeType,4466,_collection$_modifications,4467,then,4468,get$then,4468,absolute$7,4213,_captured_maxLineLength_1,4469,_subsetMask,4470,_recordResume,4360,get$_recordResume,4360,_forEachListener,3699,get$_forEachListener,3699,testRandomizeOrderingSeed,4471,visitOr,4472,get$visitOr,4472,expect,539,get$expect,539,_lastProgressFailed,4473,internalContainsKey,4293,get$internalContainsKey,4293,splitMapJoin$2$onMatch,3935,_getTableBucket$2,4268,writeln,3897,get$writeln,3897,_convert$_first,4474,_expanded$_onError$3,3845,_removeListener$1,3981,millisecond,4475,get$millisecond,4475,_highlighter$_captured_this_1,4476,validatePlatformSelectors,4429,get$validatePlatformSelectors,4429,_preGrow$1,3547,configure$2$except$only,3484,request$0,4354,_rootRegisterUnaryCallback$4,4477,_async$_captured_f_1,4478,_remote_listener$_captured_this_0,4479,reversed,4480,get$reversed,4480,_queryParameterLists,4481,hasErrorCallback,4482,get$hasErrorCallback,4482,_scanOperator,3518,get$_scanOperator,3518,_captured_testOn_1,4483,split,4425,get$split,4425,left,4484,_listenToStream$1,3862,_live_test_controller$_isClosed,4485,get$_live_test_controller$_isClosed,4485,_codeUnitAt,4078,get$_codeUnitAt,4078,_highlighter$_captured_this_0,4486,_html$_start$0,4487,_chain,4488,get$_chain,4488,_addingStream,4489,_getTableCell$2,4490,forTarget$1,4491,_captured_minified_2,4492,connectOut,4273,get$connectOut,4273,peekChar,4493,get$peekChar,4493,_collection$_next,4494,_equals_matcher$_match$3,3946,cast$2$0,3866,build,4495,get$build,4495,_engine$_runLiveTest$2,4068,_segmentError,3830,get$_segmentError,3830,_process$1,4496,_precomputed2,4497,lastMatch,4498,get$lastMatch,4498,_description,4499,get$_description,4499,_captured_chainStackTraces_5,4500,startsWith$1,4211,_captured_printZone_5,4501,decoder,4502,get$decoder,4502,hasAuthority,4503,get$hasAuthority,4503,unaryOnError,4504,_needsNormalization$1,4505,_collection$_modified$0,4036,onResume,4506,build$0,4495,_or,3754,get$_or,3754,_printPath,4507,_tdivSlow$1,4508,withResource$1$1,3430,_writeText$1,4123,handleNext,3713,get$handleNext,3713,__js_helper$_rest,4509,_paused,4510,_tearDownAll,4511,get$_tearDownAll,4511,_captured_result_3,4512,_lazy_trace$_thunk,4513,waitForOutstandingCallbacks,4514,get$waitForOutstandingCallbacks,4514,_mayComplete,4515,get$_mayComplete,4515,_captured_T_5,4516,$function,4517,_offset,4518,_asyncComplete$1,4353,load$2$groups,3770,_captured_value_1,4519,runUnaryGuarded,4180,get$runUnaryGuarded,4180,bindUnaryCallbackGuarded$1$1,4520,_sendDone$0,4521,_outstandingCallbacks,4522,get$_outstandingCallbacks,4522,extensions,4523,_closeUnchecked,4524,get$_closeUnchecked,4524,_toListGrowable$0,4525,_captured_end_2,4526,_invoker$_captured_this_0,4527,_convert$_computeKeys$0,4269,codeUnits,4528,get$codeUnits,4528,mapStackTrace$1,487,_precomputed1,4529,_stack_zone_specification$_captured_f_1,4530,insert$2,3998,floor$0,3949,internalGet$1,4531,_names,4532,internalGet,4531,get$internalGet,4531,pattern,4533,_captured_stackTrace_1,4534,_liveSuite,4535,_collection$_newLinkedCell$1,4146,then$1$2$onError,4468,_consumeNewLine$0,4536,_live_test_controller$_close,4374,get$_live_test_controller$_close,4374,_newHashTable$0,4006,_metadata$_box_0,4537,suiteSink,4538,get$suiteSink,4538,_port,4539,_passedGroup,4540,_hostStart,4541,_isWithinOrEquals$2,4542,_unlisten,3908,get$_unlisten,3908,_expanded$_captured_liveTest_1,4543,_live_suite_controller$_closeMemo,4544,_captured_target_0,4545,_captured_host_1,4546,_uriCache,4547,_nativeAnchoredVersion,4548,get$_nativeAnchoredVersion,4548,relative,3643,get$relative,3643,_consumeWhitespace,4549,get$_consumeWhitespace,4549,_scanOr$0,4550,_tryResume,4551,get$_tryResume,4551,_runner_suite$_suite,4552,set$_runner_suite$_suite,4552,bind$1,2478,toSet,4553,get$toSet,4553,_captured_level_1,4554,sourceColumn,4555,_nextListener,4556,connectIn$2,4557,_isCaseSensitive,4558,get$_isCaseSensitive,4558,_progressLine,3569,get$_progressLine,3569,_body,4559,waitForOutstandingCallbacks$1,4514,_description$1,4499,encoder,4560,get$encoder,4560,metadata,4561,get$metadata,4561,_isInputPaused,4562,get$_isInputPaused,4562,inHours,4563,get$inHours,4563,allowRelease$1,4564,serialize,2631,get$serialize,2631,_captured_getUnknownTag_0,4565,_invoker$_completer,4566,intersection$1,4567,_ensureDoneFuture,4174,get$_ensureDoneFuture,4174,state,4568,get$state,4568,_state,4569,reportLiveTest$2$countSuccess,4570,_clearPendingComplete$0,4571,_captured_timeout_2,4572,_mapUrl,4573,_controllers,4574,forEachObjectKey$2,4406,fromUri$1,1988,_tearDownAllTrace,4575,_chain$_captured_T_1,4576,_highlighter$_box_0,4577,_multi_channel$_captured_T_2,4578,_subscriptions,4579,every$1,4249,_captured_V_2,4580,_captured_original_1,4581,formatStackTrace,4450,get$formatStackTrace,4450,_subscription_stream$_captured_this_0,4582,_newLinkedCell,3662,get$_newLinkedCell,3662,_stream_queue$_captured_this_0,4583,_runCalled,4584,_testCount,4585,onDone$1,4586,_isInitialState,4587,get$_isInitialState,4587,_stack_zone_specification$_registerUnaryCallback$2$4,3649,isEven,4588,get$isEven,4588,completeError$2,4084,_checkState$1,3930,_types,4589,get$_types,4589,_stack_zone_specification$_registerUnaryCallback,3649,get$_stack_zone_specification$_registerUnaryCallback,3649,_closeInnerChannel,3681,get$_closeInnerChannel,3681,root,4590,_writeIntermediateLines$1,4591,library,4592,get$library,4592,_multiLineComment$0,3928,_hasValue,4593,member,4594,get$member,4594,addStream$1,4238,_lastSubscription,4595,set$_lastSubscription,4595,_onListen$0,4329,dartException,4596,==,3446,get$==,3446,_schemeEnd,4597,__js_helper$_captured_this_0,4598,isPosix,4599,get$isPosix,4599,_hasSkipped,4600,heartbeat,4388,get$heartbeat,4388,_cancel$0,3695,_isUpgraded,4601,get$_isUpgraded,4601,_writeSidebar$0,3613,_print,4602,get$_print,4602,set$_print,4602,_tryResume$0,4551,_rootRegisterBinaryCallback$4,4603,_recordPause$1,3902,_useCapture,4604,firstMatch,3914,get$firstMatch,3914,_captured_port_0,4605,pause$1,4179,type,4606,get$type,4606,_scanIdentifier$0,4607,substring$2,4280,_onDone,4608,set$_onDone,4608,_computeKeys,3752,get$_computeKeys,3752,origin,4609,get$origin,4609,bindUnaryCallbackGuarded,4520,get$bindUnaryCallbackGuarded,4520,convert$1,3794,_multi_channel$_parent,4610,%,4611,get$%,4611,_keysArray,4612,get$_keysArray,4612,runUnary,4151,get$runUnary,4151,_sourceFile,4613,_captured_skip_3,4614,registerBinaryCallback,4389,get$registerBinaryCallback,4389,insertAll$2,4615,_platform_selector$_inner,4616,_captured_pp_0,4617,_engine$_captured_this_0,4618,_eventState,4619,child,4620,forTag,4621,_channel,4622,_captured_iterator_0,4623,checkMutable$1,4624,_captured_controller_3,4625,flush$2,4383,replaceFirst$2,4626,_binarySearch$1,4627,transform$1$1,4628,_mapper,4629,start$0,2491,replace$2$path$pathSegments,3540,_tdivFast$1,4630,_captured_oldPredicate_0,4631,_exception,4632,replace$1$pathSegments,3540,_captured_arg2_2,4633,toUri$1,4032,_suite,4634,isIdentifier,4635,get$isIdentifier,4635,convertNativeToDart_AcceptStructuredClone,2104,get$convertNativeToDart_AcceptStructuredClone,2104,_primary,4636,then$1$1,4468,removeAt,4637,get$removeAt,4637,_captured_div_1,4638,__internal$_current,4639,set$__internal$_current,4639,__js_helper$_current,4640,set$__js_helper$_current,4640,_removeEventListener,4641,get$_removeEventListener,4641,_optionalNamed,4642,onDone,4586,get$onDone,4586,reportLiveTest,4570,get$reportLiveTest,4570,_isSent,4643,get$_isSent,4643,_receiver,4644,forPlatform$1,4645,_runner_suite$_close,3758,get$_runner_suite$_close,3758,_delegate,4646,get$_delegate,4646,firstPendingEvent,4647,inSameErrorZone$1,4648,expect$1,539,intersection,4567,get$intersection,4567,horizontalLine,1933,get$horizontalLine,1933,frames,4649,get$frames,4649,onError,3472,get$onError,3472,_span,4650,_captured_channel_2,4651,group,587,get$group,587,_currentExpansion,4652,set$_currentExpansion,4652,_union_set_controller$_sets,4653,_async$_captured_this_0,4654,_serializeTest$3,4073,_isUnicode,4655,get$_isUnicode,4655,_shlPositive,3542,get$_shlPositive,3542,_lazy_trace$_captured_terse_2,4656,spanFor,3884,get$spanFor,3884,peekChar$0,4493,_writeSidebar,3613,get$_writeSidebar,3613,_expanded$_onDone,3983,get$_expanded$_onDone,3983,_span_exception$_source,4657,__internal$_start,4658,_modifications,4659,_nextPosition,4660,_toEncodable,4661,hasMatch$1,4662,_bind,3840,get$_bind,3840,_canFire,4663,get$_canFire,4663,postMessage$1,4664,_setPendingEvents$1,4104,internalComputeHashCode,4665,get$internalComputeHashCode,4665,_isOnlyWhitespace,4110,get$_isOnlyWhitespace,4110,_outstandingCallbackZones,4666,_captured_zone_1,4667,_isWithinOrEqualsFast$2,3550,rootPattern,4668,_captured_id_1,4669,pause,4179,get$pause,4179,_platform_selector$_span,4670,decode$1,3791,replaceFirst,4626,get$replaceFirst,4626,isUtc,4671,_postMessage_2$1,4672,set,4673,get$set,4673,pathFromUri,4674,get$pathFromUri,4674,_hasOneListener,4675,get$_hasOneListener,4675,_activeLoadTests,4676,_containsTableEntry$2,4677,_restartable_timer$_timer,4678,_recursiveMatch,3612,get$_recursiveMatch,3612,_pendingEvents,4679,get$_pendingEvents,4679,_addError$2,4680,_captured_prototypeForTag_0,4681,_nullErrorHandler$1,4682,_captured_cleanUp_3,4683,+,4684,get$+,4684,_chainSource,4685,get$_chainSource,4685,_complete,4140,get$_complete,4140,_portStart,4686,_isWithinOrEquals,4542,get$_isWithinOrEquals,4542,_printZone,4687,_multi_channel$_captured_T_1,4688,_captured_frame_0,4689,_columnStart,4690,_functions$_captured_result_0,4691,_addLiveSuite$1,4692,_pattern,4693,_onStreamDisconnected$0,4694,describeMismatch,4089,get$describeMismatch,4089,_stackTrace,4695,elapsed,4696,get$elapsed,4696,_process,4496,get$_process,4496,_closeChannel$2,3493,accept$1,4697,_containsTableEntry,4677,get$_containsTableEntry,4677,_async$_subscription,4698,get$_async$_subscription,4698,_packageResolver,4699,_eventsReceived,4700,_isMultiLine,4701,get$_isMultiLine,4701,_errors,4702,_index,4703,onZero,4704,get$onZero,4704,internalRemove,3937,get$internalRemove,3937,_captured_chain_0,4705,_runSkippedTest,4706,get$_runSkippedTest,4706,take$1,3568,visitAnd,3706,get$visitAnd,3706,_captured__prettyPrint_1,4707,_shrReceiverPositive$1,4147,removeAll$1,4708,apply,3966,get$apply,3966,_captured_arg1_1,4709,_callOnCancel$0,4710,firstWhere$1,3948,spanFrom$1,4181,_binarySearch,4627,get$_binarySearch,4627,_computeHashCode,4139,get$_computeHashCode,4139,_onCompleteGroup,4711,last,4712,get$last,4712,_getNext,3894,get$_getNext,3894,_channelNames,4713,sourceUrl,4714,get$sourceUrl,4714,_async$_onListen$1,4715,_resetTimer,4716,get$_resetTimer,4716,runBinary$3$3,4455,pathsEqual$2,3576,_currentTrace$1,3566,perform$1,4251,_liveSuites,4717,_stream_channel_completer$_set,4718,_file$_end,4719,forPlatform,4645,get$forPlatform,4645,_captured_value_2,4720,remove$1,4451,_gatherCoverage,4721,_isHttps,4722,get$_isHttps,4722,_closeUnchecked$0,4524,_captured_result_1,4723,removeFragment,3911,get$removeFragment,3911,_closedIds,4724,_captured_channel_0,4725,isNewLine,4726,handleUncaughtError$2,3603,elementAt,4321,get$elementAt,4321,highlight,3871,get$highlight,3871,_runCount,4727,close,3870,get$close,3870,_add,3797,get$_add,3797,_union_set$_captured_this_0,4728,_runSkipped,4729,_skipped,4730,_stack_zone_specification$_captured_R_2,4731,_writeIntermediateLines,4591,get$_writeIntermediateLines,4591,_isPackage,4732,get$_isPackage,4732,_findLine$1,3524,_expectsEvent$1,4733,_validateTags,4734,get$_validateTags,4734,copy,4735,_captured_error_2,4736,bottomLeftCorner,1937,get$bottomLeftCorner,1937,_addPending$1,4737,_stringSink,4738,expand,3722,get$expand,3722,_get$1,4031,_progressLine$1,3569,toRadixString,3971,get$toRadixString,3971,resolve$1,4218,insertAll,4615,get$insertAll,4615,remainder$1,4739,_inAddStream,4740,get$_inAddStream,4740,_pool$_captured_registered_1,4741,_captured_serialized_0,4742,_addError$1,4680,_onReleaseCompleters,4743,_functions$_captured_result_1,4744,inGoogle,4745,runBinaryGuarded$2$3,4746,_allowErrors,4747,_captured_body_0,4748,registerBinaryCallback$3$2,4389,_createSubscription$4,4749,condition,4750,map,4367,get$map,4367,checkGrowable$1,4751,moveNext,3558,get$moveNext,3558,absolutePathToUri$1,4752,_runtimes,4753,_captured_loadResource_2,4754,_collection$_rest,4755,_addError,4680,get$_addError,4680,registerCallback$1$2,3602,_setRemoveAfterFiring$0,4756,_sink,4757,set$_sink,4757,_captured_retry_6,4758,internalComputeHashCode$1,4665,_linkStreamToController$0,4096,_context$_current,4759,_onResume,4256,get$_onResume,4256,_registerBinaryCallback,4760,get$_registerBinaryCallback,4760,set$_registerBinaryCallback,4760,_ensureListening,4336,get$_ensureListening,4336,_stream_completer$_controller,4761,set$_stream_completer$_controller,4761,isCore,4762,get$isCore,4762,_setDestinationSink,4439,get$_setDestinationSink,4439,_captured_line_1,4763,_invoker$_onRun,4434,get$_invoker$_onRun,4434,getOffset,4764,get$getOffset,4764,listen$1,4088,indexOf,3530,get$indexOf,3530,_createPeriodicTimer,4765,get$_createPeriodicTimer,4765,set$_createPeriodicTimer,4765,_pool$_timeout,4766,mustCopy,4767,_firstSubscription,4768,set$_firstSubscription,4768,_scanner$_next,4769,foldFrames,4413,get$foldFrames,4413,_callOnCancel,4710,get$_callOnCancel,4710,onTestStarted,4770,get$onTestStarted,4770,_scanAnd$0,4771,__js_helper$_removeHashTableEntry,4346,get$__js_helper$_removeHashTableEntry,4346,_sendDone,4521,get$_sendDone,4521,_once,4772,absolutePathToUri,4752,get$absolutePathToUri,4752,_query,4773,config,4774,get$config,4774,_future,4775,removeFirst,4007,get$removeFirst,4007,_subscribe$4,4435,next,4776,get$next,4776,set$next,4776,_removeEventListener$3,4641,style,4777,_invoker$_tearDowns,4778,map$1$1,4367,_contains$1,3632,__js_helper$_getBucket$2,4779,_execGlobal,3731,get$_execGlobal,3731,_removeHashTableEntry$2,3976,complete$0,3865,_stopwatch,4780,decode,3791,get$decode,3791,addOutstandingCallback$0,4077,internalSet,3764,get$internalSet,3764,_getBucket$2,4303,join$0,3647,toSet$0,4553,_active,4781,_rootRun$4,4782,_remove,3736,get$_remove,3736,decrement,3777,get$decrement,3777,_guardCallback,4783,get$_guardCallback,4783,_onTestStartedController,4784,isAbsolute$1,3724,path,4785,get$path,4785,_async$_target,4786,_handleError,3633,get$_handleError,3633,_captured_K2_0,4787,_knownTags,4788,_tick,4789,_onReleaseCallbacks,4790,schedule,4055,get$schedule,4055,_captured_suite_0,4791,_pathStart,4792,_platform_selector$_captured_platform_0,4793,_restartable_timer$_duration,4794,_captured_portSubscription_1,4795,_badEventState,3968,get$_badEventState,3968,_guarantee_channel$_captured_this_0,4796,setEmpty$0,4797,_invalidPosition$3,4798,visitVariable,3564,get$visitVariable,3564,_containsKey$1,4799,_lastMatchPosition,4800,_captured_onPlatform_8,4801,_captured_predicate_1,4802,_addListener$1,4803,_mainController,4804,_colorize$2$color,3624,_guarantee_channel$_captured_this_1,4805,_invoker$_box_0,4806,_length,4807,typedMatches,3557,get$typedMatches,3557,_sendError,4005,get$_sendError,4005,nextKind,4808,get$nextKind,4808,_collection$_box_0,4809,isRootRelative,4407,get$isRootRelative,4407,_subscription,4810,set$_subscription,4810,addTo$1,4811,_tdivFast,4630,get$_tdivFast,4630,_uri,4812,isDone,4813,get$isDone,4813,_stateData,4814,setChannel$1,4815,_writeSidebar$1$end,3613,_captured_R_2,4816,_stream_channel_completer$_channel,4817,set$_stream_channel_completer$_channel,4817,runes,4818,get$runes,4818,_jsWeakMapOrKey,4819,_containsKey,4799,get$_containsKey,4799,_trimVMChain$1,3639,_queue,4820,_null_stream_sink$_closed,4821,_lineStarts,4822,listen,4088,get$listen,4088,_eventQueue,4823,bindCallback$1$1,3565,_engine$_runLiveTest,4068,get$_engine$_runLiveTest,4068,isSeparator$1,4824,_arguments,4825,_disconnected,4826,_validateTags$0,4734,_context,4827,_createSubscription,4749,get$_createSubscription,4749,_captured_stream_1,4828,_indexFor$2,4829,scheduleMicrotask$1,302,_cancelOnError,4830,get$_cancelOnError,4830,runOnce,4331,get$runOnce,4331,_tdivSlow,4508,get$_tdivSlow,4508,needsSeparator,3710,get$needsSeparator,3710,rest,4831,get$rest,4831,_rest,4832,errorCallback,3841,get$errorCallback,3841,rootLength$1,4060,_captured_stackTrace_2,4833,downEnd,1915,get$downEnd,1915,group$9$onPlatform$retry$skip$solo$tags$testOn$timeout,587,_onPause,3984,get$_onPause,3984,release$0,3757,_guardCallback$1,4783,forEach$1,3005,_stream_subscription$_source,4834,_checkEventAllowed$0,4240,_stack_zone_specification$_run$1$2,3958,_toFilePath$0,4835,sourceUrlId,4836,_shrOtherPositive,4837,get$_shrOtherPositive,4837,_closed,4838,_onIdleController,4839,_value,4840,_captured_error_1,4841,writeCharCode$1,4842,_close$0,4119,_tearDownAlls,4843,addError,3878,get$addError,3878,_captured_sourceMap_1,4844,walk,4448,get$walk,4448,_self,4845,onStateChange,4846,get$onStateChange,4846,addError$2,3878,_timeoutTimer,4847,currentChain$1,4848,_print_sink$_buffer,4849,_live_test_controller$_suite,4850,string,4851,_engine$_captured_liveTest_1,4852,isBrowser,4853,getOffset$1,4764,_suiteController,4854,_canonicalRecipe,4855,_canceled,4856,get$_canceled,4856,_nativeGlobalVersion,4857,get$_nativeGlobalVersion,4857,_pending,4858,set$_pending,4858,_queue_list$_tail,4859,_createTimer,4860,get$_createTimer,4860,set$_createTimer,4860,passed,4861,get$passed,4861,_onData,4862,set$_onData,4862,change$2$skip$skipReason,3651,_getTableCell,4490,get$_getTableCell,4490,_captured_action_1,4863,_captured_body_1,4864,_stream_group$_captured_this_0,4865,_captured_liveTest_1,4866,addEventListener,3366,get$addEventListener,3366,_captured_beforeLoad_4,4867,spanFor$3$files,3884,_printsOnFailure,4868,merge$1,4216,_writeAuthority$1,4869,_runSkippedTest$3,4706,spanFor$3$uri,3884,current,621,get$current,621,_onTimeout$0,4870,_onStateChange$2,4385,startChunkedConversion$1,4871,next$0,4776,accept,4697,get$accept,4697,handleWhenComplete$0,4872,_addStreamCompleter,4873,_group$_map,4137,get$_group$_map,4137,_captured_K_1,4874,runBinaryGuarded,4746,get$runBinaryGuarded,4746,_toNonSimple$0,3743,normalize$3,4062,getOffset$2,4764,clear$0,4298,inputId,4875,cloneNotRequired$1,4876,first,4877,get$first,4877,matches$1,3347,_handleError$2,3633,shuffle$1,4878,_pauseCompleter,4879,newJsList$1,4880,createTimer$2,4245,_registerUnaryCallback,4881,get$_registerUnaryCallback,4881,set$_registerUnaryCallback,4881,key,4882,_first,4883,_captured_T_1,4884,name,4885,get$name,4885,_simpleMerge$2,3973,_postMessage_1$2,4886,_addEventListener$3,3922,_resetTimer$0,4716,_consumeWhitespace$0,4549,_keys,4887,_live_test_controller$_run$0,3640,allMatches$1,3605,onPause,4888,fork$2$specification$zoneValues,4320,_captured_data_1,4889,isSeparator,4824,get$isSeparator,4824,withResource,3430,get$withResource,3430,hasQuery,4890,get$hasQuery,4890,_nums,4891,_setErrorObject$1,4892,_collection$_source,4893,handlesValue,4894,get$handlesValue,4894,_progressLine$3$color$suffix,3569,_stack_zone_specification$_captured_R_3,4895,_captured_channel_1,4896,run,4042,get$run,4042,getLine$1,4038,_stack_zone_specification$_registerCallback$1$4,3692,seen,4897,_lazy_chain$_inner,4898,set$_lazy_chain$_inner,4898,_selector1,4899,_consumeNewSegment$0,4900,lastIndexOf$2,3844,_urlSafe,4901,input,4902,_subscription_stream$_captured_stackTrace_2,4903,_reverseListeners,4445,get$_reverseListeners,4445,normalize,4062,get$normalize,4062,isRunning,4904,get$isRunning,4904,postMessage,4664,get$postMessage,4664,round,3839,get$round,3839,_deleteTableEntry,4424,get$_deleteTableEntry,4424,prettyUri$1,3506,_trace$_captured_level_1,4905,_selector,4906,virtualChannel$1,4017,_pause$0,4907,_isScheme$1,4908,_onStreamDisconnected,4694,get$_onStreamDisconnected,4694,_parsed_path$_captured_this_0,4909,_declarer$_captured_this_0,4910,_isSourceStreamSet,4911,get$_isSourceStreamSet,4911,_local,4912,set$_local,4912,length,4913,get$length,4913,set$length,4913,separator,4914,get$separator,4914,_captured_T_3,4915,_captured_handleError_0,4916,toList$0,4159,_serializeGroup$3,3749,fillRange,3701,get$fillRange,3701,_setChained$1,4917,_yellow,4918,visitOr$1,4472,_captured_location_2,4919,describe$1,3396,removeLast,3819,get$removeLast,3819,registerCallback,3602,get$registerCallback,3602,validate,3977,get$validate,3977,cleanupSlots$0,4920,max$2,470,_captured_depth_3,4921,_jsTrace,4922,codeUnitAt$1,3808,_captured_dispatch_1,4923,_end,4924,__js_helper$_unlinkCell,4127,get$__js_helper$_unlinkCell,4127,_captured_matcher_0,4925,addTo,4811,get$addTo,4811,_modificationCount,4926,_processed,4927,_timer,4928,_writeString$1,4929,_cloneResult,3638,get$_cloneResult,3638,_captured_platform_1,4930,_fail$1,4931,isClosed,4932,get$isClosed,4932,keys,4933,get$keys,4933,isPaused,4934,get$isPaused,4934,pathFromUri$1,4674,_onCancel,3575,get$_onCancel,3575,_captured_engine_0,4935,_set$2,4212,_setUps,4936,_expanded$_sink,4937,_grow$0,4938,text,4939,get$text,4939,any,3793,get$any,3793,_findColumn$3,4009,_onErrorController,4940,_text,4941,_captured_this_0,4942,copyList,4071,get$copyList,4071,_prependListeners$1,4395,handlesError,4943,get$handlesError,4943,_contents,4944,_captured_milliseconds_1,4945,_updateRequests$0,4220,_captured_sdkLib_3,4946,_initializeText$0,4947,_captured_trace_0,4948,_evalCache,4949,_closeGap,4364,get$_closeGap,4364,_limit,4950,_toggleEventId$0,4951,_live_suite_controller$_active,4952,_addLiveSuite,4692,get$_addLiveSuite,4692,_createNode$1,4953,copy$0,4735,toSpec$0,4954,userInfo,4955,get$userInfo,4955,_addListener,4803,get$_addListener,4803,excludeTags,4956,_indexFor,4829,get$_indexFor,4829,_separatorIndices,4957,setState,4297,get$setState,4297,_captured_completer_1,4958,_is,4959,_shrOtherPositive$1,4837,_isUsed,4960,putIfAbsent$2,3873,_paddingAfterSidebar,4961,get$_paddingAfterSidebar,4961,code,4962,sink,4963,get$sink,4963,_captured_skipReason_7,4964,_destinationSink,4965,set$_destinationSink,4965,_values,4966,_suite$_metadata,4967,_addLoadSuite$1,4968,_captured_message_1,4969,_compareIterables,3860,get$_compareIterables,3860,values,4970,get$values,4970,_nativeRegExp,4971,chainFor,4079,get$chainFor,4079,_setTableEntry$3,4373,removeAt$1,4637,_isDefined,4972,_isDone,4973,resume$0,4345,_isDotAll,4974,get$_isDotAll,4974,_unlinkCell$1,4405,offset,4975,get$offset,4975,putIntoObject$3,4976,copies,4977,print,412,get$print,412,_runBinary,4978,get$_runBinary,4978,set$_runBinary,4978,_addPending,4737,get$_addPending,4737,_start,4979,_onTestStarted$1,3482,_stream_queue$_source,4980,year,4981,get$year,4981,_requestQueue,4982,_needsNormalization,4505,get$_needsNormalization,4505,$le,4983,$indexSet,4984,$index,4985,$xor,4986,$or,4987,$eq,4988,$mod,4989,$shr,4990,$and,4991,$ge,4992,$gt,4993,$lt,4994,$mul,4995,$not,4996,$shl,4997,$div,4998,$sub,4999,$add,5000,$negate,5001,$tdiv,5002"},"frames":"qsTAyEiB+2EuH;eAEFmduF;mXEqKbndAAAAAwR,A;iQAuHeAsI;eAEFmdwG;uEAohBwBnd8B;qEAEFAqC;oEAEDAoC;w7GGrpBvBAyEAhOXA6B,A;u1CC+YE4hF8F;qxCA0MSCuB;uCAAAA6B;wIAqBeC6B;0YAYjBD4C;uyHA4NQ7tBgB;+5DA8Ya/zD4C;igBAmBjByIyD;oFAOEAyD;eAIJzI2C;iEASAA6C;uPAmCcDoC;urCA4QZA+S;wnJAgSHAoE;iJAKKA0B;qLAWaAwH;oLASbA0B;sOAiCmBA4B;6HAGtBA4B;iRAmCCxzEAIn4BNu1JkF,gE;wEJq4BKC+C;6CACEA4B;0IAUDx1JAIh5BNu1J8D,yD;oDJk5BMC4B;2kBAmBHhiFAKj9D0BA8E,A;q1BLqlEtBA6D;AAEAA0Q;w+IAwPmCiiF0C;8EAAAA+E;wZAYXAwC;8EAAAAuD;49DAkGJA+J;AACICyL;w6CAsI7B70JACnsEF80JiD,sB;0GDusEE90JACvsEF80JiD,sB;qQDyuEcniF+G;0iCAgbMoiFgG;+dA6BjBpiFqC;qNAqBAAkD;m4BIt6FN+hFgC;OAEKtzJmBArBwB4zJY,wC;wEAyBVAM;wDAKnBCqC;sYAOACwF;AAhBK9zJAAtBFszJiB,A;AAsCHQ2B;sFAIACgE;AApBK/zJAAtBFszJiB,A;AA0CHS2B;iCACiB9zJAAwYd8zJsE,A;AA7ZE/zJAAtBFszJmB,A;AA2CcrzJAAwYd8zJ6B,2C;8xCA9VC5zJAAq2BN6zJqB,A;4zDAhxBKViC;0BAGmB/hFuC;4DACWxzE0C;4EAGpBw1J4C;8PAqDsBlzJAHmW7B4zJ6BAjBR3zJAA3I8B4zJuD,A,A,A;OGvMO7zJ+D;6NAWXizJkC;AACbaiE;qDAEXbyC;iFASKa0C;gJA0HLt0Ja;0BAAAA2D;oKAygBwByzJkC;gnEF/1BnB1yJAA2BTwzJoI,A;kTAZSxzJAAYTwzJoI,A;6yCApEuBlzJAAzChBmzJwE,A;0zDA+QSjzJsL;0gCKjNhBmwEAAAAAqG,A;+WCpESusEwB;+IAGyBnbkB;0bA0BhBxsDO;qfAuBPm+E+F;sCACFCiC;gBAGTCqF;6vBA2CODiC;0YAyBPhkDADKQh/B4B,mE;2CCLRlwDsC;wCACEi/Fc;+EACAAI;2EAGFAc;kmBA8DkCm0CgB;AAA1BFoC;0EAGRCqF;grPP/KkDEyC;AAA3BCY;AACfCyE;AADeD2B;m8CAySPEmB;qDAGVCmD;AAEW3/E0H;4FAIT4/EuD;yiBAcOCiC;+WAaMCAAqnCiBCAA/C9B//EiH,A,A;OAtkCa8/EuE;2PAMAGAAqnCjBCAAnDIlgFiH,A,A;OAlkCaigFuE;2PAMAGAAqnCjBCAAvDIrgFiH,A,A;OA9jCaogFuE;uUAQkCG2C;+HAGpCC+C;geAUMCqD;wvBAiBNbsD;mUAOCcgD;qiCAgCGC6B;ymCA+B0BCAA5ORxkFkD,A;AA6OrBykFmE;AAEACmE;AAEACmD;ycAgCd51JAAzB0B4zJsB,A;+NAgD5BxwJAAnD+BwwJmB,A;AAoD1BtwJ0B;mhCA8EkBtDAA/HK4zJoM,A;8MAoJpBrxJqF;2LAoBRszJsB;AADG5kFgB;8EAOkB1uE4C;iHAsCVmyJ6D;AAKXtrJ0E;AAIE0sJiB;AADACQ;yDAGalhFgI;+UAaGugF2DAxlBGYqB,A;6FAkmBfC4H;AAMNCmB;+HAWGCgC;6IAQOCiC;uBAKVhzJAAvR+BwwJiB,A;83BA8T/BuC8E;u2BA6BgBvjFiC;sOAQAAiC;+1IAmKXxpE8C;oPAUYksJkEAp1BDUiB,A;mnDAk5BLtBiC;gQASU2BkC;wGAKICkC;wGAKAlCkC;sHAKTgBkC;8VAcSXmC;4IAOXc2CA36BISsC,A;+4BA0mCLO4F;u4BAwCCCmB;8CAGVC+B;+UAUUlCmB;8CAGVC+C;AAEuB3/E0H;6jBAgDZAkI;AACjB6hF0B;AASIXQ;yCACADW;2CACAIQ;yPAyDGSAAIOlBAArvCHxkF4C,A,AAsvCP2lFqB,GACAC2C,A;gQAwBGCAAKOrBAApxCHxkF4C,A,AAqxCP2lFwB,AACAG4B,GACAF2C,A;qSASGGAAKOvBAAryCHxkF4C,A,AAsyCP2lFsB,AACAGyB,GACAF2C,A;2QASqBhiFiI;wTAYF2gF4B;OAEE3gFiI;mKAqBZoiF2K;iFAINCAAKOzBAA71CHxkF4C,A,AA81CP2lFqB,AACAG4B,AACAIyC,wBAGE7CsC,GAEFuC6B,A;8LAuBInCc;yBACQWoE;uKAIH+BAAlBEviF0H,kF;iFAsBRwiFAAKO5BAA14CHxkF4C,A,AA24CP2lFsB,AACAG8B,AACAI6B,GACAN6B,A;6TA8CSSAAxCPziFyJ,AACJ0iF2xB,gC;mFA2CKCAAKO/BAAr8CHxkF4C,A,AAs8CP2lFsB,AACAGiC,AACAI2B,GACAN+B,A;oMAaSYAAPP5iF0H,sE;mFAWC6iFAAKOjCAA/9CHxkF4C,A,AAg+CP2lFsB,AACAGuC,AACAIuB,GACAN+B,A;4ZAoKOcoD;itBAuBCCyL;qDAIkBrBiE;qDAIAsBiE;sDAIACiE;2DAItBCAAqERCmC,AACACuB,A;2DAlEQCkBA4GWC2BAmFACmB,4DAEnBHsC,A,imB;sPAtLsBtDAAjccCAA/C9B//EwI,A,+D;2IAwfgBigFAAncpBCAAnDIlgFwI,A,+D;2IA8fgBogFAArcpBCAAvDIrgFwI,A,+D;2DAigBEkjFAAiCRCmC,AACACuB,A;2DA9BQIkBAiG6C5CAApyDdxkFqJ,A,meA6zDvBknF2BAiCGCmB,4DAEnBHgD,A,AApCoBvCsD,AAEACmE,AACAC0D,wH;2DAxHZmCAAyBRCmC,AACACuB,A;0CAtBQKAA0HYH2BAyBDCmB,4DAEnBHqG,A,A;4DAjJQFAAiBRCmC,AACACuB,A;2CAdQMAAwHYC2BA0BDJmB,iEAEnBHqG,A,A;o9BAhHoDQsD;wJAUpCC4DAroBDhEgB,2BAEKW2F,AAGODiD,2X;0JAktBHuD4D;2DAIAC4D;uhCAsDTlEiC;wDAEcWqC;+OAQTA4D;w7BAuGJEwC;8GAKFbc;6CA6BI2BuC;yGAUJAkC;MAAAAAAxoEILmB,A;iGAipEA5BuC;sOAYIkCuC;0HAWKlCkC;oOAYIkCkC;4rBA4BS7B8CAvrEtBuBmB,A;AAwrEVvBwC;s9BAsBYa4CAxtEFUiB,A;AAytEEVsC;gkCA4BHuDa;iMAQAAa;+NASAAuC;oZAoBDC4B;+NAEJDiB;mSASKzD8C;iBACAA8C;gSAkBJyDyB;AACAAe;80BA0ECnEc;4NAYJU0CAp7EaYqB,A;AAo7EeZyC;2LAMxBC2CA96EIWqB,A;AA86EoBX0C;yJAMxBC2CA35EIUqB,A;AA25EmBV0C;yJAC/ByD6O;4DAIiBtE2CAt5ELuBqB,A;AAu5EJvB0C;qrCAqDDCc;+JAMON0C;w2FK1kFJ4EqG;oiBA+BhBC8C;grZUpF4B3+BuD;sMAmB9BrpD+C;4HAeAgNwD;4EAiFWhN2BA7BSioFAAAAjoFeE0BKlwDgB,2B,A,sC;2JFkBR4pFQ;y1BA2DM15BwBE7EElwDwD,A;AF6EFo4IqE;mdAiCXp4I0C;sJI9JckwD4BFgDDlwDgB,iC;AE/CjB61G4B;8IAyBkB3lD4BFsBDlwDgB,iC;saEORmwDoBFUmCnwDgB,uCAVpDo7DAAUAAAATEg9E6D,A,A,A;sKEEmBloFAFVIlwDwB,8D;gKEcfxVAAsrBuC0lEwC,A;0QA9oB3BlwDkC;8LAGRxVAA2oBmC0lEmE,A;qCAvoBpC09BoBFjDM5tFgB,iCADnB4tFAAAAAmD,A,A;6EE4HsC19B0KFvIblwD6D,A;kkBEuMRmwDAAlKJ27BoBFnCwC9rF+B,AAArD8rFAAAAAqB,A,A,A;uhBE0Q0BoDANsHMh/BiC,+BAAAAsC,A;iHMnFLA0CF/SFlwDoH,A;4TEgrBKAyD;mGAEpBxVAAkBuC0lEiE,A;uMF7rBjDkLAAAAAAACEg9EkF,A,A;oIAiOeCoB;sDAIfCqBArIOC4B,iC;6dAqKOCiE;uCAEICyF;uRAQhBCqBAvOKF6B,iE;ycAmUSHkC;8BACSMuB;+DAGYC2D;yjBA8BV3NkB;iEAaNt0EmB;kCAZIkiF8C;uDACGldiG;AAWPhlEsB;sDATgBiiFiBAvS9BD4B,2D;oIA8SiB34I0B;+BAEH22DqH;yFAoEJk5DkB;+lBAuBOwoB8B;AACFSiBA5SdT4B,iK;AA6SEUiBA/WFV4B,iBACMA+B,sG;gMA2XASqBA1TNTsB,sK;gFA+TJWAA9YIXsB,A;qBA2YJDsK;yBAGAYoH;mqCIrrBQCoD;+GAYqB/oF+D;4HAIrB+oFoD;yXAsBkB/oFyD;qZAwCPlwD2B;gNASrB27HM;iCAAAAgD;qLAKC37HsB;8HCuBKkwD+J;+JAQUy9BAC4SQz9BuE,A;+ED7OfA2B;wDAAAAsC;qGAs6DLA4D;OAAAAuD;qIClkEIAwG;AACAAuG;6TAwtBLlwDwD;0PChtBiB64IAAAA74I0D,A;sGAgBxBkwDqF;wKA+cKlwD6D;qXChjB2BA8C;wHAIhBxVAN84BiC0lE6F,A;u9BCj3BtClwDsB;2pDFwjCJk5IsE;weAYAAsE;wiBAYAAsE;2vBA0BmBvdc;iCAAAAwB;uoBA0BbwdAH/jCiB5/BmD,yB;OG+jCjB4/BoE;sEAIbCc;gFAIKp5IqC;4hBA0BMkwD8CArXXAAAAAAgQAcYA4D,gIAGAA4D,uIAGAA4D,sHAIAAmH,kUAeAAkG,sKAMAA6G,wC,A,A;u/BA4kBc6Mie;ygBAkBnB/8D0E;6/gBSr8CYkwD8C;+CAAAAwD;0cA4dAmpFAC/cPnpF4C,A;4GD+cOmpFAC/cPnpF+D,A;sMD4e+BmpFAC5e/BnpFuF,A;iFDofCmpFACpfDnpFqF,A;sEDupCOAqD;6EA8BmBAqD;sJAKPAuD;qGAqU7BkJ8H;2MA2GFlJAAAAAoD,A;u8BGz6CUo3DiH;wQAqBcp3DkD;iGAGpBo3DiG;oRAMKh7BkB;4gHGrPMp8BqD;gdAoBNo8BkB;uJCwdTp8BAAAAA4H,A;+kIC7ZaA2C;26IjCkDCopFwD;gVAwDMC8C;mmBAiOXC2D;iKAYACqC;6BAAAAc;qMAoBEC8E;OAAAAyH;yEAGACoH;yrCAoEHzpFuG;yMA+DQw+CsC;AAEDkrCc;uFAGFAc;0EAGEAkC;qhBA+GoBndAI3lBcqVuI,A;kGJkmBnCr+CyF;0TAKRo0CAA/Ja9lEiI,A;+7IsCnZf7RyG;+HClKFkpFwC;kZEixBkBSgQ;usGAAAA8D;8CAAAAqD;ovEA8NT3pFoG;82FAuUSAAlCrS4B4pFkD,A;sIkCqS5B5pFAlCrS4B4pFuC,A;24FkC6blCC4E;8RAcoBCgB;4GAENAuB;gOAOI14BA7B/jCR5S4D,A;8J6BokCTsrC+D;AACFtrCqB;8MASCqrCmC;y1BAgMQ3pD+G;AAApBlBAhD7pD8Bh/B2F,A;mCgD6pD9BlwD8B;00DAsDSg2FoE;szFAkNSzyBiI;6sBAsCPrTgK;uZAeIA2C;8TASX+uCAzC18CJg7CyC,A;sGyC88CaCoH;qBAAAA4F;wHAGIhqF+C;2rBAiBFA6C;2cAaRo8BkB;+nBA8BQp8B2C;icAWX+uCAzCxhDJg7CyC,A;iHyC4hDaEoH;qBAAAA4F;wHAGIjqF+C;uRAQJkqF0H;uBAAAAkG;+hBAWElqF+C;ymBAeRo8BkB;ggBAiBA+tDsH;mBAAAA0F;w6CAyCInwBA9B/6DAh6DwE,O;iC8B+6DAg6DA9B/6DAh6D4C,A;wC8Bm7DAw+CyB;gkDA0FP4rC4I;iBAAAAiF;uBAIYv4EqG;q+FAmGoBq4EgI;yBAAAAyH;w0BAiBrBlqF2C;8FAEX+uCgD;0VAWG3SkB;qbAoEKg1BA7B5iEU5SsB,A;4O6BkjEP4SA9Bt5DO5SmB,A;mI8Bw5DLA6B;osBAgCL4SA7BplEU5SsB,A;oO6B0lENA4E;obAYLAe;knEAiMX4YiH;s7CAwKuC6MA7BvgFVjkEwB,A;yoB6B6hFtBg2CoC;OAAAAAC31FAh2CyB,gB;2SDoyGL+uCAzCpyFFg7CoD,A;+KyC0yFEh7C6B;uHAEAAAzC5yFFg7C+B,A;AyC6yFEh7CwB;49EAgXa5xBuC;gpBAkBXw6DAzC1qGJoSoB,A;kByC0qGIpSAzC1qGa9lEM,AAAjBk4EkF,A;AyC4qGIpSAzC5qGa9lE+D,AAAjBk4E2B,A;AyC6qGIpSAzC7qGa9lEsC,A;wGyC6qGb8lEAzC7qGJoS2B,A;AyC8qGIpSAzC9qGa9lEM,AAAjBk4EkD,A;gxX2C3hB8B/pFgE;0EA6GdAA1BooBSAAFjvBvBAAAtB0B05BAAAA15BwBA4MLlwDgB,+C,A,A,kF,A;uoD8B0plCzBkwDAAAAAyB,A;0EA44GSlwDsB;wwECvssCsBu6IiBCEPpmBAnC6TOjkEoC,A,AmC7TpBs8BAA7BcguDyD,A,gDA6BdhuDAAaeiuDoB,0B,AAF1BjuD6C,A;urBCnBgBt8B2B;AAAwBw2DsB;yCAIG1mHsB;gTAUzCk+FsC;mHAAAA8D;AAAAhuC0BGpDkDwqFuE,AAISCgF,AAGtCCwE,A;iBH0HHn6BS;6VAcV6uBgBC/DgC7uBS,AAAQ6uBgB,A;wMDqExCAgBCrEgC7uBS,AAAQ6uBgB,A;qGDyEtBtvI+BKtInBAyB,wB;m8HEXmB66I+F;AAMACyC;AAOCCmC;AA4NVCAAAA9qFAC/NA+qFAAAA/qFAvCsvBQAAFjvBvBAAAtB0B05BAAAA15BAA4MLlwDsB,A,A,A,A,A,A,A,A;AwC5IzBkwDAAAAAwK,A;sDAgLmB8qFAAAA9qFoBC/NA+qFAAAA/qFAvCsvBQAsBFjvBvBAAAtB0B05BAAAA15BuG,A,A,A,A,A,A,A;yqC0CuBjBAqC;AAAiBg6DA9CiOjBh6DoD,O;6D8CjOiBg6DA9CiOjBh6DyD,A;+M8CjNUg6DA9CiNVh6DsD,A;O8CjNFAqC;AAAYg6DA9CiNVh6DoD,O;0E8CjNiBm8BkE;gDAAnBn8BAEmLUA8B,A;6IF9Hd8lCwD;0GAIFqnB+C;AAFArnByC;mDAEAqnBU;wFAEArnBoD;+CAMAAoD;uDAEAAoD;2EAKAqnB0C;AAHArnByC;2CAGAqnBU;m4IK8CiBH8E;giBA+BoBhtD2H;cACCA6F;8EAH9BAuF;AAjBbmdAAAAA4G,A;ibA6BAnbAAAAAuH,A;gxDAuD0CipFoB;6CACjCjrFc;89DGnKMkrFAAAAlrFACnDCmrF0D,AAvBGJAAAA/qFAjDsvBQAAFjvBvBAAAtB0B05BAAAA15BAA4MLlwD2H,A,A,A,A,A,A,A,A;AkDpGAu7I2E;AAwDCCAAAAttDmBEzIKutD4B,AAURCAAAArCAzCEXnpFoI,A,A,AyCiCZg+BAAAAAiCACcAA9C2DFh+BqC,A,mI,A,A,A;A4CoCS0rF4C;AAICC4C;AAIDC4C;AAILC8B;2DArFDXAAAAlrFkBC1EI+qFAAAA/qFAjDsvBQAsBFjvBvBAAAtB0B05BAAAA15BoH,A,A,A,A,A,A,A;AkD8FawrF4E;AAiBTM0C;AAUJCAAAA/tDA5CQlBh+BwG,A,A;A4CGmBisFuD;AAQCCAAAAluDA5CXpBh+B2H,A,A;A4CqDiBosF0C;AAMMCiD;AAgBnCrsFuE;6xIM/LcssF2E;yEAOdtsFAAAAAkCACSA4D,A,A;wbxBqMTmdAAAAAyIAG2B++D+B,+J,A;qGA0F3Bl8EAAAAAoJAGyBk8E+B,iR,A;qbYnPZl8E+G;4aAsBAAgB;gLAUqBA8B;8EAAAAgBAmHbA8B,A;gyBArGNsVAAOetV8B,+C;OAPfsVgBAOetVAA8FTA+B,A,A;ucAzFD8lCmE;0CACLmCuC;qDACR+xBAlE8BmCh6D2E,O;iCkE9BnCg6DAlE8BmCh6DwD,A;8PkEd3BkgC4C;6FACApDkF;qGAHT98ByB;AAOSg6D2E;iCAAAAoC;AAPTh6DAAyEeA+B,A;2EA5DfAyB;AAGSg6DAlE6P2B78CqB,A;AkE9P3BgfAhDuDFn8BoB,A;+DgDvDEm8BkC;iEACA69BmC;uFAHTh6DAA4DeA+B,A;4EA7CfAyB;AAISg6DAlE6O2B78CqB,A;AkE9O3BgfAhDuCFn8BoB,A;0FgDvCEm8BkC;kEACA69BmC;wFAJTh6DAA6CeA+B,A;wIAPFg6DAlE2MuB78CqB,A;AkE7MvBgfAhDMNn8BoB,A;0FgDNMm8BkC;mEAEA69BmC;oGAPbh6D2CAceA+B,A;2hFe9LbAqD;s/BCARAAAAAAqX,A;2cC6C4BusFiG;AAyBV5vDAAAA38BA3DqqBSAAFjvBvBAAAtB0B05BAAAA15BAA4MLlwD6B,A,A,A,A,A,A;0H6DhINy7IsC;AAMYkBAAAAzuDAvD8CnBh+BgG,A,A;AuDvCa2sFAAAA3uDAvDuCbh+BqG,A,A;AuDjCe6sFAAAA7uDAvDiCfh+BkG,A,A;AuD9BM28BAAAA38BA3DqqBSAsBFjvBvBAAAtB0B05BAAAA15B2E,A,A,A,A,A;A6D0H9BAAAAAAAAOcAE,wC,A;gsBCjIEAA5DuwBWAAFjvBvBAAAtB0B05BAAAA15BUA4MLlwDyG,A,A,A,A,A;A8D1MjBAmC;kCACAAQC0HMA0B,A;AD3HNAc;qEAFQkwDA5DuwBWA2D,A;8+DgE7vB3BAAAAAAuB,A;oCAAAAAAAAAkH,A;isBCoCmCoxDAtEoXX5SuB,A;AsEnXQx+C6D;yHAEAA2C;yJAAAAoD;OALvBAqC;iqFEWFunC4B;AACYz3FkD;8KAAAAiE;qBAAAA+B;80BE5Dfi9I0D;oIAMJn4CuDEsIoBwqC2B,AACZ3hD6CpC1IkCAA/Bgddz9B4B,oBAAAAiC,A,A,2B;4oEqEvYhBlwDYZqDEA0B,+B;0FYjDFAaZiDEA0B,A;AYrDFA+C;AAIQ64GAZODqkCmBAdQl9I2B,A,A;sBYOP64GkBZO8BhhBO/DhElB0gDuB,A,A;wsB2EsHCroF2B;8EAMX70DAE6JpB60D6CDjTwBitFAAAAjtFwB,A,A,4BCiTJo8BKDrSDAkB,A,A;2EDyICjxFAE4JpB60D6BDjTwBitFAAAAjtFwB,A,A,wBCiTJo8BKDrSDAkB,A,A;4FD0IXg1BA9EiRc5SwE,A;4B8EhRJ9BA1FyalBqtC2B,A;6R6FhkBFmDM;uDAMAAM;u+ER8EkCC8B;AAGEC8B;AAICCwD;AAGrCh2E6E;0GA0EuCi2EgF;AAIvCj2EwD;08BA4JAAuD;olGS1QoB8FgD;qlB8EkBpBnd6C;A5EpEAAAAAAA0Z,A;mmCC2FWmdAA9DyBowE8B,AAGGC8B,AAGAC8B,AAGtBCAAAA1tFc,4B,AAUiB2tF8B,AASLC8B,AAMIC6B,A;05FEqB3B/nD4D;2EACKA8C;gjBAmBuBgoDoM;UAAAA4E;+6CAgCvBtvCe;inEzC9DMx+CA0C7CG+tFAAAA/tFApGyDRguF0G,A,A,oCoGzDQDAAAA/tF6E,A,A;8F1CuDK2+E8T;sLAgCnBsPUA1FiDn+IiG,mD;AA0FpBm+IgBA1FoBn+IuC,A;AA0FpBmoIA0CvDIiWoCAgH/BluFO,uB,A;mB1CzD2Bi4EA0CvDIiWAAgH/BluF4B,A,W;uB1CtDKAgB;oOAoBPiuFAAjHiDn+IsB,wH;OAiHpBm+IWAjHoBn+I8B,A;mFAkHtBkwDqC;uEACpBAgB;2NASmBAS;0CAAAAyB;oIAEjBAqC;AACDg6DA/CwFDh6DyB,A;gE+CxFCg6DmC;kKAE8Bh6DqC;qGAE/BAqC;AACDg6DA/CmFCh6DyB,A;gE+CnFDg6DmC;kmJ4C1IG+NAzCdT/nE8B,A;oFyCcS+nEwB;urFGCSj4H+CRgDYA0B,qB;40C/CtCpCkwDAAAAA0KAI+By9BwD,AAAiC2hDiD,cADvD+OoB,AACsB1wDA7BqaHz9BuF,A,A6BraoCo/EA7B0alCp/E2G,A,gB6BzanBmuFoB,AACoB1wDA7BmaHz9BuF,A,A6BnaoCo/EA7BwalCp/EyH,A,A,A;6uBsFtXXouFwF;uBAIVpuFc;6lCfOIioCuF;mnBAuLI/H2D;kCAAjBlBAnG7QgCh/B2F,A;+CmG6QhClwDoC;0MgBvOyBu+IAAAAruFA1CjBTmrFU,AAvBGJAAAA/qFAjDsvBQAAFjvBvBAAAtB0B05BAAAA15BAA4MLlwD4F,A,A,A,A,A,A,A,A;A6F3ICw+IAAAAtuFA3FssBCAAFjvBvBAAAtB0B05BAAAA15BAA4MLlwDmI,A,A,A,A,A,A;uC6FnJAu+IAAAAruFkB1CxCN+qFAAAA/qFAjDsvBQAsBFjvBvBAAAtB0B05BAAAA15BoH,A,A,A,A,A,A,A;A6FiEJsuFAAAAtuFA3FssBCAsBFjvBvBAAAtB0B05BAAAA15B4B,A,A,A,A,A;A6FoECwuFAAAAxwDAvF4DnBh+BiG,A,A;AuFxDc0uF0C;AAGCC0C;AAGDC0C;AAwEP9DAAAA9qFoBpDrIA+qFAAAA/qFAvCsvBQAsBFjvBvBAAAtB0B05BAAAA15BiE,A,A,A,A,A,A,A;A6FyF9BAwC;21CC1BqBw+CuB;2HACKAwC;4FACWwOAlGkgBtB6hCuD,A;0wBoGlkBoB5qBAnGyWJjkEwC,A;AmGzW/Bg/BAcyC4Bh/B4G,A;gCdzC5BlwD6C;oJAaS0uGuB;g2CEMTx+CAAAAAwI,A;s7CCOS7wDAC0QP6wDmD,A;iEDrQO7wDACqQP6wDiB,A;iHDnQO5wDAE/BL4wDgC,AACAA0B,A;2CFwCGmtDG;kEADDrnBgD;wBACCqnBmC;kKASUgpBAtGuTMn2E+B,A;AsGvTAu0CoP;qaG1BNp3B6B;6kBA4gCDnd0C;AACd+uCkCrH5fAg7CyB,A;AqH6fc9hDkH;AACT+xBA5Hz4BmCh6D4E,O;mC4Hy4BnCg6DA5Hz4BmCh6DyD,A;gC4Hw4BxC+uCArH7fAg7CgC,A;AqHigBAh7CArHjgBAg7C6F,A;ktBoHteEh7CApHseFg7CkB,A;0BoHzeEh7C0BpHyeFg7CyB,A;IoHxeEh7CApHweFg7C6F,A;IoHteEh7CApHseFg7CmE,A;mHoHheEh7CApHgeFg7C4B,A;qBoHheEh7CApHgeFg7CiF,A;oEoH9dEh7CApH8dFg7C6B,A;AoH7dEh7CApH6dFg7CsC,A;usBiD1dsB+E4C;AAI8BCoF;AAIlCCmC;AAIDCmC;uCAwBnBjvFsC;i9FsEIqC8lC2C;yoECmKtB9lCoBCnSK6gCgD,A;k1CCgBbqfA7Eor+B+B0hBAA49G9B5hE8E,A,A;0L6EznlCiCg6BS;0DAAtBm1D8C;AACRn1D+E;wCAEOu2BS;y8CtElBlBvwDiF;ulDjDsSgCqpFgD;8qDQrM9BrX+E;wGAKAAuE;8TASAAqE;kWASAAwE;saAqBAAwE;0NAMAAwD;4YA2DAAwD;wsBAwBWhyEkE;WAAAAkE;srGA8JXiqE0D;09BAwCAA4D;4YASA+H2E;ygCAyH4BoduD;+MAcEpvF+C;+BAAAA4B;8SAO9BgyE8F;suBAoBA/H2F;2kEmH7ZOolBgQ;sBAAAAwD;yBAAAAqH;2gGlHzMACiF;6TASP1NyG;yHAKO5sIAPyBEgrDwD,A;2mBOXEAkC;k2JA0XXijFiF;smCrB5Z8BjjFmB;qBAAAA6B;WAAAA6B;8hCAuPEAyB;mCAAAA6B;mCAAAA4B;i/CEjOFAmD;uBAAAAwC;w/BAiHfw+CyB;6QASXzP0B;2RASAAU;uYAWoC/uC2E;WAAAA+E;q/HA6LVAqB;uDAAAA6B;WAAAA+B;4uCA6DAAgD;sGAAAAqC;iDAGUmdyB;4EAAAA8D;yaA6BVndyB;oFAAAAAASMuvFkB,6B;WATNvvF+B;y+BAmMnBAoD;0GAAAAyC;2nIE/fAAoC;sBAAAAsC;6FA8B+Bg/BAgBibZh/Ba,A;iBhBjbYg/B0B;iCAAAAAgBibZh/BS,yBAAAA4B,A;yVf5jBdwvFiE;6xECitDYhxCwC;wuEAo2BV6qCiD;2hB6B5hFPrpFgD;kPAAAAuC;48BAwBEyvF8E;qhCAiCAAoF;opJA8HgBzvFwB;85FA0JlBAa;sFAAAAwD;EAAAAAA0BbAAAAAA0B,A,A;knDtBzWe0vFsB;yTAU4CAsB;mNA4CrD9N8F;kUAqBO5hF8C;qtCAyDT4Ee;uIAQ6Bh3DwE;+EA0CzBoyDsD;6oBA4BQ4EiD;AAII02CAA5GEq0CkD,A;gUA+GVC0E;4iBCrPiBhiJ2E;WAAAAQ;4FAoCrBoyD4D;0RAKOA4B;wnBA0BEAK;urJPZRmiFiC;yJAMiB0NqB;AA+vBnB3KiC;oMA/E+BthFgI;0hIehf5B5DoC;+6BuDjIiBAerD+DFlwDsC,A;igCqDfnButI4D;sDAESr9EoC9C6gBsClwDwB,mDAArDkwDAAAAA0B,A,A;+B8C3gB2CAAApLrCAA/CizBAAAC/uBkB2oFAAAA74IwD,A,A,A,0HAgBxBkwDsF,A;uB8CkG2CAAAtL3CAAAAAA0G,A,A;AAwLE8vF8d;gZAYiBC+B;kBACfCyE;gDAKKD2B;AAAaEuC;gYAahB5Se;mCACSr9E6D;qDAGFAkE;8YASH1lEAnDiqBuC0lEuC,A;2GmD/pBjBlwDyD;mGAEpBxVAnD6pBqC0lEiE,A;2OmDtpB3Cq9E8B;ihBA8BG6S2C;iGAIPx1CQ;0PAMIq1Ce;4JAIAE2B;yJAaEEsB;meAgBFFqC;oHAMGA8C;AACH5S2B;8+BAe0C0SkB;kDAIjC/vFS;AADT+vF4B;8RAQAEqC;wBACAGmG;sEAKEHuC;2NAWFAqC;qMAOCAqC;m8CAsB0BjwFwB;4JAAAAmC;iOAQAA6C;qFAK1BiwF2B;u/EnD4D0BngJkB;gvBA8CzB8WeA8XsB9W+D,+GAEpBxVAAOuC0lEqE,A,6H;43BF34BvC1lEAE24BuC0lE+C,A;OF14BnCqoFuB;uFACkBv4IyD;mGAEpBxVAEu4BqC0lEiE,A;qWFx3BnCqoFuB;+cAWAAuB;oYA4FPtmC4B;8BACE4mC2B;AAA6B0H4D;0JAI7BrSyB;kBAAgB7csCAbhBmvB6C,A;wLAkBE3HqB;wkBAyHe74I2C;wNAUAkwDwBAhEDlwDgB,qE;oBAiENuwHsH;6PAYOrgEwBA7EDlwDgB,iC;oBA8ENygJkJ;uKAKOvwFAAnFDlwDsB,kD;gGAwFN60F6E;gBAAAAyC;qKAKO3kCAA7FDlwDsB,kD;yGAiGN+9F4E;gBAAAAyC;sFA+CTs6CoB;qBACMAyB;8OAOVGe;sNAQiBCqF;0KAOZJuB;0UAULGe;oaAeiBCqF;gLAOZJuB;yQAWDAoB;2mBA2EAAgD;4QASNDoBAzKMC2B,+D;yOA+KAAoB;yGAIRDoBAnLQCyB,2D;sNAwLAAoB;8CAGRqIAA/KA1HoBANQXyB,mB,AAMYnoFK,AAApB8oFiE,A;kTAoLQXgD;iFAgBRCoBArOOC2B,mB;2QA6OKI2B;AAERLoBA/OGC+B,uB;8XA6PCFoB;AAERCoBA/POC2B,mB;umBAwIWoIsB;AAIdCiBAvIGDwB,mB;8PA+IWAsB;0iCA+KK1Vc;sCACAiD2B;qEAGEvE4BAxeRkXyC,mBAAVhIsB,AAAUgIgG,A;8JA0ewBjIiBA/TlCD0B,mD;iOAgUiCCiBAhUjCD0B,E;kDAgUiCC+C;AAEH1oFE;mOAMmBmoF4C;AAC3BM6B;iCACqBCiBA1U3CD2D,E;kDA0U2CCoC;iyBAiBnBh4BoB;wBAAAAAA9hBOkgCkBAxB/B7V4B,A,Y;0BAsjBwBrqBAA9hBxBi4B2B,AAA+BiIwG,A;qHAgiBH5wFE;8UAOI0oFiBApWhCDwB,+E;6FAsWctnBkBA9iBd6cqC,AACAsSiD,A;+VAkjBsB5HiBA3WtBDuD,qC;0IA4WiCCiBA5WjCD0B,E;oCA4WiCC+C;AAEH1oFE;ohBK+RXA6CL/vBHlwD4C,A;iPKogCCkwD6CLpgCDlwDgB,A;sBKogCCkwDmE;kPA6BAA6CLjiCDlwDgB,A;sBKiiCCkwD+D;4aA+FAAwBLhoCDlwDgB,sE;u1BKuBTkwDa;qDAAAAAEsR4Cg/BAXqF5Bh/B2B,yBAAAA8B,A,I;yxHUxFvB6wF2B;UACFX4B;8WASEWqC;AACFXwC;6CACclwFU;2DAAAA0C;oQAI4BAU;mCAAAA2C;+JAQxC8tDqC;AACHoiC8B;qVAaA7Se;mCACSr9EkD;qDAGFA0D;qNAKN8wFe;0GACuBl1DoBNxVuB9rFgD,AAArD8rFAAAAAmC,A,A;oDM0VU57BmCAyXJAAArDsBAoBNhqBHlwD8C,A,2M,AMmtBzBkwDAAAAAAAGiBu9EAA3bbzvBe,mG,oB,A,K;8DAiEM9tDkF;oJAiBQ+wFmD;AAAuC/wFeN7WhClwD8C,A;mJMqXlBghJsB;iNAQAAsB;iFACGx2JAJsUuC0lEuC,A;eIrUjBlwDyD;mGAEpBxVAJmUqC0lEiE,A;uOI9S3Cq9Ee;slBAqBAvvBe;qIAG6B9tD+D;iIAK7B8tDe;gJAG6B9tD6C;2FAM1BkwF2B;yLAIPx1CqD;uRAOKm2C4B;0FAGyC7wFAAwK1CAAC/uBkB2oFAAAA74IwD,A,A,6GAgBxBkwDsF,A;0QD+jBI04D+D;6bAsBEw3B4B;wdAkBelwFyBN1fIlwDoD,A;wgBMkhBnBogJ4B;wFAEF9hCiB;gOAME8hC4B;wFAEFx3BkB;wgBAzBuC2vBuB;qpBAoDXroF8D;uGAIAA6C;6gBAyCAg1CgC;unHC7pB1B+7Ce;oNAMgC9wB2B;2OAKhC8wBe;86BA2DDCsC;mKAGgBAc;0NAKjB/wB2B;ySAqBMgxBqC;AACJFe;+HAIc/wF2F;4EAKd+wFe;2IAIc/wF6C;qFAKVixFqC;AACJFe;gQAcGGyB;2DAICAyB;2DAIDH2B;sQAeoB/wF+C;qFAGtBmxFe;gWAWGJ2B;oBACACsB;qBACAIsC;AACcFoB;2VAQdH2B;oBACACsB;qBACAIsC;AACcFe;qhBAmCdH2B;oBACACsB;qBACAI4B;4bA6BAAsC;AACcFoB;kRAkBdEsC;AACJDyC;8WASEJiB;8FAIiBGwC;sRAWnBCe;mtBAzGEJe;2sBAqCCMe;q0HA6QHpgCuB;yEAEAqgCe;mhCA2CIrgCoC;qXAsCJsgC4B;6iBAiBAhUe;6+BAiTOv9EoCA3UwClwDwB,iDAArDkwDAAAAAwB,A,A;mgHNgIuBAyB;8rYA4PPAoB;kIAEdwxF0F;mhDA6K2BxxFyB;qdAqBzBoqC2F;2cAYAA2F;giBAYAA2F;m3EAgFF8+CyB;6iDSvyCWlpFyC;6OAAAAkC;iNAU0ByxFa;gJAGHAa;wiKAuL7BAiE;kiBAuGqBCyD;+nBAiEf1xFa;uEAAAA2C;+1BAg1BWA8C;qEAAAA6B;+CASXAwE;oDAAAA+CA2XbAAAAAAqD,A,A;u5BAjWeyvF8C;2jDAiEXvmF4E;y1DA4F4BlJqG;w9EwGj8CJk3DI;wiBJkCAl3D4C;+DAAAA2B;yBAAAAqC;6rBA2IUA4E;WAAAA4E;0kE9F9JhC+uCqC;AACAAA/BohBJg7C8B,A;A+BnhBIh7C4B;+lFAiVF/uCkD;4FAAAAmE;8GCyMwBA+H;k2BA+Bf2xFkN;m8CA0KSC0gB;qXAmGpBCoG;yrBkGjvBE7xFyE;WAAAA6E;gsCAmOgBk8E0B;wpBA2D2BA6B;AAE7Cl9CuG;gGAAAlvFsC;4MAKEkwDyE;WAAAA6E;iMAYoCAgD;WAAAA+B;oNAuBtCg/BoH;0DAAAlvF8B;sIAKAkvF8F;gEAAAlvFmC;6JAyBAkvF8F;kEAAAlvFmC;2EAuBiBkvFsH;wGAIPlvFqB;2CAIOkvFsI;qHAMHlvFoC;wXjG5XVgiJmB;gUAWYA+B;gRAMZA6B;wDACO9xF+B;0DAwCP8xF6B;yOAaCAyD;qNAoBDA6B;0jBA+BGA4B;4HAQCA4B;sSASJA6B;+XAiBFn8BkD;yiBAyCam8B6B;qTASAA+B;wHAEc9yDAtBiQCh/BwC,yBAAAA4C,A;0LwHpjBGimEmC;4+CjGyEpB8rB6Q;+sBAqBmB7V6F;0TAQfl8E6C;4FAEX23EAlC+aW9lEM,AAAjBk4EkG,A;kQkCja6B7NiB;uWASvBntC6BlCmZNg7C6B,A;sDkC/YyC3tDoB;w5BkGrBb+Z0B;kBAAAAkB;6kB1FlED67CwC;0pBA0DdlvJgF;0mHAiLFk9DgD;0BAKGAiD;6GADHAuC;AACGA0D;+IAIPo8BkB;2LAkFH25B+B;4jEAsEE4hBA1C+FW9lE2E,A;wiEAnNCmiDe;mPoC2MKssB0C;sBACDx/B2C;sBACAkCyC;sBACAyT6C;sBACE3f+C;sBACA9F8C;wBACC4vBmI;6NtBrWiB5RU;oQAyCtCAkB;iCACSijCAAiCmBCoC,A;oCA/BG1tCuD;4BACA4KsD;yFAG1BgXoD;0qPdxJP+rByR;qCAGKC4I;uTAQLC0FAYaryFmC,4H;ycM2E0BAyD;cAAAAwC;oZAwJnBA8B;gpCA8IfA6D;cAAAA4C;qvDN9buBqpF4C;wiBAkVlBv0BsCwIjTKw9B2E,yE;QxIiTLx9B6B;0LwCqPe90DwC;62HC4sCXwiEc;0PAQYsnB+E;+DAIYtrCsC;4HAkB5BqrCoD;wfAaIz4BA7Bx8CM5SkF,A;0I6B88CFwbA9BxnDTh6DyB,A;oE8BwnDSg6DqC;4jGAiuBHgE2BA+CWxf+B,A;mEA7CN8SgD;yTAcHA+B;AAAuC1M6F;2UAiB9CilC0F;suBAsCRjiDe;uKAIAykBkB;gKAIQkmC4F;4DACgCCSAIxChwB0D,yPAUJpL8B,AADIxS6I,A;wJA2Da6tCyEAObjwByC,0EAIFkwBsLA1BA3jD8E,A,8L;0UAsCEyzByD;SACAockD;oNAIAjEkE;2LAEA5pB6E;yiFAqsBQ/wD4C;y4FA8xBD2yFkF;kzEA4FN5hCgD;AACE/wDY;AADF+wDiB;k5BA2CeKA7B/8HE5S4D,A;mJ6Bq9HWsrCmE;gJAIOtrCsC;iaAmB5BqrC+D;0vBAoBJv4BmB;8CACAkRmB;+BACIlRqB;2FAGQ0M8C;uNAUTh+DiB;sVAcHg+D+C;uCACE2cyB;4FAIC36EiB;2OAUD+wD+C;AAIC/wDS;gVAYH4kDwF;2DAIC5kDiB;kPAUAg+DsF;AAAqBwEkC;yIAUrBxiEiB;k6BA4D4C4kDkC;AAAnB0MyF;8DAmB3BtxDmC;s4BAuBUuyF4F;qEACgCCsKAUrCte6E,A;siBAmBH1RkB;mHAEA0RgI;AACAyGuB;uDANGkP0C;AAOH94BU;y5EI89eO6hCA6F3koBX9pHADgBDk3BsC,AAAAl3BwB,A,A;kgD5F80lCA+pHgC;6LA4BAAgC;uMAYAA+B;AAActV2B;4LAMMA2B;qQAOtBljBsG;89B6Ft1lCOxwFADjDuBmqFQ,A;yNCqE5B6lBuG;8GAIS7iB0E;6BAAAAgB;4FAGXOqD;6LAckDP0E;uNAQvCA0E;6BAAAAgB;4FAGXOqD;+WAeFA4D;+oCAsESptFwCD9LA2oHArG2VXp3DApC/IAAuF,A,mBoC+IAAApC/IAAuH,A,A,A;O0IdWvxDAD9LA2oHsC,A;wPC0MLCoG;8CAIS/7B0E;iCAAAAgB;sKAIXOqD;8NAQwDP0E;sNAOxDOqD;qjHlFhOG3C0CANuBjtBqBzCDE0gDuB,A,A;2qDmDyDf1gDOnDzDe0gDuB,A;wRmDmCb1gDOnDnCa0gDuB,A;wgBmD+Cb1gDOnD/Ca0gDuB,A;0hB6HiCsBpoFA3H6LzC27BwBFnCwC9rFgD,AAArD8rFAAAAA6C,A,A,A;glEgIlJco3DgC;yEAGZCwK;kuBAqDmBx1DA1H2VOz9BE,A;oD0H3VPy9BoB1H2VOz9BiC,A;i5F8CtQM6pDS;sRAKbAK;4qDAjB8BuVa;uBAAAA4G;0DAAAA0I;0S6EhC7Bp/DAAugBH+qFAAAA/qFA/HmGQAAFjvBvBAAAtB0B05BAAAA15BoBA4MLlwDgB,mC,A,A,A,A,A,A;oBiI/CHkwDmBAugBH+qFAAAA/qFA/HmGQA6D,A,A,yC;uN+H/WJoxDuC;AACD0oB2L;gBAAAAuB;kHAQlBqZiD;wIAaAnzFS;4CAAAAqC;6OAYWAAC3afAAAAAAsG,A,A;mDD2aeAwE;wpBAsDbs6CkE;+EAmBOt6CqC;qLAQWw+C+B;4HAIlBlEiE;iVA5DsBt6CkB;+BAAAAoC;2NAEAuiBAyCtZpBviByB,A;yOzCyZEozFmD;yMAmNOhiCAnB7mBW5S+C,A;6ImBknBKx+CiC;qTAyLhBw+CyD;yFAEPs2B2BDpyBQkekC,8FAGZKyNAoF4B51DA1HiTFz9B4B,oBAAAA6C,A,sE,A;mK2HoaxBg/BAnBz0BwBh/BkH,A;8BmBy0BxBlwDkD;gLAMsC2tFA3H1adz9BoC,4BAAAAiD,A;+c6HxXGgcAjIouBChcAF1xB5BAAAjC0B05BAAAA15BoBA4MLlwDgD,A,A,A,I,A;60CmIvDM2tFA7H0THz9B4B,oBAAAAkC,A;gxC4H7apBAuJ;irOIlBqCA0N;+BAAAAoB;8PAMjBmd0B;AAAEndkB;gCACtBAuC;6EAYWAgB;mtBC5BfAuC;qyDG4BKA2C;oLAUAAmB;yLAUAAoB;oRAcIAc;oZAWAAwB;2/BCtBE81EACtBIhoCkC,A;ADuBR9tCa;AADI81EwB;kDACkDrPA5GnDnCzmEiC,A;0b4GkEjBszFAAsBU7sBA5GxF+B34BsC,A,6B;O4GkEzCwlDAAwBJtzFa,6BAFcymEA5GxFOzmEiC,A,A;oC4GoEjBuzFAA6BU9sBA5GjG+B34BsC,A,6B;O4GoEzCylDAA+BJvzFa,8BAFcymEA5GjGOzmEiC,A,A;6B4GsEjBwzF2HAmC4CvpD4C,AAAhDjqCE,AAAgDiqC6B,A;+BAnC5CupDAAmC4CvpDe,A;oGA1BlCw8BA5G/E+B34B2C,A;A4GgFpDoFAClCI4iC6C,AAAQzjEoE,4D;ODmCLrSkB;cAFcymEA5G/EOzmEiC,A;4H4G+GrBqrC0B;oDAAAA+G;kPAYAA0B;yCAAAA+G;+8CIlIuCrMgB;miJ7C6L1B4yDwkB;sjEzCxJNjgD+G;sDAAAAA0D4XZ3xC2F,A;gI1DhWFg/Bc;6CAAAAiE;+CAAAlvF8B;oqFuFsO4B2jJsB;wDAEKAsC;OAAjBzzFoB;AAAiByzFwC;YAAjBzzF+B;yO5CtP+Bs6CiC;qPAgQ7CAuB;2JxBjTmB4hCiB;+DAIF9/CkB;sLAyBjBkeuD;gjByBPSt6CyC;AACX+uCApHkhBAg7CoC,A;+doHpgBIh7CApHogBJg7CoB,A;4CoHpgBIh7CApHogBJg7C+H,A;qGoHhgBIh7CApHggBJg7CiI,A;klBoHnfIh7CyBpHmfJg7C6G,A;AoH9e+B3tDqC;AAAxBke0D;67FAwFat6CsCzB3JIitFAAAAjtFiC,A,A;6wEyB6MNAAzB7MMitFAAAAjtFmC,A,A;2ByBkNtBs6CAzBjMFvLA3FgiBAg7C6B,A,A;AoHpWkB/pFiC;sCAOXs6C2C;gDAGGleAzB3MSAoB,A;2eyBsNTg1BAxGqMY5S0C,A;oDwGpMV4SAxGoMU5SsC,A;qOwG3LtBm1C8L;6fAoBWn1CoC;AAA+B09BKzBxPrBAqD,A;AyByPnB5hCoBzBhPFvLA3FgiBAg7CkB,A,A;oBoHhTEzvCAzBhPFvLA3FgiBAg7CiC,A,A;qEoH9SEzvCAzBlPFvLA3FgiBAg7CgC,A,A;s0BgKjiBsBzvCoC;urBzCNFt6CsC5BVIitFAAAAjtFiC,A,A;ygC4ByClBg6DA5GoNKh6D0D,O;iD4GpNLg6DA5GoNKh6D4C,A;0B4GhNL4zFuE;8qBAwBA55BA5GwLKh6D0D,O;kD4GxLLg6DA5GwLKh6D4C,A;0B4GpLL4zFuE;0GAMA55BA5G8KKh6DyB,A;gE4G9KLg6DoC;uGAAuC45BkF;iEAGIA2F;qBAA5B9tD6D;i1BAxCN8tDgD;wcA4BAAgD;yJ2CMKp7GAAiBpB4jDuC,A;mEAjBoB5jDAAiBpB4jD2B,qDAAK0JkE,A;AAhBEwU0D;k5C7CFczIkD;AAAsB2qBkC;6CAI/B1sH0B;wCAAAA6D;gaA6IGqsFA1GAJn8B2B,kC;2b0GsBMm8BO;uCAAjB6CgC5H8K8Bh/B+E,A;2G4H9K9BlwD+B;AACM0sHyE;AAGWrrD4G;+RASJ0gCyC;AACuB2qBmE;AAGhCztBgD;2PAKeotCgE;8IAiCNhrEiF;4DAESgrBA1G/EXn8BsC,A;iB0G+EiBgtDiB;AAAN7wBA1G/EXn8B8C,O;2C0G+EiBgtD6C;oPAqCf77CgE;gYAwBHy9CoE;mIAhBWqVAzGuBQjkE+B,A;AyGFKk8E8D;yEACjBttB2D;w8BA2EGtMAAzQWzQuD,A;kEA2QT/hGuF;kDAGlBwyGAA9Q2BzQgD,A;AA8QFAmC;sCAMzByQAApR2BzQkC,A;AAoRF2qBmC;wCAMzBlaAA1R2BzQkC,A;AA0RFAmC;kGAIZ1gC4D;gCACAA4D;oEAEIigDA1GkHC5Se,A;ue0GnGE4SA1GmGF5SiB,A;kE0GlGD4SA1GkGC5SmB,A;8nB0GvFD4SA1GuFC5Se,A;onB0G9EDAe;slBA4CE3M+N;AACDA0D;2qCA8BjByQAAhZ0BzQoB,+C;qmMAgzB3ByQAAhzB2BzQsD,A;mEAmzBO/hG4B;+DAAAAmB;8aAuCjBu1CyD;k3C8C19BNqXuC;2erE8BP00DAnFqfc5SuB,A;gTmFlfT4SAnFkfS5SwB,A;wNmF9eP4SAnF8eO5Se,A;0kBmFleL4SAnFkeK5SqB,A;uQmFtdjB3MuB;sHAKQ2MsB;AAAY3MuB;oLAUrBAa;mEAAuBufAnFucL5SiB,A;wQmF7bb1YK;yXASPiJgB;qGACAAgB;oBAEFAU;umDsEpHalYyD;0QAOI2nBuB;u4IEyCU1YyD;OAAhBjPyD;oNAUmBsFA3JoInBn8BgC,A;4D2JpImBm8BkC;qYAkBXqiB8D;6HAOK1YuD;kCAAKAoD;6vC/G1BzBu3CiBAjC0BzoB2BC7BFjtBOzCDE0gDuB,A,A,A;gOwCqEdpoFAtCyJL27BoBFnCwC9rFqD,AAArD8rFAAAAAoB,A,A,A;AwCtHqCzeoC;0EACJi0CmC;2EAGbpxDAtC2qBOAAFjvBvBAAAtB0B05BAAAA15BoBA4MLlwDiE,A,A,A,A,A;gCwC/GrBwqGkD;AADgBt6CAtC2qBOA2E,A;+vFsCngBDoxDiC;2HAGbisBiBAtNmBzoB2BC7BFjtBOzCDE0gD2B,A,A,A;+LwCyPZv4IoC;gCAEhBwqGkD;oYAgBYt+BAtC6hBgBhcAF1xB5BAAAjC0B05BAAAA15BoBA4MLlwD4D,A,A,A,A,A;6BwCmFvBwqGkD;AADct+BAtC6hBgBhcqE,A;iLsCphBNw+C6B;AACtBnc8D;AAEAwxD0J;8LAzE8Cn6DgC;kCAI9B15BE;iCAAAAAWpND+qFAAAA/qFAjDsvBQAsBFjvBvBAAAtB0B05BAAAA15BeA4MLlwDkF,A,A,A,A,A,A,AmDpKTq7ImF,A;AX8LVnsDY;2DAAAAqC;yCAAAlvF+B;oSAQmB4pFO;6WA2CoCvc6B;ihBAwD3D22E6DA3FwB1iCiC,8BAEQj0C2F,AAG1BkgEiBA1MwBzoB2BC7BFjtBOzCDE0gDqC,A,A,A,uC;mhC0CsCL5+CyB;yBAAAA+B;iQAIjBAoB;qEAJiBAmC;0RASgC6zCiB;sKAClB1uB8B;iCAC1BnlBuD;AAXYAuC;mhBAoBdzpCmC;wxH4BqEmBmgEmH;2RAE5BpxBY;uCASFAiB;2RAYE6rBY;yGAAAA+C;2nCA8DS56DiEuF5JbAqD,A;gnCvFuQmBqqFAtCrSKpmBAnC6TOjkEwC,A,AmC7TpBs8BAA7BcguD8C,A,sBA6BdhuD6EAaeiuDoB,8B,AAF1BjuD+C,A;kJsCmSsBt8BwG;sEAGHu1CgD;uKAAAA8D;iEAEAiJ+B;4BACGx+CqD;sSAqBR+zF4C;kDACc7hD0D;iCACNlyCqF;AAEJ+zFkE;+MAKY7hD4D;mEACb6hD+C;oDACa7hD4D;mEACX6hDiD;oDACW7hD4D;iCACNlyCkG;AAEH+zFsE;2LAML/zFyG;6GAKDw+CuB;4BACGx+C6C;+HA4EVAgH;2zDAmDSi/B2KuFtcjBj/B4C,A;kCvFwciBA2DuFxcjBA+C,A;oTvF8c6BmgE4E;AAAfngEmB;AAAA+uCuC;iCAAAAS;4BAAAAS;uBAAAAS;wBAAAAS;imBAoDSoxBgD;oRAiBAAqD;y7CA4CrBpxBwB;AACAAc;wxDtCtjBoBmtC+B;siEAiEAA+B;otBA8BD94B8C;2NAQN84BiC;kiCAwFIz7BuE;KAAAAoB;iTAYXy7BmD;AAGqB94B2E;4HAEjB3C8F;kHAKiB2C+C;AAGR84B4C;wIAOZz7BqF;uYA2CoBkvBW;uIAKvBAgB;AAAmBAU;4MAWnBAa;cAAAAW;KAAmBAe;6iBoDlME/uFCsEzDDozGyC,A;0mBtE4EACqB;8sBAWTz1CuC;yQAQWteiD;+OAGNAyE;0BAEKr/CCsE1GHmzGoC,A;AtE4Gf53DkB;ytEA+DP4CA1GtQ8Bh/B2H,A;0D0GsQ9BlwD8B;snDAmEAkvFA1GzU8Bh/B2H,A;iC0G2URi0Fa;mCAFtBnkJ8B;iSAYsBm0HAvFEOjkEkC,A;AuFF7Bg/BA0B9T0Bh/BqH,A;uE1B8T1BlwD8B;gGAII6nIAnGqMa9lEiE,A;khBmG9KKoyDAvFzBOjkEsC,A;AuFyB7Bg/BA0BzV0Bh/B4G,A;gC1ByV1BlwDsC;sGAQsBm0HAvFjCOjkEsC,A;AuFiC7Bg/BA0BjW0Bh/BiG,A;mC1BiW1BlwD8B;6QAWoBi/F6C;kVA3KFntDa;4EAAAAAuEvNlBoyGgD,A;AvEwNIjlDAnGgUJg7C6B,A;iXmGrSwBloGiBsE/MMmyGoC,A;6CtEgNNlyGCsE5NOkyG0C,A;2BtE6N3BjlDAnGmSJg7C2B,A;iZmG9QwB/nGa;4EAAAAAsE5OKgyGqC,A;AtE6OzBjlDAnG6QJg7C6B,A;8ImGvPkBnoGa;4EAAAAAuEjSlBoyGiD,A;AvEkSIjlDAnGsPJg7C6B,A;+ImG5OsB/nGa;4EAAAAAsE9QOgyGqC,A;AtE+Q3BjlDAnG2OFg7C6B,A;iNmG3NsB7nGiBsE7QW8xGuC,A;6CtE8QXlyGCsEtSSkyG0C,A;qBtEuS7BjlDAnGyNFg7C2B,A;0bmGhL6B/nG8BsE1UAgyGsC,A;6tB9FwBP7zByF;qCAAsBhhBkB;aAAAA0G;6WgGpExCwwBW;gYAmBFAW;2IAGgBAiB;oDAEIxPa;qGAAsBhhBAA7B/BwwB6C,oEACKp1CwB,oD;4CA4B0B4kBAA5BdtgB8B,A;qqClFY1B5C8B;mCAAqBNyB;uDACSAiC;m3BoFkBSwImE;gGAI5BqayD;qXAUJx+CA1EHGk0FglB,kI;O0EGHl0FA1EEAmd0JA3BOg3EAAAAn0FwB,A,A,A;gf0EiCImgEoD;sZnHgJlBnGA/CiDOh6DsH,O;kH+ChDUm8B+E;+CAcFqiBkE;AAAwB4SgD;OAC9BpxDqC;8GAGFAkE;qHAOUAqC;AAAM2xCA/CNhB3xC0D,O;gC+CMgB2xCA/CNhB3xCsD,A;A+CMUAACPFA8B,A;+IDmBZg6DA/CWIh6DqD,O;6B+CnBGg6DA/CmBHh6DkD,O;kC+CnBGg6DA/CmBHh6DyC,A;iE+CXJg6DA/CWIh6D4C,A;+d+CjKFlwDiE;oSA2CgBowFgC;kBAAAA+C;mGADPlgCuDCyFCA0B,A;ADvFgBo8B6C;2DACM8DgF;OAA5BlgCsD;iUA4BoCsVYCpCrBtVyB,uCAAAAAA8FTA+B,A,A;klBDfAw+CuB;ihBA2BJwbA/CkBJh6DkD,O;mC+ClBIg6DA/CkBJh6DyC,A;wc+CVIg6DA/CUJh6DqD,O;8C+CVIg6DA/CUJh6D4C,A;ghB6GtKJmkCgC;+jCAoCUnkCY;yJAIiBAoBChIhB6gCiD,A;kBDoID+tBApH2DchhHgE,A;6EoH3DTk4F2D;AACbA+E;AAEe8oBApHwDOhhHiD,A;wCoHtDPghHApHsDOhhHiD,A;mKoHjDhBoyDgC;8TAMmBAoBCpJhB6gC8C,A;kFD2KV+tBApHoBuBhhH+E,A;eoHpBvBghHApHoBuBhhHW,A;mEoHdhBk4FmE;AACAA0E;qBACAA8D;yBAKY8oBApHOIhhH4C,A;gXoHpCZghHApHoCYhhHoE,A;sIoH/BZoyDY;2JAIoBAoBCpKrB6gCkD,A;4BDsKqB+tBApHyBRhhHgE,A;mDoHzBgCghHApHyBhChhHiD,A;qDoHxBXghHApHwBWhhHiD,A;eoHzBdoyDoB;yUAkCiBAoBCxMhB6gCiD,A;kBD2MY+tBApHZChhHgE,A;0EoHevBghHApHfuBhhH0C,A;eoHevBghHApHfuBhhHW,A;0BoHkBUghHApHlBVhhH4C,A;8WoH4BhBghHApH5BgBhhHiD,A;eoH4BhBghHApH5BgBhhHW,A;gEoH8BvBghHApH9BuBhhHiD,A;QoH+BhBoyDO;AADP4uDApH9BuBhhHW,A;2hBoHsDjBghHApHtDiBhhHgE,A;eoHsDjBghHApHtDiBhhH4C,A;AoHuDjBymJA/EiDShKAAi9FDrqFyC,2KAeHk8E6D,+FASF9/CoB,AAAFjfqE,A,gC;oE+ErhGsB93B+B;AAAzB4/DiB;AAAWqLiB;AAAcjrEAF8JlBAE,qBAAAA6E,A;AE3JJupEApH/DgBhhHiD,A;eoH+DhBghHApH/DgBhhHW,A;iEoHgEdghHApHhEchhHiD,A;eoHgEdghHApHhEchhHW,A;mEoHiESghHApHjEThhHiD,A;eoHiEhBoyDqC;4ZnB7OTAgB;8IACeAgB;inC5BDfAgB;2kC2BuE2BAqC;sEACpBAgB;gFAOAAgC;iCAHGAgB;uPAWCs0FyBA1EQxkJyB,4D;wDA2Edo+IoC;SAAAAqB;0GAAAAAA+ELluFiD,A;gZAvEWs0FyBAnFQxkJyB,4D;iEAoFdo+IoC;SAAAAqB;oHAAAAAAsELluFyD,A;8YA5DWs0FyBA9FQxkJyB,4D;2IAgGdo+IoC;SAAAAqB;sHAAAAAA0DLluFiE,A;icApBFs0FYAtIqBxkJyB,4D;iGA0IVo+IwEAgBTluFqD,A;kHAdmDkuF4E;4BAAAAAAcnDluFkE,A;iGAV0BAgD;stBAuCrBAwB;wzFAKEAqC;AAAYkgC4F;AAAZlgCAzCIMA8B,A;wQyC4BRAW;4CAAAA6C;qVzCgCcihEc;uCAAAAAhDmOKjhEkF,A;AgDnO9Bg/BAlEnQ8Bh/BuF,A;mCkEmQ9BlwD0F;0GAGuB0uGwC;8GAENx+CY;+EAKHg6DAhDxCHh6DgD,kC;wRgDmDAAqC;AAAgBihEAhD8MGjhEsC,gCAAAAmD,A;AgD9MnBAAAjFQA4B,A;SAiFiCo8Bc;+IAU7C49BAhD7DIh6DqD,O;6BgD0DPg6DAhD1DOh6DkD,O;kCgD0DPg6DAhD1DOh6DyC,A;iEgD6DJg6DAhD7DIh6D4C,A;kTgD9KckgCgC;kBAAAA+C;qCAAZlgCuDAgJMA0B,A;AA/IGo8Bc;i+EAwNPp8BE;gDADS8lCsD;yuCPnSgBrIA/Bgddz9BE,A;oD+Bhdcy9BoB/Bgddz9BgC,A;6M+B3blBAuCAgDau0FAAAAv0FAnCmsBIAsBFjvBvBAAAtB0B05BAAAA15BeA4MLlwDyF,A,A,A,A,A,A,yC;opDqCtGnB2kJyC;6JAKJn6CmE;6OAMIm6CyC;+ZAcFl5CK;OAAAAuD;0KAYFRK;OAAAA2B;wYAMI05CyC;yHAG6Bx0FAnC6FtB27BoBFnCwC9rF6C,AAArD8rFAAAAAmC,A,A,A;yBqCxDkC5fAnCqqBFhc0BF1xB5BAAAjC0B05BAAAA15BeA4MLlwDkF,A,A,A,A,A;kXqC3CnB2kJyC;6HAIgB5qCsB;wJAKM9OK;OAAAA2C;YAGnB8OsB;8JASaliBOrCnKU0gDuB,A;iCqCqKzBoM+B;i9BH9DWj+BO;AAAM/4B6CG3HkBAA/Bgddz9B4B,oBAAAAiC,A,A;gK4BjVQy9BiBG/HMAA/Bgddz9BK,A,A;wD4BjVQy9BAG/HMAoB/Bgddz9BiC,A,A;mG4BvTGw2DO;AAAM4oB4B;qdAyBsBp/EA2FrJLCA3HqNzC27BoBFnCwC9rFgD,AAArD8rFAAAAAmC,A,A,A,A;OkC7B0BzegC;AAAwBndmD;AAASA2D;AAAjCmdgC;ohBAgBPsgB6CGlMuBAA/Bgddz9B4B,oBAAAAiC,A,A;6K4B1QKuwDwB;AAAQ9yB0B;AADjBtgBE;AACiBsgBiB;uCAAAAAGtMCAA/Bgddz9B4B,oBAAAAoC,A,A;A4B1QwCo/EQ;AAD5CjiEuC;6RASLiiEO;kGAMVAgB;ykBAaYAO;2/BAlFEAgB;uEAMAAuB;82DH7EgBtxCkC;uTAURA4B;orB6GdjBAkC;gpBAkEIhI8D;AAAWAiF;AAI3BzzBkEA2DmCy7BiC,A;uNA5CQAwC;moDrE1JjCxhDACiCsBx8C6I,2K;ygBD/BhCy8CAC6CkCz8CkJ,8M;uWmC9BFkqFiB;kEAA2BwIA7E4+nBzC91CA6Fp+nBbDADcDuT4C,4D,A,qB;oSfnBwByoD6C;sFAAAA6F;AAIjB+NO;AAAM/4B6CtEvBuBAA/Bgddz9B4B,oBAAAAiC,A,A;mSqG5bbw2DO;AAAM4oBgB;AAAiB58CA7Ew+nBlB91CA6Fp+nBbDADcDuT4C,4D,A,A;m0CxCoGmB20FwB;AAAV30FkF;kGAAAAyC;i3BAoDmB20FwB;AAARx3EgGAzJUowEyC,AAGGCyC,AAGACyC,AAGtBCgC,AAUiBC+E,AASLC2C,AAMIC2C,8EAzBhBHAAAA1tF2E,A,A;AAkJf8wCqB;mDAAAA0G;iFASqB8jDAA/HQxjCAtFqfP5Se,A,A;oVsFvURwbAtFCHh6DyD,O;sCsFDGg6DAtFCHh6DgD,A;qsDsFmD6Bw+Ce;mDAGpCm2CwB;AADG30FiE;OAAAAoB;wnCA3JLg/BAxG/H4Bh/BsI,A;8YwGiIhBlwD2G;AAAA+5FmEnB0BV8eAA3FaqkCkI,A,gLA8FNvuBwB,AAAA3uHyH,mI;gLmB7BG+5FAnB6BH/5FmE,A;uTmBxBSAmD;4CAAAACnB5BRA0B,c;ghDmB2HN8kJqB;SAAAAAA/KuBxjCAtFqfP5S4D,A,A;AsFrUVx+CgB;mnBAuDOlwD2D;4CAAAACnBnLPA0B,c;w9DjBhFC0uGsB;QAAmB4SAlDihBV5SuB,A;uPkD1ffwbAlDoLIh6DoH,O;sFkDnLNm8BkE;4CACA6wBwD;8yBiB7BiB7vCAAkDEmxEAAAAtuFA7D4qBCA2BFjvBvBAAAtB0B05BAAAA15BeA4MLlwDwE,A,A,A,A,A,A,4B;W+DnKDqtEAAmCH43EAAAA/0FoB,A,AAgCmBg1F8C,AAOpBCAAAAj1FgB,A,AAyCWwtF6D,AAGE0HuD,AAEjC/3EAAAAAkJ,A,A;SAvHiBqfAAoBoBAU,A;0MAdlBrfqB;qWAkDErtE6B;sQAgGf64GAA/GaqkCmBAdQl9I6B,wB,kBAcuB63FO/DhElB0gDuB,A,A;+S+D8MhBroFAA2NG+qFAAAA/qFA7D2UQAAFjvBvBAAAtB0B05BAAAA15BoBA4MLlwD2C,A,A,A,A,A,A,8B+DgPNi7IAAAA/qFA7D2UQAwF,A,A,A;yoB6DzgBrBw8B+B;kCAAS6YAmGlNQoxB6B,uC;0GnGsNPjqC+B;kCAAS7uFM;kkBAkEJ6uF8C;kCAASiqC2C;AAAMx/BwFoG3TyBgJiE,2E;gUpGsUtDzT+B;gDAAS7uFM;SAAc0yFsC;yOAMP+wBAnEyOC5SyB,A;uDmEvOpBmXmD;8CASEn5B+B;kCAAStB6B;udAcqBl7BAA8EjB+qFAAAA/qFA7D2UQAAFjvBvBAAAtB0B05BAAAA15BAA4MLlwDyD,A,A,A,A,A,A,A;A+DkNd0sF+B;8FAhDyBx8BoBA8EjB+qFAAAA/qFA7D2UQAsBFjvBvBAAAtB0B05BAAAA15B+E,A,A,A,A,A,A;A+D8ZVryDM;SAAc0yF+C;++GAzJQ9wCAc7EnBi1D8B,A;Qd6EmBj1DAc7EnBi1D2F,qBACA4KqE,iDACK/FwI,2R;4fdoFlB7sB+B;kCAAS6YAmGlOIoxB6B,uC;iCnGmOC32HgB;AAASkwDuB;ueA8DhB06CkCAgIC/SO/D1bc0gDuB,A,uB;mH+D+V5B+Ma;kIAAAAwF;uoEAwBkCvyJgC;0+CAR5B64H6H;0SA0BmD25BI;MAAAAmCAeLxyJyC,A;mMA0BvC8kGO/Dlbe0gDuB,A;8L6DcViN6HA6ITrEmBAtE4B5T4B,A,qJ;SAvEnBiYAAoJb94DU,kCAASuoBAAvJyBAiB,A,A;uIA4GrCksCkCAlCmC5T4B,A;cAoCtBr9EqC;iNAWbixFmBA/CmC5T4B,A;wSAwDdvvBARxCFmiCqC,A;yCQ6ChBptJA5D+sCPqmJqB,A;yO4DtsCW+HmBAtE4B5T4B,A;2KA6EhC7gDU;kCAASuoBAAvJyBAiB,A;oGAiKrCksCkCAvFmC5T4B,A;YAuFjBt4BiB;wMAWfAiB;oTd2DFiVArEyJmC78C8D,A;AqExJnC6vCiB;AADAgNArEyJmC78CiD,O;qDqExJnC6vCiD;AAGWxOe;snGA+FJjeoG;AAAwCnE0C;8qBAmBK4yBkB;k5BAtIO7xCyD;oDACxCnb0BuF5ORhCaINmBA6B,A,A;4B3FkPXgCY;+mEA4HlBmbe;oiCkBvRFojBkF;0CACoBpjBuB;wdA/D2Bnb2D;oDAAAAAqEnBnChCaINmBAiC,A,A;azEyBgBgCU;krCAkD1BwmEsE;8pC3B5BNhhIA6B9BN0rDAGHKqiGuC,A,0GHGLriGO,gCAAAAAGHKqiG0F,A,6F;kjBhCqCNnkCA5BguCU5SoC,A;6YyJrwCGxJgC;eAAuBAgC;6MAKV5YK;qsBxF0CZp8BACtEFitFAAAAjtFuC,A,A;iCDsEEAuD;OAGYo8BAC7DnBAkB,A;wc3B8GgBp8BuB;mGACE4kC0E;iBAAR5kCc;AAAQ4kCAlDErBstDe,2C;0MkDDDjH4B;+MAQIrmDsD;UAAAAAlDPHstDoB,gE;20BkCqDNllCArCsZG6hCsC,A;4IqCjZIzyDqF;2VAGE49BArCmERh6DuD,O;kEqCnEQg6DArCmERh6D8C,A;6cqCzCKo8B2E;0YAYP27CiC4BzM8Bt6CARuFbz9B2B,oBAAAAgC,A,A;4EpB0HjBiiC2B4B3MsDxEARiFrCz9B2B,oBAAAAgC,A,A;sFpBoIjBkgD6B4BlNuDziBAR8EtCz9B2B,oBAAAAgC,A,A;+hBpB7DhBo/EgBCmC8B7uBS,AAAQ6uBgB,A;wSD3B9Cp/EAK3CUw1FgL,A;AL2CVxnDsC;+JAAAA+D;AAAAhuC8BKvCgBy1FsE,A;+jFL+DoBh4DACCQAAG9ENAoB/Bgddz9BkC,A,A,A;A2BnYRAAgGyBiCmdAARZw4EoC,AAKECqF,A,A;0WhGlB7B5e6T;qNAW+C6egC;ifAUjC/lJgF;2cAObghG8J;kHAG6B33BoC;+CAAAA4P;mHADxBnZuE;yCAFL8wCwG;sZA1BQ0lBO;AAAM4oB2B;gGAKCtvIoCG5ErBAyB,8B;sLH4EqBg2HyIGlDLkQsV2HKvB15BS,gBAAAAA5BEIw5CoE,2K,A,kO;iYlGwE6BCEA8CzB3WgBCnFgC7uBS,AAAQ6uBgB,A,mE;ADqCfjiE6B;YAAA44EqH;4vCAoG/Bh7CI;gpBAgB0BjrGoCKtNrBAyB,8C;gPLuNuBnCM;SAAcwyF8D;gjBAc1CwlBI;k3BG3NgB3lDA2H3BKg2FAAAAh2FA/BSTi2FAAAAj2FuE,A,A,A,A+BNOk2FAAAAl2FA5BMIo/EAAAAp/EmE,A,A,A,yC4BTFg2FAAAAh2F0D,A,AAGFk2FAAAAl2FmH,A,AAuBvBAAAAAAiDACaAAtF6BTAuE,A,A,A,A;oFrC3BiBi6BmC;iGiIxBGiiDa;oBAAAA4B;uEAGUl9CAvDiCNh/Ba,A;0DuDjCMg/BAvDiCNh/B+D,A;+ehDrCLlwD4BCwHTA0B,qB;ADxHS4rH4E;sGeuCjBgYuC;ga3B8B+BzzEAhDuKxB27BwBFnCwC9rF8C,AAArD8rFAAAAAiC,A,A,A;qhDkDrDa/uBeO7HF64DmC,A;2BP6HQoTaAUsB5LkC,A;AAVdnsCcAcgBmsCkC,A;AAdP57BaAkBK47B6B,A;AAlBGltEkB;AAAYq3CAAsB3Br3CgC,8J;oHAiCpB05B0C;mZAsCyB+DA5CyNNz9B2C,oBAAAAiC,A;qnD4CtKKq7CyI;ueAMepLmN;iGAKtB+cAtD+QX6hCAAIPsHuC,4tB,A;i9CsDnQMxhDiLa3RUx3BAAmEgB63E+C,AAgDTxH+B,AAGE0H8C,AAEjC/3EAAAAAAAGgBndAF3FYusFwF,AAuD0Bx+EqJ5EmT7Cw7EmH,A,A,yD8E/QOvpFAFxFGurFyY,A,A,A,A,A;q0CXmQMxwCiG;spEAcvBT4E;wOAQwBy9BAWnVet6CoBRuFbz9BgC,A,A;umCHoRUgxE+H;2hFA8GFmCiC;mCAAAAA2CtdK11CAxCoFbz9B2B,oBAAAAkD,A,A;oEHmY1Bs6CwE;AAA2Bw+BA2CpdD94E4B,iC;sB3Cqd1Bs6CwE;AAA4BvZA2CldD/gC4B,kC;qB3Cmd3Bs6CwE;AAA2BhJA2ChdDtxC4B,qB;iK3CwDbymE8C;+BAAax2BiD;k6GAwLpBmN4K;AAEAipByV;m3BA0FQ7nBiC;iBAA4B4SAxC66BpB5S6C,A;2BwC56BlBlEkD;qyBAwCqBpayD;oa2CzTZlgCK;mEAEI05BkD;oQAaY2jD4B;6GAIbniD0C;iBAAAAsC;yKAKP68CiChChG8Bt6CARuFbz9B2B,oBAAAAgC,A,A;gKwC2BI+kDAhCtGWAwB,A;wwDgCmH7BhKkH;0nC0EPM0gCsB;gBAAW72EoD9ClGjB0tF6E,0E;Y8CkGiB1tFwD;cAAAAqF;QAIfyyCgB;AAAO6kCqC;0EAKSnEmE;8BAAAAA1GjISt6CARuFbz9B2B,oBAAAAgC,A,A;+HkHoDEiiC4E;YAAAAA1GrImCxEARiFrCz9B2B,oBAAAAgC,A,A;yFkHuDEkgD6B;YAAAAA1GrIoCziBAR8EtCz9B2B,oBAAAAgC,A,A;gPkHqEdq3CgErHCer3C+C,A;AqHDRoxDAzDhHG5SuC,A;AyDiHenHArHAVr3CiD,A;4LqHMdymE+D;4iBA4BSjoBqC;qFAGSnHArHrCJr3CiF,oB;AqHqCzBg/BAzD1KwBh/B8F,A;8HyD0KxBlwD+E;qFAKiBgpIarHtDoB5LqC,A;AqHsDb1uBuC;+QAcds6B8BrHpE2B5LmC,A;qEqHqE3BnsCcrHjE6BmsCqC,A;wEqHkE7B57BarH9D2B47BuC,A;yXqHqET4LArH7ES5LmC,A;4DqH8ERnsC6BrH1EUmsCmC,A;6DqH2EX57B4BrHvES47BmC,A;gPqH8E1BltEkB;AADayuEsB;yCAIV2nBAA8BG5xCkB,6DAAAA4D,6EACF4KqE,A;4BA5BI0pBArH5FkB5L6C,A;iBqH4FvCn+Bc;sCAGYhOArH3F6BmsCmC,A;AqH2FrB9bsD;gCAGGrwBArH9FkBmsCqC,A;AqH8FvCn+Bc;+DAIUuCArH9F2B47BmC,A;AqH8FpB9bsD;6BAGI9fArHjGgB47BqC,A;AqHiGrCn+Bc;6DAMFAkD;0jBAiBoBphGM;09EChRlBgoH6B;sErGiDoCx4CoF;k8BuB5B5BgnBuM;AAFEnkCA4EKcq2FAAqDECgR,A,AApDJn5EAAOpBnd2H,A,AANuBCApKoMhB27BAFnCbAAAAAA0C,A,A,A,uD;gF0FnKS0eA+EjCPAY,A;A/EiCOqqBAxC4D0DyakC,A;AwC5D1D9kCA+EjCPAO,iD;A/EkCOSA+E9BPAmF,A;A/E+BiBw7CA6EsCOp5EAAvCPs5EAAAAz2FA9C1BnBAAAAAAAAC0B22F+H,A,A,A,A,A8CiDiBnL8Y,AAmB3CruEAAAAAuCAW6Bg2DArH6D6B11CAEjJtBAoBC2FRz9BgC,A,A,A,kIkHHC4oCqD,uH,A,A,A;i5qFzL2zCViuDoL;oZAUACwL;kZAUACsH;waAUAC0H;+tBqCn8BgCzM8C;6xEoFpc7B5tFAD3DYktF4C,A;oF/DAP7pFiB8GKFi9D6B,AACK92BiC,AACV0mC6B,A;wF9GAS7sEmBgHGJi9DmC,AACK92BqC,AACV0mC6E,AACQ/yB8C,A;gFhHEH95Ce+GVAi9D6B,AACK92B+D,AACV0mC2D,AACQ/yB6B,A;8gB3GHT95Cc;spD0CqBWAc;09C/C3BZAc;qFFHAAc;ilBoDesBmdyb;OAAAA0B;kwBxGmIbteAAqE3BgkF4B,A;"}}
\ No newline at end of file
diff --git a/pkgs/coverage/test/test_files/test_app.dart b/pkgs/coverage/test/test_files/test_app.dart
new file mode 100644
index 0000000..1e50703
--- /dev/null
+++ b/pkgs/coverage/test/test_files/test_app.dart
@@ -0,0 +1,61 @@
+// Copyright (c) 2015, 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.
+
+// coverage:ignore-file
+
+import 'dart:async';
+import 'dart:developer';
+import 'dart:isolate';
+
+import 'package:coverage/src/util.dart';
+
+import 'test_app_isolate.dart';
+
+part 'test_app.g.dart';
+
+Future<void> main() async {
+  for (var i = 0; i < 10; i++) {
+    for (var j = 0; j < 10; j++) {
+      final sum = usedMethod(i, j);
+      if (sum != (i + j)) {
+        throw 'bad method!';
+      }
+
+      final multiplication = usedGeneratedMethod(i, j);
+      if (multiplication != i * j) {
+        throw 'bad generated method!';
+      }
+    }
+  }
+
+  final port = ReceivePort();
+
+  final isolate =
+      await Isolate.spawn(isolateTask, [port.sendPort, 1, 2], paused: true);
+  await Service.controlWebServer(enable: true);
+  final isolateID = Service.getIsolateID(isolate);
+  print('isolateId = $isolateID');
+
+  isolate.addOnExitListener(port.sendPort);
+  isolate.resume(isolate.pauseCapability!);
+
+  final value = await port.first as int;
+  if (value != 3) {
+    throw 'expected 3!';
+  }
+
+  final result = await retry(() async => 42, const Duration(seconds: 1)) as int;
+  print(result);
+}
+
+int usedMethod(int a, int b) {
+  return a + b;
+}
+
+int unusedMethod(int a, int b) {
+  return a - b;
+}
+
+// ignore_for_file: unreachable_from_main, only_throw_errors
+// ignore_for_file: deprecated_member_use
diff --git a/pkgs/coverage/test/test_files/test_app.g.dart b/pkgs/coverage/test/test_files/test_app.g.dart
new file mode 100644
index 0000000..c80718a
--- /dev/null
+++ b/pkgs/coverage/test/test_files/test_app.g.dart
@@ -0,0 +1,5 @@
+part of 'test_app.dart';
+
+int usedGeneratedMethod(int a, int b) {
+  return a * b;
+}
diff --git a/pkgs/coverage/test/test_files/test_app_isolate.dart b/pkgs/coverage/test/test_files/test_app_isolate.dart
new file mode 100644
index 0000000..8bbc6be
--- /dev/null
+++ b/pkgs/coverage/test/test_files/test_app_isolate.dart
@@ -0,0 +1,73 @@
+// Copyright (c) 2015, 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.
+
+import 'dart:async';
+import 'dart:io';
+import 'dart:isolate';
+
+const int answer = 42;
+
+String fooSync(int x) {
+  if (x == answer) {
+    return '*' * x;
+  }
+  return List.generate(x, (_) => 'xyzzy').join(' ');
+}
+
+class BarClass {
+  BarClass(this.x);
+
+  int x;
+
+  void baz() {
+    print(x);
+  }
+}
+
+Future<String> fooAsync(int x) async {
+  if (x == answer) {
+    return '*' * x;
+  }
+  return List.generate(x, (_) => 'xyzzy').join(' ');
+}
+
+/// The number of covered lines is tested and expected to be 4.
+///
+/// If you modify this method, you may have to update the tests!
+void isolateTask(List threeThings) async {
+  sleep(const Duration(milliseconds: 500));
+
+  fooSync(answer);
+  unawaited(fooAsync(answer).then((_) {
+    final port = threeThings.first as SendPort;
+    final sum = (threeThings[1] as int) + (threeThings[2] as int);
+    port.send(sum);
+  }));
+
+  final bar = BarClass(123);
+  bar.baz();
+
+  print('678'); // coverage:ignore-line
+
+  // coverage:ignore-start
+  print('1');
+  print('2');
+  print('3');
+  // coverage:ignore-end
+
+  print('4 // coverage:ignore-line');
+  print('5 // coverage:ignore-file');
+
+  print('6'); // coverage:ignore-start
+  print('7');
+  print('8');
+  // coverage:ignore-end
+  print('9'); // coverage:ignore-start
+  print('10');
+  print('11'); // coverage:ignore-line
+
+  // Regression test for https://github.com/dart-lang/tools/issues/520.
+  await Isolate.run(() => print('Isolate.run'), debugName: 'Grandchild');
+  // coverage:ignore-end
+}
diff --git a/pkgs/coverage/test/test_files/test_library.dart b/pkgs/coverage/test/test_files/test_library.dart
new file mode 100644
index 0000000..d2fe49f
--- /dev/null
+++ b/pkgs/coverage/test/test_files/test_library.dart
@@ -0,0 +1,9 @@
+// Copyright (c) 2022, 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.
+
+part 'test_library_part.dart';
+
+int libraryFunction() {
+  return 123;
+}
diff --git a/pkgs/coverage/test/test_files/test_library_part.dart b/pkgs/coverage/test/test_files/test_library_part.dart
new file mode 100644
index 0000000..c99876d
--- /dev/null
+++ b/pkgs/coverage/test/test_files/test_library_part.dart
@@ -0,0 +1,9 @@
+// Copyright (c) 2022, 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.
+
+part of 'test_library.dart';
+
+int otherLibraryFunction() {
+  return 123;
+}
diff --git a/pkgs/coverage/test/test_util.dart b/pkgs/coverage/test/test_util.dart
new file mode 100644
index 0000000..e0a3edb
--- /dev/null
+++ b/pkgs/coverage/test/test_util.dart
@@ -0,0 +1,91 @@
+// Copyright (c) 2015, 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.
+
+import 'dart:async';
+import 'dart:io';
+
+import 'package:path/path.dart' as p;
+import 'package:test/test.dart';
+import 'package:test_process/test_process.dart';
+
+final String testAppPath = p.join('test', 'test_files', 'test_app.dart');
+
+const Duration timeout = Duration(seconds: 20);
+
+Future<TestProcess> runTestApp(int openPort) => TestProcess.start(
+      Platform.resolvedExecutable,
+      [
+        '--enable-vm-service=$openPort',
+        '--pause_isolates_on_exit',
+        '--branch-coverage',
+        testAppPath
+      ],
+    );
+
+List<Map<String, dynamic>> coverageDataFromJson(Map<String, dynamic> json) {
+  expect(json.keys, unorderedEquals(<String>['type', 'coverage']));
+  expect(json, containsPair('type', 'CodeCoverage'));
+
+  return (json['coverage'] as List).cast<Map<String, dynamic>>();
+}
+
+final _versionPattern = RegExp('([0-9]+)\\.([0-9]+)\\.([0-9]+)');
+
+bool platformVersionCheck(int minMajor, int minMinor) {
+  final match = _versionPattern.matchAsPrefix(Platform.version);
+  if (match == null) return false;
+  if (match.groupCount < 3) return false;
+  final major = int.parse(match.group(1)!);
+  final minor = int.parse(match.group(2)!);
+  return major > minMajor || (major == minMajor && minor >= minMinor);
+}
+
+/// Returns a mapping of (URL: (function_name: hit_count)) from [sources].
+Map<String, Map<String, int>> functionInfoFromSources(
+  Map<String, List<Map<dynamic, dynamic>>> sources,
+) {
+  Map<int, String> getFuncNames(List list) {
+    return {
+      for (var i = 0; i < list.length; i += 2)
+        list[i] as int: list[i + 1] as String,
+    };
+  }
+
+  Map<int, int> getFuncHits(List list) {
+    return {
+      for (var i = 0; i < list.length; i += 2)
+        list[i] as int: list[i + 1] as int,
+    };
+  }
+
+  return {
+    for (var entry in sources.entries)
+      entry.key: entry.value.fold(
+        {},
+        (previousValue, element) {
+          expect(element['source'], entry.key);
+          final names = getFuncNames(element['funcNames'] as List);
+          final hits = getFuncHits(element['funcHits'] as List);
+
+          for (var pair in hits.entries) {
+            previousValue[names[pair.key]!] =
+                (previousValue[names[pair.key]!] ?? 0) + pair.value;
+          }
+
+          return previousValue;
+        },
+      ),
+  };
+}
+
+extension ListTestExtension on List {
+  Map<String, List<Map<dynamic, dynamic>>> sources() => cast<Map>().fold(
+        <String, List<Map>>{},
+        (Map<String, List<Map>> map, value) {
+          final sourceUri = value['source'] as String;
+          map.putIfAbsent(sourceUri, () => <Map>[]).add(value);
+          return map;
+        },
+      );
+}
diff --git a/pkgs/coverage/test/test_with_coverage_package/lib/validate_lib.dart b/pkgs/coverage/test/test_with_coverage_package/lib/validate_lib.dart
new file mode 100644
index 0000000..771c040
--- /dev/null
+++ b/pkgs/coverage/test/test_with_coverage_package/lib/validate_lib.dart
@@ -0,0 +1,19 @@
+// Copyright (c) 2024, 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.
+
+int sum(Iterable<int> values) {
+  var val = 0;
+  for (var value in values) {
+    val += value;
+  }
+  return val;
+}
+
+int product(Iterable<int> values) {
+  var val = 1;
+  for (var value in values) {
+    val *= value;
+  }
+  return val;
+}
diff --git a/pkgs/coverage/test/test_with_coverage_package/pubspec.yaml b/pkgs/coverage/test/test_with_coverage_package/pubspec.yaml
new file mode 100644
index 0000000..3fa7ee0
--- /dev/null
+++ b/pkgs/coverage/test/test_with_coverage_package/pubspec.yaml
@@ -0,0 +1,12 @@
+name: coverage_integration_test_for_test_with_coverage
+publish_to: none
+
+environment:
+  sdk: '>=2.15.0 <3.0.0'
+
+dev_dependencies:
+  test: ^1.16.0
+
+dependency_overrides:
+  coverage:
+    path: ../../
diff --git a/pkgs/coverage/test/test_with_coverage_package/test/product_test.dart b/pkgs/coverage/test/test_with_coverage_package/test/product_test.dart
new file mode 100644
index 0000000..91eac53
--- /dev/null
+++ b/pkgs/coverage/test/test_with_coverage_package/test/product_test.dart
@@ -0,0 +1,14 @@
+// Copyright (c) 2022, 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.
+
+import 'package:test/test.dart';
+
+// ignore: avoid_relative_lib_imports
+import '../lib/validate_lib.dart';
+
+void main() {
+  test('product', () {
+    expect(product([2, 3]), 6);
+  });
+}
diff --git a/pkgs/coverage/test/test_with_coverage_package/test/sum_test.dart b/pkgs/coverage/test/test_with_coverage_package/test/sum_test.dart
new file mode 100644
index 0000000..f5b1ea4
--- /dev/null
+++ b/pkgs/coverage/test/test_with_coverage_package/test/sum_test.dart
@@ -0,0 +1,14 @@
+// Copyright (c) 2022, 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.
+
+import 'package:test/test.dart';
+
+// ignore: avoid_relative_lib_imports
+import '../lib/validate_lib.dart';
+
+void main() {
+  test('sum', () {
+    expect(sum([1, 2]), 3);
+  });
+}
diff --git a/pkgs/coverage/test/test_with_coverage_test.dart b/pkgs/coverage/test/test_with_coverage_test.dart
new file mode 100644
index 0000000..689452d
--- /dev/null
+++ b/pkgs/coverage/test/test_with_coverage_test.dart
@@ -0,0 +1,157 @@
+// Copyright (c) 2022, 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.
+
+@Timeout(Duration(seconds: 60))
+library;
+
+import 'dart:convert';
+import 'dart:io';
+
+import 'package:path/path.dart' as p;
+import 'package:test/test.dart';
+import 'package:test_descriptor/test_descriptor.dart' as d;
+import 'package:test_process/test_process.dart';
+
+import 'test_util.dart';
+
+// this package
+final _pkgDir = p.absolute('');
+final _testWithCoveragePath = p.join(_pkgDir, 'bin', 'test_with_coverage.dart');
+
+// test package
+final _testPkgDirPath = p.join(_pkgDir, 'test', 'test_with_coverage_package');
+
+/// Override PUB_CACHE
+///
+/// Use a subdirectory different from `test/` just in case there is a problem
+/// with the clean up. If other packages are present under the `test/`
+/// subdirectory their tests may accidentally get run when running `dart test`
+final _pubCachePathInTestPkgSubDir = p.join(_pkgDir, 'var', 'pub-cache');
+final _env = {'PUB_CACHE': _pubCachePathInTestPkgSubDir};
+
+const _testPackageName = 'coverage_integration_test_for_test_with_coverage';
+
+int _port = 9300;
+
+Iterable<File> _dartFiles(String dir) =>
+    Directory(p.join(_testPkgDirPath, dir)).listSync().whereType<File>();
+
+String _fixTestFile(String content) => content.replaceAll(
+      "import '../lib/",
+      "import 'package:$_testPackageName/",
+    );
+
+void main() {
+  setUpAll(() async {
+    for (var dir in const ['lib', 'test']) {
+      await d.dir(dir, [
+        for (var dartFile in _dartFiles(dir))
+          d.file(
+            p.basename(dartFile.path),
+            _fixTestFile(dartFile.readAsStringSync()),
+          ),
+      ]).create();
+    }
+
+    var pubspecContent =
+        File(p.join(_testPkgDirPath, 'pubspec.yaml')).readAsStringSync();
+
+    expect(
+      pubspecContent.replaceAll('\r\n', '\n'),
+      contains(r'''
+dependency_overrides:
+  coverage:
+    path: ../../
+'''),
+    );
+
+    pubspecContent =
+        pubspecContent.replaceFirst('path: ../../', 'path: $_pkgDir');
+
+    await d.file('pubspec.yaml', pubspecContent).create();
+
+    final localPub = await _run(['pub', 'get']);
+    await localPub.shouldExit(0);
+  });
+
+  test('dart run bin/test_with_coverage.dart -f', () async {
+    final list = await _runTest(['run', _testWithCoveragePath, '-f']);
+
+    final sources = list.sources();
+    final functionHits = functionInfoFromSources(sources);
+
+    expect(
+      functionHits['package:$_testPackageName/validate_lib.dart'],
+      {
+        'product': 1,
+        'sum': 1,
+      },
+    );
+  });
+
+  test('dart run bin/test_with_coverage.dart -f -- -N sum', () async {
+    final list = await _runTest(
+      ['run', _testWithCoveragePath, '-f'],
+      extraArgs: ['--', '-N', 'sum'],
+    );
+
+    final sources = list.sources();
+    final functionHits = functionInfoFromSources(sources);
+
+    expect(
+      functionHits['package:$_testPackageName/validate_lib.dart'],
+      {
+        'product': 0,
+        'sum': 1,
+      },
+      reason: 'only `sum` tests should be run',
+    );
+  });
+
+  test('dart run coverage:test_with_coverage', () async {
+    await _runTest(['run', 'coverage:test_with_coverage']);
+  });
+
+  test('dart pub global run coverage:test_with_coverage', () async {
+    final globalPub =
+        await _run(['pub', 'global', 'activate', '-s', 'path', _pkgDir]);
+    await globalPub.shouldExit(0);
+
+    await _runTest(
+      ['pub', 'global', 'run', 'coverage:test_with_coverage'],
+    );
+  });
+}
+
+Future<TestProcess> _run(List<String> args) => TestProcess.start(
+      Platform.executable,
+      args,
+      workingDirectory: d.sandbox,
+      environment: _env,
+    );
+
+Future<List<Map<String, dynamic>>> _runTest(
+  List<String> invokeArgs, {
+  List<String>? extraArgs,
+}) async {
+  final process = await _run([
+    ...invokeArgs,
+    '--port',
+    '${_port++}',
+    ...?extraArgs,
+  ]);
+
+  await process.shouldExit(0);
+
+  await d.dir(
+    'coverage',
+    [d.file('coverage.json', isNotEmpty), d.file('lcov.info', isNotEmpty)],
+  ).validate();
+
+  final coverageDataFile = File(p.join(d.sandbox, 'coverage', 'coverage.json'));
+
+  final json = jsonDecode(coverageDataFile.readAsStringSync());
+
+  return coverageDataFromJson(json as Map<String, dynamic>);
+}
diff --git a/pkgs/coverage/test/util_test.dart b/pkgs/coverage/test/util_test.dart
new file mode 100644
index 0000000..6a4e556
--- /dev/null
+++ b/pkgs/coverage/test/util_test.dart
@@ -0,0 +1,358 @@
+// Copyright (c) 2015, 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.
+
+// ignore_for_file: only_throw_errors
+
+import 'dart:async';
+
+import 'package:coverage/src/util.dart';
+import 'package:test/test.dart';
+
+const _failCount = 5;
+const _delay = Duration(milliseconds: 10);
+
+void main() {
+  test('retry', () async {
+    var count = 0;
+    final stopwatch = Stopwatch()..start();
+
+    Future failCountTimes() async {
+      expect(stopwatch.elapsed, greaterThanOrEqualTo(_delay * count));
+
+      while (count < _failCount) {
+        count++;
+        throw 'not yet!';
+      }
+      return 42;
+    }
+
+    final value = await retry(failCountTimes, _delay) as int;
+
+    expect(value, 42);
+    expect(count, _failCount);
+    expect(stopwatch.elapsed, greaterThanOrEqualTo(_delay * count));
+  });
+
+  group('retry with timeout', () {
+    test('if it finishes', () async {
+      var count = 0;
+      final stopwatch = Stopwatch()..start();
+
+      Future failCountTimes() async {
+        expect(stopwatch.elapsed, greaterThanOrEqualTo(_delay * count));
+
+        while (count < _failCount) {
+          count++;
+          throw 'not yet!';
+        }
+        return 42;
+      }
+
+      final safeTimoutDuration = _delay * _failCount * 10;
+      final value = await retry(
+        failCountTimes,
+        _delay,
+        timeout: safeTimoutDuration,
+      ) as int;
+
+      expect(value, 42);
+      expect(count, _failCount);
+      expect(stopwatch.elapsed, greaterThanOrEqualTo(_delay * count));
+    });
+
+    test('if it does not finish', () async {
+      var count = 0;
+      final stopwatch = Stopwatch()..start();
+
+      var caught = false;
+      var countAfterError = 0;
+
+      Future failCountTimes() async {
+        if (caught) {
+          countAfterError++;
+        }
+        expect(stopwatch.elapsed, greaterThanOrEqualTo(_delay * count));
+
+        count++;
+        throw 'never';
+      }
+
+      final unsafeTimeoutDuration = _delay * (_failCount / 2);
+
+      try {
+        await retry(failCountTimes, _delay, timeout: unsafeTimeoutDuration);
+        // ignore: avoid_catching_errors
+      } on StateError catch (e) {
+        expect(e.message, 'Failed to complete within 25ms');
+        caught = true;
+
+        expect(countAfterError, 0,
+            reason: 'Execution should stop after a timeout');
+
+        await Future<dynamic>.delayed(_delay * 3);
+
+        expect(countAfterError, 0, reason: 'Even after a delay');
+      }
+
+      expect(caught, isTrue);
+    });
+  });
+
+  group('extractVMServiceUri', () {
+    test('returns null when not found', () {
+      expect(extractVMServiceUri('foo bar baz'), isNull);
+    });
+
+    test('returns null for an incorrectly formatted URI', () {
+      const msg = 'Observatory listening on :://';
+      expect(extractVMServiceUri(msg), null);
+    });
+
+    test('returns URI at end of string', () {
+      const msg = 'Observatory listening on http://foo.bar:9999/';
+      expect(extractVMServiceUri(msg), Uri.parse('http://foo.bar:9999/'));
+    });
+
+    test('returns URI with auth token at end of string', () {
+      const msg = 'Observatory listening on http://foo.bar:9999/cG90YXRv/';
+      expect(
+          extractVMServiceUri(msg), Uri.parse('http://foo.bar:9999/cG90YXRv/'));
+    });
+
+    test('return URI embedded within string', () {
+      const msg = '1985-10-26 Observatory listening on http://foo.bar:9999/ **';
+      expect(extractVMServiceUri(msg), Uri.parse('http://foo.bar:9999/'));
+    });
+
+    test('return URI with auth token embedded within string', () {
+      const msg =
+          '1985-10-26 Observatory listening on http://foo.bar:9999/cG90YXRv/ **';
+      expect(
+          extractVMServiceUri(msg), Uri.parse('http://foo.bar:9999/cG90YXRv/'));
+    });
+
+    test('handles new Dart VM service message format', () {
+      const msg =
+          'The Dart VM service is listening on http://foo.bar:9999/cG90YXRv/';
+      expect(
+          extractVMServiceUri(msg), Uri.parse('http://foo.bar:9999/cG90YXRv/'));
+    });
+  });
+
+  group('getIgnoredLines', () {
+    const invalidSources = [
+      '''final str = ''; // coverage:ignore-start
+        final str = '';
+        final str = ''; // coverage:ignore-start
+        ''',
+      '''final str = ''; // coverage:ignore-start
+        final str = '';
+        final str = ''; // coverage:ignore-start
+        final str = ''; // coverage:ignore-end
+        final str = '';
+        final str = ''; // coverage:ignore-end
+        ''',
+      '''final str = ''; // coverage:ignore-start
+        final str = '';
+        final str = ''; // coverage:ignore-end
+        final str = '';
+        final str = ''; // coverage:ignore-end
+        ''',
+      '''final str = ''; // coverage:ignore-end
+        final str = '';
+        final str = ''; // coverage:ignore-start
+        final str = '';
+        final str = ''; // coverage:ignore-end
+        ''',
+      '''final str = ''; // coverage:ignore-end
+        final str = '';
+        final str = ''; // coverage:ignore-end
+        ''',
+      '''final str = ''; // coverage:ignore-end
+        final str = '';
+        final str = ''; // coverage:ignore-start
+        ''',
+      '''final str = ''; // coverage:ignore-end
+        ''',
+      '''final str = ''; // coverage:ignore-start
+        ''',
+    ];
+
+    test('throws FormatException when the annotations are not balanced', () {
+      void runTest(int index, String errMsg) {
+        final content = invalidSources[index].split('\n');
+        expect(
+          () => getIgnoredLines('content-$index.dart', content),
+          throwsA(
+            allOf(
+              isFormatException,
+              predicate((FormatException e) => e.message == errMsg),
+            ),
+          ),
+          reason: 'expected FormatException with message "$errMsg"',
+        );
+      }
+
+      runTest(
+        0,
+        'coverage:ignore-start found at content-0.dart:'
+        '3 before previous coverage:ignore-start ended',
+      );
+      runTest(
+        1,
+        'coverage:ignore-start found at content-1.dart:'
+        '3 before previous coverage:ignore-start ended',
+      );
+      runTest(
+        2,
+        'unmatched coverage:ignore-end found at content-2.dart:5',
+      );
+      runTest(
+        3,
+        'unmatched coverage:ignore-end found at content-3.dart:1',
+      );
+      runTest(
+        4,
+        'unmatched coverage:ignore-end found at content-4.dart:1',
+      );
+      runTest(
+        5,
+        'unmatched coverage:ignore-end found at content-5.dart:1',
+      );
+      runTest(
+        6,
+        'unmatched coverage:ignore-end found at content-6.dart:1',
+      );
+      runTest(
+        7,
+        'coverage:ignore-start found at content-7.dart:'
+        '1 has no matching coverage:ignore-end',
+      );
+    });
+
+    test(
+        'returns [[0,lines.length]] when the annotations are not '
+        'balanced but the whole file is ignored', () {
+      for (final content in invalidSources) {
+        final lines = content.split('\n');
+        lines.add(' // coverage:ignore-file');
+        expect(getIgnoredLines('', lines), [
+          [0, lines.length]
+        ]);
+      }
+    });
+
+    test('returns [[0,lines.length]] when the whole file is ignored', () {
+      final lines = '''final str = ''; // coverage:ignore-start
+      final str = ''; // coverage:ignore-end
+      final str = ''; // coverage:ignore-file
+      '''
+          .split('\n');
+
+      expect(getIgnoredLines('', lines), [
+        [0, lines.length]
+      ]);
+    });
+
+    test('return the correct range of lines ignored', () {
+      final lines = '''
+      final str = ''; // coverage:ignore-start
+      final str = ''; // coverage:ignore-line
+      final str = ''; // coverage:ignore-end
+      final str = ''; // coverage:ignore-start
+      final str = ''; // coverage:ignore-line
+      final str = ''; // coverage:ignore-end
+      '''
+          .split('\n');
+
+      expect(getIgnoredLines('', lines), [
+        [1, 3],
+        [4, 6],
+      ]);
+    });
+
+    test('return the correct list of lines ignored', () {
+      final lines = '''
+      final str = ''; // coverage:ignore-line
+      final str = ''; // coverage:ignore-line
+      final str = ''; // coverage:ignore-line
+      '''
+          .split('\n');
+
+      expect(getIgnoredLines('', lines), [
+        [1, 1],
+        [2, 2],
+        [3, 3],
+      ]);
+    });
+
+    test('ignore comments have no effect inside string literals', () {
+      final lines = '''
+      final str = '// coverage:ignore-file';
+      final str = '// coverage:ignore-line';
+      final str = ''; // coverage:ignore-line
+      final str = '// coverage:ignore-start';
+      final str = '// coverage:ignore-end';
+      '''
+          .split('\n');
+
+      expect(getIgnoredLines('', lines), [
+        [3, 3],
+      ]);
+    });
+
+    test('allow white-space after ignore comments', () {
+      // Using multiple strings, rather than splitting a multi-line string,
+      // because many code editors remove trailing white-space.
+      final lines = [
+        "final str = ''; // coverage:ignore-start      ",
+        "final str = ''; // coverage:ignore-line\t",
+        "final str = ''; // coverage:ignore-end \t   \t   ",
+        "final str = ''; // coverage:ignore-line     \t ",
+        "final str = ''; // coverage:ignore-start    \t   ",
+        "final str = ''; // coverage:ignore-end  \t    \t ",
+      ];
+
+      expect(getIgnoredLines('', lines), [
+        [1, 3],
+        [4, 4],
+        [5, 6],
+      ]);
+    });
+
+    test('allow omitting space after //', () {
+      final lines = [
+        "final str = ''; //coverage:ignore-start",
+        "final str = ''; //coverage:ignore-line",
+        "final str = ''; //coverage:ignore-end",
+        "final str = ''; //coverage:ignore-line",
+        "final str = ''; //coverage:ignore-start",
+        "final str = ''; //coverage:ignore-end",
+      ];
+
+      expect(getIgnoredLines('', lines), [
+        [1, 3],
+        [4, 4],
+        [5, 6],
+      ]);
+    });
+
+    test('allow text after ignore comments', () {
+      final lines = [
+        "final str = ''; // coverage:ignore-start due to XYZ",
+        "final str = ''; // coverage:ignore-line",
+        "final str = ''; // coverage:ignore-end due to XYZ",
+        "final str = ''; // coverage:ignore-line due to 123",
+        "final str = ''; // coverage:ignore-start",
+        "final str = ''; // coverage:ignore-end it is done",
+      ];
+
+      expect(getIgnoredLines('', lines), [
+        [1, 3],
+        [4, 4],
+        [5, 6],
+      ]);
+    });
+  });
+}
diff --git a/pkgs/extension_discovery/.gitignore b/pkgs/extension_discovery/.gitignore
new file mode 100644
index 0000000..ddfdca1
--- /dev/null
+++ b/pkgs/extension_discovery/.gitignore
@@ -0,0 +1,5 @@
+.dart_tool/
+.packages
+.pub/
+build/
+pubspec.lock
diff --git a/pkgs/extension_discovery/CHANGELOG.md b/pkgs/extension_discovery/CHANGELOG.md
new file mode 100644
index 0000000..f35371e
--- /dev/null
+++ b/pkgs/extension_discovery/CHANGELOG.md
@@ -0,0 +1,24 @@
+## 2.1.0
+
+- Require Dart 3.4.
+- Update to the latest version of `package:dart_flutter_team_lints`.
+- Add `findPackageConfig()` allowing for automatic discovery of the
+  packageConfig based on a package directory.
+
+## 2.0.0
+
+- Use `extension/<package>/config.yaml` instead of
+  `extension/<package>/config.json` for better consistency with other tooling.
+- Require that the top-level value in `extension/<package>/config.yaml` is
+  always a `Map`, and that the structure can be converted to a JSON equivalent
+  structure.
+
+## 1.0.1
+
+- Support optional `packageUri`.
+- Improve error messaging for `package_config.json` parsing.
+- Update the package description.
+
+## 1.0.0
+
+- Initial version.
diff --git a/pkgs/extension_discovery/LICENSE b/pkgs/extension_discovery/LICENSE
new file mode 100644
index 0000000..ac90031
--- /dev/null
+++ b/pkgs/extension_discovery/LICENSE
@@ -0,0 +1,27 @@
+Copyright 2023, the Dart project authors.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+    * Redistributions of source code must retain the above copyright
+      notice, this list of conditions and the following disclaimer.
+    * Redistributions in binary form must reproduce the above
+      copyright notice, this list of conditions and the following
+      disclaimer in the documentation and/or other materials provided
+      with the distribution.
+    * Neither the name of Google LLC nor the names of its
+      contributors may be used to endorse or promote products derived
+      from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
\ No newline at end of file
diff --git a/pkgs/extension_discovery/README.md b/pkgs/extension_discovery/README.md
new file mode 100644
index 0000000..0214ae9
--- /dev/null
+++ b/pkgs/extension_discovery/README.md
@@ -0,0 +1,237 @@
+[![package:extension_discovery](https://github.com/dart-lang/tools/actions/workflows/extension_discovery.yml/badge.svg)](https://github.com/dart-lang/tools/actions/workflows/extension_discovery.yml)
+[![pub package](https://img.shields.io/pub/v/extension_discovery.svg)](https://pub.dev/packages/extension_discovery)
+[![package publisher](https://img.shields.io/pub/publisher/extension_discovery.svg)](https://pub.dev/packages/extension_discovery/publisher)
+
+A convention and utilities for package extension discovery.
+
+## What's this?
+
+A convention to allow other packages to provide extensions for your package
+(or tool). Including logic for finding extensions that honor this convention.
+
+The convention implemented in this package is that if `foo` provides an
+extension for `<targetPackage>`.
+Then `foo` must contain a config file `extension/<targetPackage>/config.yaml`.
+This file indicates that `foo` provides an extension for `<targetPackage>`.
+
+If `<targetPackage>` accepts extensions from other packages it must:
+ * Find extensions using `findExtensions('<targetPackage>')` from this package.
+ * Document how extensions are implemented:
+   * What should the contents of the `extension/<targetPackage>/config.yaml` file be?
+   * Should packages providing extensions have a dependency constraint on `<targetPackage>`?
+   * What libraries/assets should packages that provide extensions include?
+   * Should packages providing extensions specify a [topic in `pubspec.yaml`][1]
+     for easy discovery on pub.dev.
+
+The `findExtensions(targetPackage, packageConfig: ...)` function will:
+ * Load `.dart_tool/package_config.json` and find all packages that contain a
+   valid YAML file: `extension/<targetPackage>/config.yaml`.
+ * Provide the package name, location and contents of the `config.yaml` file,
+   for all detected extensions (aimed at `targetPackage`).
+ * Cache the results for fast loading, comparing modification timestamps to
+   ensure consistent results.
+
+It is the responsibility package that can be extended to validate extensions,
+decide when they should be enabled, and documenting how such extensions are
+created.
+
+
+## Packages that extend tools
+
+You can also use this package (and associated convention), if you are developing
+a tool that can be extended by packages. In this case, you would call
+`findExtensions(<my_tool_package_name>, packageConfig: ...)` where
+`packageConfig` points to the `.dart_tool/package_config.json` in the workspace
+the tool is operating on.
+
+If you tool is not distributed through pub.dev, you might consider publishing
+a placeholder package in order to reserve a unique name (and avoid collisions).
+Using a placeholder package to reserve a unique is also recommended for tools
+that wish to cache files in `.dart_tool/<my_tool_package_name>/`.
+See [package layout documentation][2] for details.
+
+
+## Example: Hello World
+
+Imagine that we have a `hello_world` package that defines a single method
+`sayHello(String language)`, along the lines of:
+
+```dart
+void sayHello(String language) {
+  if (language == 'danish') {
+    print('Hej verden');
+  } else {
+    print('Hello world!');
+  }
+}
+```
+
+### Enabling packages to extend `hello_world`
+
+If we wanted to allow other packages to provide additional languages by
+extending the `hello_world` package. Then we could do:
+
+```dart
+import 'package:extension_discovery/extension_discovery.dart';
+
+Future<void> sayHello(String language) async {
+  // Find extensions for the "hello_world" package.
+  // WARNING: This only works when running in JIT-mode, if running in AOT-mode
+  //          you must supply the `packageConfig` argument, and have a local
+  //          `.dart_tool/package_config.json` and `$PUB_CACHE`.
+  //          See "Runtime limitations" section further down.
+  final extensions = await findExtensions('hello_world');
+
+  // Search extensions to see if one provides a message for language
+  for (final ext in extensions) {
+    final config = ext.config;
+    if (config is! Map<String, Object?>) {
+      continue; // ignore extensions with invalid configation
+    }
+    if (config['language'] == language) {
+      print(config['message']);
+      return; // Don't print more messages!
+    }
+  }
+
+  if (language == 'danish') {
+    print('Hej verden');
+  } else {
+    print('Hello world!');
+  }
+}
+```
+
+The `findExtensions` function will search other packages for
+`extension/hello_world/config.yaml`, and provide the contents of this file as
+well as provide the location of the extending packages.
+As authors of the `hello_world` package we should also document how other
+packages can extend `hello_world`. This is typically done by adding a segment
+to the `README.md`.
+
+
+### Extending `hello_world` from another package
+
+If in another package `hello_world_german` we wanted to extend `hello_world`
+and provide a translation for German, then we would create a
+`hello_world_german` package containing an
+**`extension/hello_world/config.yaml`**:
+
+```yaml
+language: german
+message: "Hello Welt!"
+```
+
+Obviously, this is a contrived example. The authors of the `hello_world` package
+could specify all sorts configuration options that extension authors can
+specify in `extension/hello_world/config.yaml`.
+
+The authors of `hello_world` could also specify that extensions must provide
+certain assets in `extension/hello_world/` or that they must provide certain
+Dart libraries implementing a specified interface somewhere in `lib/src/...`.
+
+It is up to the authors of `hello_world` to specify what extension authors must
+provide. The `extension_discovery` package only provides a utility for finding
+extensions.
+
+
+### Using `hello_world` and `hello_world_german`
+
+If writing `my_hello_world_app` I can now take advantage of `hello_world` and
+`hello_world_german`. Simply write a `pubspec.yaml` as follows:
+
+```yaml
+# pubspec.yaml
+name: my_hello_world_app
+dependencies:
+  hello_world: ^1.0.0
+  hello_world_german: ^1.0.0
+environment:
+  sdk: ^3.4.0
+```
+
+Then I can write a `bin/hello.dart` as follows:
+
+```dart
+// bin/hello.dart
+import 'package:hello_world/hello_world.dart';
+
+Future<void> main() async {
+  await sayHello('german');
+}
+```
+
+
+## What can an extension provide?
+
+As far as the `extension_discovery` package is concerned an extension can
+provide anything. Naturally, it is the authors of the extendable package that
+decides what extensions can be provide.
+
+In the example above it is the authors of the `hello_world` package that decides
+what extension packages can provide. For this reason it is important that the
+authors of `hello_world` very explicitly document how an extension is written.
+
+Obviously, authors of `hello_world` should document what should be specified in
+`extension/hello_world/config.yaml`. They could also specify that other files
+should be provided in `extension/hello_world/`, or that certain Dart libraries
+should be provided in `lib/src/hello_world/...` or something like that.
+
+When authors of `hello_world` consumes the extensions discovered through
+`findExtensions` they would naturally also be wise to validate that the
+extension provides the required configuration and files.
+
+
+## Compatibility considerations
+
+When writing an extension it is strongly encouraged to have a dependency
+constraint on the package being extended. This ensures that the extending
+package will be incompatibility with new major versions of the extended package.
+
+In the example above, it is strongly encouraged for `hello_world_german` to
+have a dependency constraint `hello_world: ^1.0.0`. Even if `hello_world_german`
+doesn't import libraries from `package:hello_world`.
+
+Because the next major version of `hello_world` (version `2.0.0`) might change
+what is required of an extension. Thus, it's fair to assume that
+`hello_world_german` might not be compatible with newer versions of
+`hello_world`. Hence, adding a dependency constraint `hello_world: ^1.0.0` saves
+users from resolving dependencies that aren't compatible.
+
+Naturally, after a new major version of `hello_world` is published a new
+version of `hello_world_german` can then also be published, addressing any
+breaking changes and bumping the dependency constraint.
+
+**Tip:** Authors of packages that can be extended might want to force extension
+authors take dependency on their package, to ensure that they have the ability
+to do breaking changes in the future.
+
+
+## Runtime limitations
+
+The `findExtensions` function only works when running in JIT-mode, otherwise the
+`packageConfig` parameter must be used to provide the location of
+`.dart_tool/package_config.json`. Obviously, the `package_config.json` must be
+present, as must the pub-cache locations referenced here.
+
+Hence, `findExtensions` effectively **only works from project workspace!**.
+
+You can't use `findExtensions` in a compiled Flutter application or an
+AOT-compiled executable distributed to end-users. Because in these environments
+you don't have a `package_config.json` nor do you have a pub-cache. You don't
+even have access to your own source files.
+
+If your deployment target a compiled Flutter application or AOT-compiled
+executable, then you will have to create some code/asset-generation.
+You code/asset-generation scripts can use `findExtensions` to find extensions,
+and then use the assets or Dart libraries from here to generate assets or code
+that is embedded in the final Flutter application (or AOT-compiled executable).
+
+This makes `findExtensions` immediately useful, if you are writing development
+tools that users will install into their project workspace. But if you're
+writing a package for use in deployed applications, you'll likely need to figure
+out how to embed the extensions, `findExtensions` only helps
+you find the extensions during code-gen.
+
+[1]: https://dart.dev/tools/pub/pubspec#topics
+[2]: https://dart.dev/tools/pub/package-layout#project-specific-caching-for-tools
diff --git a/pkgs/extension_discovery/analysis_options.yaml b/pkgs/extension_discovery/analysis_options.yaml
new file mode 100644
index 0000000..aadd26e
--- /dev/null
+++ b/pkgs/extension_discovery/analysis_options.yaml
@@ -0,0 +1,5 @@
+include: package:dart_flutter_team_lints/analysis_options.yaml
+
+linter:
+  rules:
+    - avoid_catches_without_on_clauses
diff --git a/pkgs/extension_discovery/example/hello_world/README.md b/pkgs/extension_discovery/example/hello_world/README.md
new file mode 100644
index 0000000..39ec96d
--- /dev/null
+++ b/pkgs/extension_discovery/example/hello_world/README.md
@@ -0,0 +1,26 @@
+# `hello_world` package
+
+Example of a package that can be extended, and uses `extension_discovery` to
+find extensions.
+
+## Limitations
+
+The `sayHello` function in this package can only be used in a project workspace,
+where dependencies are resolved and you're running in JIT-mode.
+
+The `sayHello` function uses `findExtensions` and, thus, cannot be called in a
+compiled Flutter application or AOT-compiled executable. For this to work, we'd
+need to augment this package with code-generation, such that the code-generation
+uses `findExtensions` and compiles a `sayHello` function into your application.
+
+## Extending the `hello_world` package
+
+Other packages can extend this package by providing an `extension/hello_world/config.json` file the following form:
+
+```js
+// extension/hello_world/config.json
+{
+  "language": "<language>",
+  "message": "<message>"
+}
+```
diff --git a/pkgs/extension_discovery/example/hello_world/lib/hello_world.dart b/pkgs/extension_discovery/example/hello_world/lib/hello_world.dart
new file mode 100644
index 0000000..9e4a848
--- /dev/null
+++ b/pkgs/extension_discovery/example/hello_world/lib/hello_world.dart
@@ -0,0 +1,28 @@
+// Copyright (c) 2023, 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.
+
+import 'package:extension_discovery/extension_discovery.dart';
+
+Future<void> sayHello(String language) async {
+  // Find extensions for the "hello_world" package.
+  // WARNING: This only works when running in JIT-mode, if running in AOT-mode
+  //          you must supply the `packageConfig` argument, and have a local
+  //          `.dart_tool/package_config.json` and `$PUB_CACHE`.
+  final extensions = await findExtensions('hello_world');
+
+  // Search extensions to see if one provides a message for language
+  for (final ext in extensions) {
+    final config = ext.config;
+    if (config['language'] == language) {
+      print(config['message']);
+      return; // Don't print more messages!
+    }
+  }
+
+  if (language == 'danish') {
+    print('Hej verden');
+  } else {
+    print('Hello world!');
+  }
+}
diff --git a/pkgs/extension_discovery/example/hello_world/pubspec.yaml b/pkgs/extension_discovery/example/hello_world/pubspec.yaml
new file mode 100644
index 0000000..40c68a3
--- /dev/null
+++ b/pkgs/extension_discovery/example/hello_world/pubspec.yaml
@@ -0,0 +1,10 @@
+name: hello_world
+version: 1.0.0
+publish_to: none # This is an example, don't publish!
+
+dependencies:
+  extension_discovery: # ^1.0.0
+    path: ../../
+
+environment:
+  sdk: ^3.4.0
diff --git a/pkgs/extension_discovery/example/hello_world_app/README.md b/pkgs/extension_discovery/example/hello_world_app/README.md
new file mode 100644
index 0000000..1d45229
--- /dev/null
+++ b/pkgs/extension_discovery/example/hello_world_app/README.md
@@ -0,0 +1,8 @@
+# `hello_world_app`
+
+An application that uses the `hello_world` package and has a dependency on
+`hello_world_german` such that when `hello_world` calls `findExtensions` it will
+find the extension in `hello_world_german`.
+
+**Notice**: This application only works when running from a project workspace.
+See "runtime limitation" in the README for `package:extension_discovery`.
diff --git a/pkgs/extension_discovery/example/hello_world_app/bin/hello.dart b/pkgs/extension_discovery/example/hello_world_app/bin/hello.dart
new file mode 100644
index 0000000..a4715ef
--- /dev/null
+++ b/pkgs/extension_discovery/example/hello_world_app/bin/hello.dart
@@ -0,0 +1,9 @@
+// Copyright (c) 2023, 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.
+
+import 'package:hello_world/hello_world.dart';
+
+Future<void> main() async {
+  await sayHello('german');
+}
diff --git a/pkgs/extension_discovery/example/hello_world_app/pubspec.yaml b/pkgs/extension_discovery/example/hello_world_app/pubspec.yaml
new file mode 100644
index 0000000..30338d2
--- /dev/null
+++ b/pkgs/extension_discovery/example/hello_world_app/pubspec.yaml
@@ -0,0 +1,11 @@
+name: my_hello_world_app
+publish_to: none # applications should never be published!
+
+dependencies:
+  hello_world: # ^1.0.0
+    path: ../hello_world
+  hello_world_german: # ^1.0.0
+    path: ../hello_world_german
+
+environment:
+  sdk: ^3.4.0
diff --git a/pkgs/extension_discovery/example/hello_world_german/README.md b/pkgs/extension_discovery/example/hello_world_german/README.md
new file mode 100644
index 0000000..4a58703
--- /dev/null
+++ b/pkgs/extension_discovery/example/hello_world_german/README.md
@@ -0,0 +1,4 @@
+# `hello_world_german`
+
+Example of a simple package that provides an extension for the `hello_world`
+package.
diff --git a/pkgs/extension_discovery/example/hello_world_german/extension/hello_world/config.yaml b/pkgs/extension_discovery/example/hello_world_german/extension/hello_world/config.yaml
new file mode 100644
index 0000000..ef57087
--- /dev/null
+++ b/pkgs/extension_discovery/example/hello_world_german/extension/hello_world/config.yaml
@@ -0,0 +1,9 @@
+# This config file let's `package:extension_discovery` find out that
+# `package:hello_world_german` has an extension for `package:hello_world`.
+#
+# The root object must be a map, and the data structure must be representable
+# as JSON, but those are the only constraints. Beyond that it is the
+# responsibility of `package:hello_world` to define what this file should
+# contain, to validate the contents, and do something useful with it.
+language: german
+message: "Hello Welt!"
diff --git a/pkgs/extension_discovery/example/hello_world_german/pubspec.yaml b/pkgs/extension_discovery/example/hello_world_german/pubspec.yaml
new file mode 100644
index 0000000..39e80be
--- /dev/null
+++ b/pkgs/extension_discovery/example/hello_world_german/pubspec.yaml
@@ -0,0 +1,15 @@
+name: hello_world_german
+version: 1.0.0
+publish_to: none # This is an example, don't publish!
+
+dependencies:
+  # We keep a dependency on package `hello_world` because this package provides
+  # an extension for this package. Hence, a newer major version of hello_world
+  # might be incompatible with the extension options we've provided in
+  #   extension/hello_world/config.json
+  # It is `hello_world` that specifies what is required in `config.json`.
+  hello_world: # ^1.0.0
+    path: ../hello_world
+
+environment:
+  sdk: ^3.4.0
diff --git a/pkgs/extension_discovery/lib/extension_discovery.dart b/pkgs/extension_discovery/lib/extension_discovery.dart
new file mode 100644
index 0000000..662435a
--- /dev/null
+++ b/pkgs/extension_discovery/lib/extension_discovery.dart
@@ -0,0 +1,285 @@
+// Copyright (c) 2023, 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.
+
+/// Find extensions with [findExtensions].
+library;
+
+import 'dart:collection' show UnmodifiableListView;
+import 'dart:io' show File, IOException;
+import 'dart:isolate' show Isolate;
+
+import 'src/io.dart';
+import 'src/package_config.dart';
+import 'src/registry.dart';
+import 'src/yaml_config_format.dart';
+
+export 'src/package_config.dart' show PackageConfigException, findPackageConfig;
+
+/// Information about an extension for target package.
+final class Extension {
+  /// Name of the package providing an extension.
+  final String package;
+
+  /// Absolute path to the package root.
+  ///
+  /// This folder usually contains a `lib/` folder and a `pubspec.yaml`
+  /// (assuming dependencies are fetched using the pub package manager).
+  ///
+  /// **Examples:** If `foo` is installed in pub-cache this would be:
+  ///  * `/home/my_user/.pub-cache/hosted/pub.dev/foo-1.0.0/`
+  ///
+  /// See `rootUri` in the [specification for `package_config.json`][1],
+  /// for details.
+  ///
+  /// [1]: https://github.com/dart-lang/language/blob/main/accepted/2.8/language-versioning/package-config-file-v2.md
+  final Uri rootUri;
+
+  /// Path to the library import path relative to [rootUri].
+  ///
+  /// In Dart code the `package:<package>/<path>` will be resolved as
+  /// `<rootUri>/<packageUri>/<path>`.
+  ///
+  /// If dependencies are installed using `dart pub`, then this is
+  /// **always** `lib/`.
+  ///
+  /// See `packageUri` in the [specification for `package_config.json`][1],
+  /// for details.
+  ///
+  /// [1]: https://github.com/dart-lang/language/blob/main/accepted/2.8/language-versioning/package-config-file-v2.md
+  final Uri packageUri;
+
+  /// Contents of `extension/<targetPackage>/config.yaml` parsed as YAML and
+  /// converted to JSON compatible types.
+  ///
+  /// If parsing YAML from this file failed, then no [Extension] entry
+  /// will exist.
+  ///
+  /// This field is always a structure consisting of the following types:
+  ///  * `null`,
+  ///  * [bool] (`true` or `false`),
+  ///  * [String],
+  ///  * [num] ([int] or [double]),
+  ///  * `List<Object?>`, and,
+  ///  * `Map<String, Object?>`.
+  final Map<String, Object?> config;
+
+  Extension._({
+    required this.package,
+    required this.rootUri,
+    required this.packageUri,
+    required this.config,
+  });
+}
+
+/// Find extensions for [targetPackage] provided by packages in
+/// `.dart_tool/package_config.json`.
+///
+/// ## Locating `.dart_tool/package_config.json`
+///
+/// This method requires the location of the [packageConfig], unless the current
+/// isolate has been setup for package resolution.
+/// Notably, Dart programs compiled for AOT cannot find their own
+/// `package_config.json`.
+///
+/// If operating on a project that isn't the current project, for example, if
+/// you are developing a tool that users are globally activating and then
+/// running against their own projects, and you wish to detect extensions within
+/// their projects, then you must specify the path the
+/// `.dart_tool/package_config.json` for the users project as [packageConfig].
+///
+/// The [packageConfig] parameter must reference a file, absolute or
+/// relative-path, may use the `file://` scheme. This method throws, if
+/// [packageConfig] is not a valid [Uri] for a file-path.
+///
+/// ## Detection of extensions
+///
+/// An extension for [targetPackage] is detected in `package:foo` if `foo`
+/// contains `extension/<targetPackage>/config.yaml`, and the contents of this
+/// file is valid YAML, that can be represented as JSON.
+///
+/// ### Caching results
+///
+/// When [useCache] is `true` then the detected extensions will be cached
+/// in `.dart_tool/extension_discovery/<targetPackage>.json`.
+/// This function will compare modification timestamps of
+/// `.dart_tool/package_config.json` with the cache file, before reusing cached
+/// results.
+/// This function will also treat relative path-dependencies as mutable
+/// packages, and check such packages for extensions every time [findExtensions]
+/// is called. Notably, it'll compare the modification time of the
+/// `extension/<targetPackage>/config.yaml` file, to ensure that it's older than
+/// the extension cache file. Otherwise, it'll reload the extension
+/// configuration.
+///
+/// ## Exceptions
+///
+/// This method will throw [PackageConfigException], if the
+/// `.dart_tool/package_config.json` file specified in [packageConfig] could not
+/// be loaded or is invalid. This usually happens if dependencies are not
+/// resolved, and users can probably address it by running `dart pub get`.
+///
+/// But, **do consider catch** [PackageConfigException] and handling the failure
+/// to load extensions appropriately.
+///
+/// This method will throw an [Error] if [packageConfig] is not specified, and
+/// the current isolate isn't configured for package resolution.
+Future<List<Extension>> findExtensions(
+  String targetPackage, {
+  bool useCache = true,
+  Uri? packageConfig,
+}) async {
+  packageConfig ??= await Isolate.packageConfig;
+  if (packageConfig == null) {
+    throw UnsupportedError(
+      'packageConfigUri must be provided, if not running in JIT mode',
+    );
+  }
+  if ((packageConfig.hasScheme && !packageConfig.isScheme('file')) ||
+      packageConfig.hasEmptyPath ||
+      packageConfig.hasFragment ||
+      packageConfig.hasPort ||
+      packageConfig.hasQuery) {
+    throw ArgumentError.value(
+      packageConfig,
+      'packageConfig',
+      'must be a file:// URI',
+    );
+  }
+  // Always normalize to an absolute URI
+  final packageConfigUri = File.fromUri(packageConfig).absolute.uri;
+
+  return await _findExtensions(
+    targetPackage: targetPackage,
+    useCache: useCache,
+    packageConfigUri: packageConfigUri,
+  );
+}
+
+/// Find extensions with normalized arguments.
+Future<List<Extension>> _findExtensions({
+  required String targetPackage,
+  required bool useCache,
+  required Uri packageConfigUri,
+}) async {
+  final packageConfigFile = File.fromUri(packageConfigUri);
+  final registryFile = File.fromUri(packageConfigFile.parent.uri.resolve(
+    'extension_discovery/$targetPackage.json',
+  ));
+
+  Registry? registry;
+  final registryStat = registryFile.statSync();
+  if (registryStat.isFileOrLink && useCache) {
+    final packageConfigStat = packageConfigFile.statSync();
+    if (!packageConfigStat.isFileOrLink) {
+      throw packageConfigNotFound(packageConfigUri);
+    }
+    if (packageConfigStat.isPossiblyModifiedAfter(registryStat.modified)) {
+      await registryFile.tryDelete();
+    } else {
+      registry = await loadRegistry(registryFile);
+    }
+  }
+
+  final configFileName = 'extension/$targetPackage/config.yaml';
+  var registryUpdated = false;
+  if (registry != null) {
+    // Update mutable entries in registry
+    for (var i = 0; i < registry.length; i++) {
+      final p = registry[i];
+      if (p.rootUri.hasAbsolutePath) continue;
+
+      final rootUri = packageConfigUri.resolveUri(p.rootUri);
+      final configFile = File.fromUri(rootUri.resolve(configFileName));
+      final configStat = configFile.statSync();
+      if (configStat.isFileOrLink) {
+        if (configStat.isPossiblyModifiedAfter(registryStat.modified)) {
+          try {
+            registryUpdated = true;
+            registry[i] = (
+              package: p.package,
+              rootUri: p.rootUri,
+              packageUri: p.packageUri,
+              config: parseYamlFromConfigFile(await configFile.readAsString()),
+            );
+            continue;
+          } on FormatException {
+            // pass
+          } on IOException {
+            // pass
+          }
+          registryUpdated = true;
+          registry[i] = (
+            package: p.package,
+            rootUri: p.rootUri,
+            packageUri: p.packageUri,
+            config: null,
+          );
+        }
+      } else {
+        // If there is no file present, but registry says there is then we need
+        // to update the registry.
+        if (p.config != null) {
+          registryUpdated = true;
+          registry[i] = (
+            package: p.package,
+            rootUri: p.rootUri,
+            packageUri: p.packageUri,
+            config: null,
+          );
+        }
+      }
+    }
+  } else {
+    // Load packages from package_config.json
+    final packages = await loadPackageConfig(packageConfigFile);
+    registryUpdated = true;
+    registry = (await Future.wait(packages.map((p) async {
+      try {
+        final rootUri = packageConfigUri.resolveUri(p.rootUri);
+        final configFile = File.fromUri(rootUri.resolve(configFileName));
+        final configStat = configFile.statSync();
+        if (configStat.isFileOrLink) {
+          return (
+            package: p.name,
+            rootUri: p.rootUri,
+            packageUri: p.packageUri,
+            config: parseYamlFromConfigFile(await configFile.readAsString()),
+          );
+        }
+      } on FormatException {
+        // pass
+      } on IOException {
+        // pass
+      }
+      if (!p.rootUri.hasAbsolutePath) {
+        return (
+          package: p.name,
+          rootUri: p.rootUri,
+          packageUri: p.packageUri,
+          config: null,
+        );
+      }
+      return null;
+    })))
+        .whereType<RegistryEntry>()
+        .toList(growable: false);
+  }
+
+  // Save registry
+  if (registryUpdated && useCache) {
+    await saveRegistry(registryFile, registry);
+  }
+
+  return UnmodifiableListView(
+    registry
+        .where((e) => e.config != null)
+        .map((e) => Extension._(
+              package: e.package,
+              rootUri: packageConfigUri.resolveUri(e.rootUri),
+              packageUri: e.packageUri,
+              config: e.config!,
+            ))
+        .toList(growable: false),
+  );
+}
diff --git a/pkgs/extension_discovery/lib/src/expect_json.dart b/pkgs/extension_discovery/lib/src/expect_json.dart
new file mode 100644
index 0000000..c2784bc
--- /dev/null
+++ b/pkgs/extension_discovery/lib/src/expect_json.dart
@@ -0,0 +1,73 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:convert' show jsonDecode;
+
+Map<String, Object?> decodeJsonMap(String json) {
+  final root = jsonDecode(json);
+  if (root case Map<String, Object?> v) return v;
+  throw const FormatException('root must be a map');
+}
+
+extension ExpectJson on Map<String, Object?> {
+  bool expectBool(String key) {
+    if (this[key] case bool v) return v;
+    throw FormatException('The value at "$key" must be a bool:\n$toString()');
+  }
+
+  num expectNumber(String key) {
+    if (this[key] case num v) return v;
+    throw FormatException('The value at "$key" must be a number:\n$toString()');
+  }
+
+  String expectString(String key) {
+    if (this[key] case String v) return v;
+    throw FormatException('The value at "$key" must be a string:\n$toString()');
+  }
+
+  Uri expectUri(String key) {
+    try {
+      return Uri.parse(expectString(key));
+    } on FormatException {
+      throw FormatException('The value at "$key" must be a URI:\n$toString()');
+    }
+  }
+
+  Map<String, Object?> expectMap(String key) {
+    if (this[key] case Map<String, Object?> v) return v;
+    throw FormatException('The value at "$key" must be a map:\n$toString()');
+  }
+
+  Map<String, Object?>? optionalMap(String key) {
+    if (containsKey(key)) {
+      return expectMap(key);
+    }
+    return null;
+  }
+
+  Uri? optionalUri(String key) {
+    if (containsKey(key)) {
+      return expectUri(key);
+    }
+    return null;
+  }
+
+  List<Object?> expectList(String key) {
+    if (this[key] case List<Object?> v) return v;
+    throw FormatException('The value at "$key" must be a list:\n$toString()');
+  }
+
+  Iterable<Map<String, Object?>> expectListObjects(String key) sync* {
+    final list = expectList(key);
+    for (final entry in list) {
+      if (entry case Map<String, Object?> v) {
+        yield v;
+      } else {
+        throw FormatException(
+          'The value at "$key" must be a list of map:\n$toString()',
+        );
+      }
+    }
+  }
+}
diff --git a/pkgs/extension_discovery/lib/src/io.dart b/pkgs/extension_discovery/lib/src/io.dart
new file mode 100644
index 0000000..9343ced
--- /dev/null
+++ b/pkgs/extension_discovery/lib/src/io.dart
@@ -0,0 +1,84 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:async';
+import 'dart:io'
+    show
+        File,
+        FileStat,
+        FileSystemEntityType,
+        FileSystemException,
+        IOException,
+        Platform;
+
+const _maxAttempts = 20;
+
+/// When comparing modification timestamps of files to see if A is newer than B,
+/// such that data cached in A about B does not need to be recomputed, we
+/// required that A is at-least [modificationMaturityDelay] older than B.
+///
+/// This ensures that if `pub get` is racing with cache writing then we won't
+/// rely on the result.
+Duration modificationMaturityDelay = const Duration(seconds: 5);
+
+/// On windows some renaming files/folders recently created can be problematic
+/// as they may be locked by security scanning systems.
+///
+/// This function will retry [fn] a few times with a short delay, if running on
+/// Windows and the error appears to be related to permissions or file locking.
+Future<T> _attempt<T>(FutureOr<T> Function() fn) async {
+  if (!Platform.isWindows) {
+    return await fn();
+  }
+  var attempts = 0;
+  while (true) {
+    try {
+      await fn();
+    } on FileSystemException catch (e) {
+      attempts += 1;
+      if (attempts >= _maxAttempts) rethrow;
+
+      // Cargo culting error codes from:
+      // https://github.com/dart-lang/pub/blob/98565c3e5defcd80c59910795ba3548552102f2c/lib/src/io.dart#L419-L427
+      final code = e.osError?.errorCode;
+      if (code != 5 && code != 32) rethrow;
+
+      // Sleep a bit a try again.
+      await Future<void>.delayed(const Duration(milliseconds: 5));
+    }
+  }
+}
+
+extension FileExt on File {
+  /// Try to delete this file, ignore errors.
+  Future<void> tryDelete() async {
+    try {
+      await delete();
+    } on IOException {
+      // pass
+    }
+  }
+
+  Future<void> reliablyRename(String newPath) =>
+      _attempt(() => rename(newPath));
+}
+
+extension FileStatExt on FileStat {
+  /// Returns `false` if we're pretty certain that the current file was NOT
+  /// modified after [other].
+  ///
+  /// We do this by subtracting 5 seconds from [other], thus, making it more
+  /// likely that the current file was _possibly modified_ after [other].
+  ///
+  /// This, aims to ensure that file where modified within 5 seconds of
+  /// eachother then we don't trust the file modification stamps. This mostly
+  /// makes sense if someone is updating a file while we're writing the registry
+  /// cache file.
+  bool isPossiblyModifiedAfter(DateTime other) =>
+      modified.isAfter(other.subtract(modificationMaturityDelay));
+
+  /// True, if current [FileStat] is possibly a file (link or file)
+  bool get isFileOrLink =>
+      type == FileSystemEntityType.file || type == FileSystemEntityType.link;
+}
diff --git a/pkgs/extension_discovery/lib/src/package_config.dart b/pkgs/extension_discovery/lib/src/package_config.dart
new file mode 100644
index 0000000..f2eaffc
--- /dev/null
+++ b/pkgs/extension_discovery/lib/src/package_config.dart
@@ -0,0 +1,107 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:io' show File, IOException;
+import 'expect_json.dart';
+
+typedef PackageConfigEntry = ({String name, Uri rootUri, Uri packageUri});
+typedef PackageConfig = List<PackageConfigEntry>;
+
+/// Searches in [packageDir] and all directories above for a
+/// `.dart_tool/package_config.json` file. Returns the Uri of that file if
+/// found.
+///
+/// Returns `null` if no file was found.
+Uri? findPackageConfig(Uri packageDir) {
+  if (!packageDir.isScheme('file')) {
+    throw ArgumentError(
+      'Expected [packageDir] to be a file URI, got $packageDir',
+    );
+  }
+  if (!packageDir.path.endsWith('/')) {
+    packageDir = packageDir.replace(path: '${packageDir.path}/');
+  }
+  while (true) {
+    final packageConfigCandidate =
+        packageDir.resolve('.dart_tool/package_config.json');
+    try {
+      if (File.fromUri(packageConfigCandidate).existsSync()) {
+        return packageConfigCandidate;
+      }
+    } on IOException {
+      return null; // if we get a permission error, etc, we return null
+    }
+    final next = packageDir.resolve('..');
+    if (next == packageDir) return null;
+    packageDir = next;
+  }
+}
+
+/// Load list of packages and associated URIs from the
+/// `.dart_tool/package_config.json` file in [packageConfigFile].
+Future<PackageConfig> loadPackageConfig(
+  File packageConfigFile,
+) async {
+  try {
+    final packageConfig = decodeJsonMap(await packageConfigFile.readAsString());
+    if (packageConfig.expectNumber('configVersion') != 2) {
+      throw const FormatException('"configVersion" must be 2');
+    }
+    return packageConfig.expectListObjects('packages').map((p) {
+      final rootUri = p.expectUri('rootUri').asDirectory();
+      return (
+        name: p.expectString('name'),
+        rootUri: rootUri,
+        packageUri: p.optionalUri('packageUri')?.asDirectory() ?? rootUri,
+      );
+    }).toList();
+  } on IOException catch (e) {
+    if (!packageConfigFile.existsSync()) {
+      throw packageConfigNotFound(packageConfigFile.uri);
+    }
+    throw packageConfigIOException(e);
+  } on FormatException catch (e) {
+    throw packageConfigInvalid(packageConfigFile.uri, e);
+  }
+}
+
+/// Thrown, if the `.dart_tool/package_config.json` cannot be found or parsing
+/// it fails.
+///
+/// This could be because the `package_config.json` file is missing or simply
+/// invalid.
+///
+/// Mostly, this will happen if dependencies are not resolved, the solution is
+/// call `dart pub get`.
+final class PackageConfigException implements Exception {
+  final String message;
+  PackageConfigException._(this.message);
+
+  @override
+  String toString() => message;
+}
+
+PackageConfigException packageConfigNotFound(Uri packageConfigUri) =>
+    PackageConfigException._(
+      'package_config.json not found at: "$packageConfigUri"',
+    );
+
+PackageConfigException packageConfigInvalid(
+        Uri packageConfigUri, FormatException e) =>
+    PackageConfigException._(
+      'Invalid package_config.json found at "$packageConfigUri": $e',
+    );
+
+PackageConfigException packageConfigIOException(IOException e) =>
+    PackageConfigException._(
+      'Failed to read package_config.json: $e',
+    );
+
+extension on Uri {
+  Uri asDirectory() => replace(
+        pathSegments: pathSegments.lastOrNull != ''
+            ? pathSegments.followedBy([''])
+            : pathSegments,
+      );
+}
diff --git a/pkgs/extension_discovery/lib/src/registry.dart b/pkgs/extension_discovery/lib/src/registry.dart
new file mode 100644
index 0000000..60efc75
--- /dev/null
+++ b/pkgs/extension_discovery/lib/src/registry.dart
@@ -0,0 +1,144 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:convert' show jsonEncode;
+import 'dart:io' show File, FileSystemEntityType, IOException;
+
+import 'expect_json.dart';
+import 'io.dart';
+
+// TODO: Convert the 'rootUri' reference below to a doc comment reference once
+// https://github.com/dart-lang/linter/issues/4645 is addressed.
+
+/// Entry in the `.dart_tool/extension_discovery/<package>.json` file.
+///
+/// If the `rootUri` is not an absolute path, then we will assume that the
+/// package is mutable (either it's the root package or a path dependency).
+/// If there is no extension config file for a mutable package, then we will
+/// still store a [RegistryEntry] with `config = null`. Because everytime we
+/// load the registry, we still need to check if a configuration file has been
+/// added to the mutable package.
+typedef RegistryEntry = ({
+  String package,
+  Uri rootUri,
+  Uri packageUri,
+  Map<String, Object?>? config,
+});
+
+typedef Registry = List<RegistryEntry>;
+
+Future<Registry?> loadRegistry(File registryFile) async {
+  try {
+    final registryJson = decodeJsonMap(await registryFile.readAsString());
+    if (registryJson.expectNumber('version') != 2) {
+      throw const FormatException('"version" must be 2');
+    }
+    return registryJson
+        .expectListObjects('entries')
+        .map((e) => (
+              package: e.expectString('package'),
+              rootUri: e.expectUri('rootUri'),
+              packageUri: e.expectUri('packageUri'),
+              config: e.optionalMap('config'),
+            ))
+        .toList(growable: false);
+  } on IOException {
+    return null; // pass
+  } on FormatException {
+    await registryFile.tryDelete();
+    return null;
+  }
+}
+
+Future<void> saveRegistry(
+  File registryFile,
+  Registry registry,
+) async {
+  try {
+    if (!registryFile.parent.existsSync()) {
+      await registryFile.parent.create();
+    }
+    final tmpFile = File('${registryFile.path}.tmp');
+    final tmpFileStat = tmpFile.statSync();
+    if (tmpFileStat.type != FileSystemEntityType.notFound) {
+      final tmpAge = DateTime.now().difference(tmpFileStat.modified);
+      if (tmpAge.inSeconds < 5) {
+        // Don't try to write registry, if there is an abandoned temporary file
+        // no older than 5 seconds. Otherwise, we could have race conditions!
+        // Note: That saving the registry is a performance improvement, not a
+        //       strict necessity!
+        return;
+      } else {
+        await tmpFile.delete();
+      }
+    }
+
+    await tmpFile.writeAsString(jsonEncode({
+      'version': 2,
+      'entries': registry
+          .map((e) => {
+                'package': e.package,
+                'rootUri': e.rootUri.toString(),
+                'packageUri': e.packageUri.toString(),
+                if (e.config != null) 'config': e.config,
+              })
+          .toList(),
+    }));
+    await tmpFile.reliablyRename(registryFile.path);
+    await _ensureReadme(
+      File.fromUri(registryFile.parent.uri.resolve('README.md')),
+    );
+  } on IOException {
+    // pass
+  }
+}
+
+Future<void> _ensureReadme(File readmeFile) async {
+  try {
+    final stat = readmeFile.statSync();
+    if (stat.type != FileSystemEntityType.notFound) {
+      final age = DateTime.now().difference(stat.modified);
+      if (age.inDays < 5) {
+        return; // don't update README.md, if it's less than 5 days old
+      }
+    }
+    await readmeFile.writeAsString(_readmeContents);
+  } on IOException {
+    // pass
+  }
+}
+
+const _readmeContents = '''
+Extension Discovery Cache
+=========================
+
+This folder is used by `package:extension_discovery` to cache lists of
+packages that contains extensions for other packages.
+
+DO NOT USE THIS FOLDER
+----------------------
+
+ * Do not read (or rely) the contents of this folder.
+ * Do write to this folder.
+
+If you're interested in the lists of extensions stored in this folder use the
+API offered by package `extension_discovery` to get this information.
+
+If this package doesn't work for your use-case, then don't try to read the
+contents of this folder. It may change, and will not remain stable.
+
+Use package `extension_discovery`
+---------------------------------
+
+If you want to access information from this folder.
+
+Feel free to delete this folder
+-------------------------------
+
+Files in this folder act as a cache, and the cache is discarded if the files
+are older than the modification time of `.dart_tool/package_config.json`.
+
+Hence, it should never be necessary to clear this cache manually, if you find a
+need to do please file a bug.
+''';
diff --git a/pkgs/extension_discovery/lib/src/yaml_config_format.dart b/pkgs/extension_discovery/lib/src/yaml_config_format.dart
new file mode 100644
index 0000000..a28b31b
--- /dev/null
+++ b/pkgs/extension_discovery/lib/src/yaml_config_format.dart
@@ -0,0 +1,85 @@
+// Copyright (c) 2023, 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.
+
+/// Utilities for loading and validating YAML from a config file.
+///
+/// When writing YAML config files it's often preferable to force a few
+/// constraints on the YAML files. Specifically:
+///  * Root value must be a map.
+///  * No anchors / aliases, this can't be represented in JSON and
+///    can be used to created cycles, which might crash someone trying to
+///    serialize the data as JSON.
+///  * Maps can only have string keys.
+///
+/// Basically, only allow value that can't be represented in JSON.
+///
+/// This library aims to provide a [parseYamlFromConfigFile] that throws
+/// a [FormatException] when parsing YAML files that doesn't satisfy this
+/// constraint.
+library;
+
+import 'package:yaml/yaml.dart'
+    show YamlList, YamlMap, YamlNode, YamlScalar, loadYamlNode;
+
+/// Parse YAML from a config file.
+///
+/// This will validate that:
+///  * Maps only have string keys.
+///  * Anchor and aliases are not used (to avoid cycles).
+///  * Values can be represented as JSON.
+///  * Root node is a map.
+///
+/// Throw will throw [FormatException], if the [yamlString] does not satisfy
+/// constraints above.
+///
+/// Returns a structure consisting of the following types:
+///  * `null`,
+///  * [bool] (`true` or `false`),
+///  * [String],
+///  * [num] ([int] or [double]),
+///  * `List<Object?>`, and,
+///  * `Map<String, Object?>`.
+Map<String, Object?> parseYamlFromConfigFile(String yamlString) {
+  final visited = <YamlNode>{};
+  Object? toPlainType(YamlNode n) {
+    if (!visited.add(n)) {
+      throw const FormatException(
+        'Anchors/aliases are not supported in YAML config files',
+      );
+    }
+    if (n is YamlScalar) {
+      return switch (n.value) {
+        null => null,
+        String s => s,
+        num n => n,
+        bool b => b,
+        _ => throw const FormatException(
+            'Only null, string, number, bool, map and lists are supported '
+            'in YAML config files',
+          ),
+      };
+    }
+    if (n is YamlList) {
+      return n.nodes.map(toPlainType).toList();
+    }
+    if (n is YamlMap) {
+      return n.nodes.map((key, value) {
+        final k = toPlainType(key as YamlNode);
+        if (k is! String) {
+          throw const FormatException(
+            'Only string keys are allowed in YAML config files',
+          );
+        }
+        return MapEntry(k, toPlainType(value));
+      });
+    }
+    throw UnsupportedError('Unknown YamlNode: $n');
+  }
+
+  final value = toPlainType(loadYamlNode(yamlString));
+  if (value is! Map<String, Object?>) {
+    throw const FormatException('The root of a YAML config file must be a map');
+  }
+  return value;
+}
diff --git a/pkgs/extension_discovery/pubspec.yaml b/pkgs/extension_discovery/pubspec.yaml
new file mode 100644
index 0000000..05acdbd
--- /dev/null
+++ b/pkgs/extension_discovery/pubspec.yaml
@@ -0,0 +1,17 @@
+name: extension_discovery
+description: >-
+  A convention and utilities for package extension discovery.
+version: 2.1.0
+repository: https://github.com/dart-lang/tools/tree/main/pkgs/extension_discovery
+
+environment:
+  sdk: ^3.4.0
+
+dependencies:
+  yaml: ^3.0.0
+
+dev_dependencies:
+  collection: ^1.18.0
+  dart_flutter_team_lints: ^3.0.0
+  test: ^1.21.0
+  test_descriptor: ^2.0.1
diff --git a/pkgs/extension_discovery/test/find_extensions_test.dart b/pkgs/extension_discovery/test/find_extensions_test.dart
new file mode 100644
index 0000000..33e8bf7
--- /dev/null
+++ b/pkgs/extension_discovery/test/find_extensions_test.dart
@@ -0,0 +1,350 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:isolate' show Isolate;
+
+import 'package:extension_discovery/extension_discovery.dart';
+import 'package:extension_discovery/src/io.dart';
+import 'package:test/test.dart';
+
+import 'test_descriptor.dart' as d;
+
+void main() {
+  test('findExtensions', () async {
+    // Override the maturity delay for reliable testing of caching logic.
+    modificationMaturityDelay = const Duration(milliseconds: 500);
+
+    final pkgLibDir = await Isolate.resolvePackageUri(
+      Uri.parse('package:extension_discovery/'),
+    );
+    final pkgDir = pkgLibDir!.resolve('..');
+
+    await d.dir('myapp', [
+      d.pubspec({
+        'name': 'myapp',
+        'dependencies': {
+          'extension_discovery': {'path': pkgDir.toFilePath()},
+        },
+        'environment': {'sdk': '^3.0.0'},
+      }),
+    ]).create();
+
+    // Get dependencies
+    await d.dartPubGet(d.path('myapp'));
+
+    // Check that we don't find any extensions
+    expect(
+        await findExtensions(
+          'myapp',
+          packageConfig: d.fileUri('myapp/.dart_tool/package_config.json'),
+        ),
+        isEmpty);
+
+    // Check that there is a myapp.json cache file
+    await d
+        .file(
+          'myapp/.dart_tool/extension_discovery/myapp.json',
+          isNotEmpty,
+        )
+        .validate();
+
+    // ################################## Create foo that provides extension
+    await d.dir('foo', [
+      d.pubspec({
+        'name': 'foo',
+        'environment': {'sdk': '^3.0.0'},
+      }),
+      // It has a config.yaml for myapp
+      d.dir('extension/myapp', [
+        d.json('config.yaml', {'fromFoo': true}),
+      ]),
+    ]).create();
+
+    // Update the pubspec.yaml with a dependency on foo
+    await d.dir('myapp', [
+      d.pubspec({
+        'name': 'myapp',
+        'dependencies': {
+          'extension_discovery': {'path': pkgDir.toFilePath()},
+          'foo': {'path': '../foo'},
+        },
+        'environment': {'sdk': '^3.0.0'},
+      }),
+    ]).create();
+
+    // Get dependencies
+    await d.dartPubGet(d.path('myapp'));
+
+    // Check that we do find an extension
+    {
+      final ext = await findExtensions(
+        'myapp',
+        packageConfig: d.fileUri('myapp/.dart_tool/package_config.json'),
+      );
+      expect(ext, isNotEmpty);
+      expect(
+        ext.any(
+          (e) =>
+              e.package == 'foo' &&
+              e.rootUri == d.directoryUri('foo/') &&
+              e.packageUri == Uri.parse('lib/') &&
+              e.config['fromFoo'] == true,
+        ),
+        isTrue,
+      );
+    }
+
+    // ################################## Modify the config
+    await d.json('foo/extension/myapp/config.yaml', {'fromFoo': 42}).create();
+
+    // Check that we do find an extension
+    {
+      final ext = await findExtensions(
+        'myapp',
+        packageConfig: d.fileUri('myapp/.dart_tool/package_config.json'),
+      );
+      expect(ext, isNotEmpty);
+      expect(
+        ext.any(
+          (e) =>
+              e.package == 'foo' &&
+              e.rootUri == d.directoryUri('foo/') &&
+              e.packageUri == Uri.parse('lib/') &&
+              e.config['fromFoo'] == 42,
+        ),
+        isTrue,
+      );
+    }
+
+    // ################################## Make config invalid
+    await d.file('foo/extension/myapp/config.yaml', 'invalid YAML').create();
+
+    // Check that we do not find extensions
+    {
+      final ext = await findExtensions(
+        'myapp',
+        packageConfig: d.fileUri('myapp/.dart_tool/package_config.json'),
+      );
+      expect(ext, isEmpty);
+    }
+
+    // ################################## Make config valid again
+    await d.json('foo/extension/myapp/config.yaml', {'fromFoo': true}).create();
+
+    // Check that we do find extensions
+    {
+      final ext = await findExtensions(
+        'myapp',
+        packageConfig: d.fileUri('myapp/.dart_tool/package_config.json'),
+      );
+      expect(ext, isNotEmpty);
+    }
+
+    // ################################## Remove config file
+    await d.file('foo/extension/myapp/config.yaml').io.delete();
+    // Check that we do not find extensions
+    {
+      final ext = await findExtensions(
+        'myapp',
+        packageConfig: d.fileUri('myapp/.dart_tool/package_config.json'),
+      );
+      expect(ext, isEmpty);
+    }
+
+    // ################################## Make config valid again
+    await d.json('foo/extension/myapp/config.yaml', {'fromFoo': true}).create();
+
+    // Check that we do find extensions
+    {
+      final ext = await findExtensions(
+        'myapp',
+        packageConfig: d.fileUri('myapp/.dart_tool/package_config.json'),
+      );
+      expect(ext, isNotEmpty);
+    }
+
+    // ################################## Create bar as absolute path-dep
+    await d.dir('bar', [
+      d.pubspec({
+        'name': 'bar',
+        'environment': {'sdk': '^3.0.0'},
+      }),
+      // It has a config.yaml for myapp
+      d.dir('extension/myapp', [
+        d.json('config.yaml', {'fromFoo': false}),
+      ]),
+    ]).create();
+
+    // Update the pubspec.yaml with a dependency on foo
+    await d.dir('myapp', [
+      d.pubspec({
+        'name': 'myapp',
+        'dependencies': {
+          'extension_discovery': {'path': pkgDir.toFilePath()},
+          'foo': {'path': '../foo'},
+          'bar': {'path': d.path('bar')},
+        },
+        'environment': {'sdk': '^3.0.0'},
+      }),
+    ]).create();
+
+    // We won't find bar without running `dart pub get`
+    {
+      final ext = await findExtensions(
+        'myapp',
+        packageConfig: d.fileUri('myapp/.dart_tool/package_config.json'),
+      );
+      expect(ext.any((e) => e.package == 'bar'), isFalse);
+    }
+
+    // Get dependencies
+    await d.dartPubGet(d.path('myapp'));
+
+    // Check that we do find both extensions
+    {
+      final ext = await findExtensions(
+        'myapp',
+        packageConfig: d.fileUri('myapp/.dart_tool/package_config.json'),
+      );
+      expect(ext, isNotEmpty);
+      expect(
+        ext.any(
+          (e) =>
+              e.package == 'foo' &&
+              e.rootUri == d.directoryUri('foo/') &&
+              e.packageUri == Uri.parse('lib/') &&
+              e.config['fromFoo'] == true,
+        ),
+        isTrue,
+      );
+      expect(
+        ext.any(
+          (e) =>
+              e.package == 'bar' &&
+              e.rootUri == d.directoryUri('bar/') &&
+              e.packageUri == Uri.parse('lib/') &&
+              e.config['fromFoo'] == false,
+        ),
+        isTrue,
+      );
+    }
+
+    // ################################## Changes to bar are not detected
+
+    // Ensure that we wait long enough for the cache to be trusted,
+    // this delay is to make sure that the logic we have handling races isn't
+    // triggered. Think of it as waiting...
+    // If the modification time of package_config.json and the cache is no more
+    // than [modificationMaturityDelay] time apart, we'll ignore the cache.
+    // Under the assumption that there was a tiny risk of a race condition.
+    await Future<void>.delayed(modificationMaturityDelay * 2);
+    // Ensure that we have a cache value!
+    await findExtensions(
+      'myapp',
+      packageConfig: d.fileUri('myapp/.dart_tool/package_config.json'),
+    );
+
+    // Delete config from package that has an absolute path, hence, a package
+    // we assume to be immutable.
+    await d.file('bar/extension/myapp/config.yaml').io.delete();
+
+    // Check that we do find both extensions
+    {
+      final ext = await findExtensions(
+        'myapp',
+        packageConfig: d.fileUri('myapp/.dart_tool/package_config.json'),
+      );
+      expect(ext.any((e) => e.package == 'foo'), isTrue);
+      // This is the wrong result, but it is expected. Essentially, if we expect
+      // that if you have packages in package_config.json using an absolute path
+      // then these won't be modified. If you do modify the
+      //   extension/<targetPackage>/config.yaml
+      // file, then the cache will give the wrong result. The workaround is to
+      // touch `package_config.json`, or run `dart pub get` (essentially).
+      expect(ext.any((e) => e.package == 'bar'), isTrue);
+    }
+
+    // Get dependencies
+    await d.dartPubGet(d.path('myapp'));
+
+    // We won't find bar after `dart pub get`, because we removed the config
+    {
+      final ext = await findExtensions(
+        'myapp',
+        packageConfig: d.fileUri('myapp/.dart_tool/package_config.json'),
+      );
+      expect(ext.any((e) => e.package == 'foo'), isTrue);
+      expect(ext.any((e) => e.package == 'bar'), isFalse);
+    }
+
+    // ################################## Sanity check bar and foo
+    expect(
+      await findExtensions(
+        'foo',
+        packageConfig: d.fileUri('myapp/.dart_tool/package_config.json'),
+      ),
+      isEmpty,
+    );
+    expect(
+      await findExtensions(
+        'bar',
+        packageConfig: d.fileUri('myapp/.dart_tool/package_config.json'),
+      ),
+      isEmpty,
+    );
+
+    // ################################## What if foo has extensions for bar
+    await d.dir('foo/extension/bar', [
+      d.json('config.yaml', {'fromFoo': true}),
+    ]).create();
+
+    {
+      final ext = await findExtensions(
+        'bar',
+        packageConfig: d.fileUri('myapp/.dart_tool/package_config.json'),
+      );
+      expect(ext.any((e) => e.package == 'foo'), isTrue);
+      expect(ext.any((e) => e.package == 'bar'), isFalse);
+      expect(ext.any((e) => e.package == 'myapp'), isFalse);
+    }
+
+    // ################################## myapp could also extend bar
+    await d.dir('myapp/extension/bar', [
+      d.json('config.yaml', {'fromFoo': false}),
+    ]).create();
+
+    {
+      final ext = await findExtensions(
+        'bar',
+        packageConfig: d.fileUri('myapp/.dart_tool/package_config.json'),
+      );
+      expect(ext.any((e) => e.package == 'foo'), isTrue);
+      expect(ext.any((e) => e.package == 'bar'), isFalse);
+      expect(ext.any((e) => e.package == 'myapp'), isTrue);
+    }
+
+    // ################################## config could also be written in YAML
+    await d.dir('myapp/extension/bar', [
+      d.file('config.yaml', '''
+writtenAsYaml: true
+'''),
+    ]).create();
+
+    {
+      final ext = await findExtensions(
+        'bar',
+        packageConfig: d.fileUri('myapp/.dart_tool/package_config.json'),
+      );
+      expect(ext.any((e) => e.package == 'foo'), isTrue);
+      expect(ext.any((e) => e.package == 'bar'), isFalse);
+      expect(ext.any((e) => e.package == 'myapp'), isTrue);
+      expect(
+        ext.any(
+          (e) => e.package == 'myapp' && e.config['writtenAsYaml'] == true,
+        ),
+        isTrue,
+      );
+    }
+  });
+}
diff --git a/pkgs/extension_discovery/test/integration_test.dart b/pkgs/extension_discovery/test/integration_test.dart
new file mode 100644
index 0000000..ec52265
--- /dev/null
+++ b/pkgs/extension_discovery/test/integration_test.dart
@@ -0,0 +1,134 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:convert' show jsonDecode;
+import 'dart:isolate' show Isolate;
+
+import 'package:test/test.dart';
+
+import 'test_descriptor.dart' as d;
+
+typedef Ext = ({
+  String package,
+  String rootUri,
+  String packageUri,
+  dynamic config
+});
+
+void main() {
+  test('findExtensions', () async {
+    final pkgLibDir = await Isolate.resolvePackageUri(
+      Uri.parse('package:extension_discovery/'),
+    );
+    final pkgDir = pkgLibDir!.resolve('..');
+
+    await d.dir('myapp', [
+      d.pubspec({
+        'name': 'myapp',
+        'dependencies': {
+          'extension_discovery': {'path': pkgDir.toFilePath()},
+        },
+        'environment': {'sdk': '^3.0.0'},
+      }),
+      d.dir('bin', [
+        d.file('find_extensions.dart', '''
+import 'dart:convert' show JsonEncoder;
+import 'package:extension_discovery/extension_discovery.dart';
+
+Future<void> main(List<String> args) async {
+  final extensions = await findExtensions(args.first);
+  print(JsonEncoder.withIndent('  ').convert([
+    for (final e in extensions)
+      {
+        'package': e.package,
+        'rootUri': e.rootUri.toString(),
+        'packageUri': e.packageUri.toString(),
+        'config': e.config,
+      },
+  ]));
+}
+        '''),
+      ])
+    ]).create();
+
+    Future<List<Ext>> findExtensionsInSandbox(String target) async {
+      final out = await d.dart(
+        d.path('myapp/bin/find_extensions.dart'),
+        target,
+      );
+      return (jsonDecode(out) as List<Object?>)
+          .cast<Map>()
+          .map((e) => (
+                package: e['package'] as String,
+                rootUri: e['rootUri'] as String,
+                packageUri: e['packageUri'] as String,
+                config: e['config'],
+              ))
+          .toList();
+    }
+
+    // Get dependencies
+    await d.dartPubGet(d.path('myapp'));
+
+    // Check that we don't find any extensions
+    expect(await findExtensionsInSandbox('myapp'), isEmpty);
+
+    // Check that there is a myapp.json cache file
+    await d
+        .file(
+          'myapp/.dart_tool/extension_discovery/myapp.json',
+          isNotEmpty,
+        )
+        .validate();
+
+    // Check that there is README.md
+    await d
+        .file(
+          'myapp/.dart_tool/extension_discovery/README.md',
+          isNotEmpty,
+        )
+        .validate();
+
+    // Create a foo package
+    await d.dir('foo', [
+      d.pubspec({
+        'name': 'foo',
+        'environment': {'sdk': '^3.0.0'},
+      }),
+      // It has a config.yaml for myapp
+      d.dir('extension/myapp', [
+        d.json('config.yaml', {'fromFoo': true}),
+      ]),
+    ]).create();
+
+    // Update the pubspec.yaml with a dependency on foo
+    await d.dir('myapp', [
+      d.pubspec({
+        'name': 'myapp',
+        'dependencies': {
+          'extension_discovery': {'path': pkgDir.toFilePath()},
+          'foo': {'path': '../foo'},
+        },
+        'environment': {'sdk': '^3.0.0'},
+      }),
+    ]).create();
+
+    // Get dependencies
+    await d.dartPubGet(d.path('myapp'));
+
+    // Check that we do find an extension
+    final ext = await findExtensionsInSandbox('myapp');
+    expect(ext, isNotEmpty);
+    expect(
+      ext.any(
+        (e) =>
+            e.package == 'foo' &&
+            e.rootUri == d.directoryUri('foo/').toString() &&
+            e.packageUri == Uri.parse('lib/').toString() &&
+            (e.config as Map)['fromFoo'] == true,
+      ),
+      isTrue,
+    );
+  });
+}
diff --git a/pkgs/extension_discovery/test/package_config_test.dart b/pkgs/extension_discovery/test/package_config_test.dart
new file mode 100644
index 0000000..83c6c4d
--- /dev/null
+++ b/pkgs/extension_discovery/test/package_config_test.dart
@@ -0,0 +1,192 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:convert' show jsonDecode, jsonEncode;
+
+import 'package:extension_discovery/src/package_config.dart';
+import 'package:test/test.dart';
+
+import 'test_descriptor.dart' as d;
+
+void main() {
+  test('loadPackageConfig', () async {
+    await d.dir('myapp', [
+      d.pubspec({
+        'name': 'myapp',
+        'dependencies': {},
+        'environment': {'sdk': '^3.0.0'},
+      }),
+    ]).create();
+
+    final packageConfigFile = d.file('myapp/.dart_tool/package_config.json').io;
+
+    // Loading before `dart pub get` throws PackageConfigException
+    expect(
+      loadPackageConfig(packageConfigFile),
+      throwsA(isA<PackageConfigException>()),
+    );
+
+    // Get dependencies
+    await d.dartPubGet(d.path('myapp'));
+
+    // Parse package_config
+    {
+      final packages = await loadPackageConfig(packageConfigFile);
+      expect(packages, isNotEmpty);
+      expect(packages.any((p) => p.name == 'myapp'), isTrue);
+      expect(packages.any((p) => p.name == 'foo'), isFalse);
+      expect(packages.any((p) => p.name == 'bar'), isFalse);
+    }
+
+    // ################################## Create foo as relative path-dep
+    await d.dir('foo', [
+      d.pubspec({
+        'name': 'foo',
+        'environment': {'sdk': '^3.0.0'},
+      }),
+    ]).create();
+
+    // Update the pubspec.yaml with a dependency on foo
+    await d.dir('myapp', [
+      d.pubspec({
+        'name': 'myapp',
+        'dependencies': {
+          'foo': {'path': '../foo'},
+        },
+        'environment': {'sdk': '^3.0.0'},
+      }),
+    ]).create();
+
+    // Get dependencies
+    await d.dartPubGet(d.path('myapp'));
+
+    // Parse package_config
+    {
+      final packages = await loadPackageConfig(packageConfigFile);
+      expect(packages, isNotEmpty);
+      expect(packages.any((p) => p.name == 'myapp'), isTrue);
+      expect(packages.any((p) => p.name == 'foo'), isTrue);
+      expect(packages.any((p) => p.name == 'bar'), isFalse);
+    }
+
+    // ################################## Create bar as absolute path-dep
+
+    await d.dir('bar', [
+      d.pubspec({
+        'name': 'bar',
+        'environment': {'sdk': '^3.0.0'},
+      }),
+    ]).create();
+
+    // Update the pubspec.yaml with a dependency on foo
+    await d.dir('myapp', [
+      d.pubspec({
+        'name': 'myapp',
+        'dependencies': {
+          'foo': {'path': '../foo'},
+          'bar': {'path': d.path('bar')},
+        },
+        'environment': {'sdk': '^3.0.0'},
+      }),
+    ]).create();
+
+    // Get dependencies
+    await d.dartPubGet(d.path('myapp'));
+
+    // Parse package_config
+    {
+      final packages = await loadPackageConfig(packageConfigFile);
+      expect(packages, isNotEmpty);
+      expect(packages.any((p) => p.name == 'myapp'), isTrue);
+      expect(packages.any((p) => p.name == 'foo'), isTrue);
+      expect(packages.any((p) => p.name == 'bar'), isTrue);
+    }
+
+    // ################################## Cannot read version 99
+
+    {
+      final pkgcfg = jsonDecode(packageConfigFile.readAsStringSync()) as Map;
+      pkgcfg['configVersion'] = 99;
+      packageConfigFile.writeAsStringSync(jsonEncode(pkgcfg));
+    }
+
+    // Loading before `dart pub get` throws PackageConfigException
+    expect(
+      loadPackageConfig(packageConfigFile),
+      throwsA(isA<PackageConfigException>()),
+    );
+
+    // ################################## packageUri is optional
+
+    // Get dependencies
+    await d.dartPubGet(d.path('myapp'));
+
+    {
+      final pkgcfg = jsonDecode(packageConfigFile.readAsStringSync()) as Map;
+      for (final p in pkgcfg['packages'] as List) {
+        (p as Map).remove('packageUri');
+      }
+      packageConfigFile.writeAsStringSync(jsonEncode(pkgcfg));
+    }
+
+    // Parse package_config
+    {
+      final packages = await loadPackageConfig(packageConfigFile);
+      expect(packages, isNotEmpty);
+      expect(packages.any((p) => p.name == 'myapp'), isTrue);
+      expect(packages.any((p) => p.name == 'foo'), isTrue);
+      expect(packages.any((p) => p.name == 'bar'), isTrue);
+      expect(packages.every((p) => p.rootUri == p.packageUri), isTrue);
+    }
+
+    // ################################## packageUri is optional
+
+    // Get dependencies
+    await d.dartPubGet(d.path('myapp'));
+
+    {
+      final pkgcfg = jsonDecode(packageConfigFile.readAsStringSync()) as Map;
+      for (final p in pkgcfg['packages'] as List) {
+        (p as Map).remove('rootUri');
+      }
+      packageConfigFile.writeAsStringSync(jsonEncode(pkgcfg));
+    }
+
+    // Loading before `dart pub get` throws PackageConfigException
+    expect(
+      loadPackageConfig(packageConfigFile),
+      throwsA(isA<PackageConfigException>()),
+    );
+  });
+
+  test('`findPackageConfig()`', () async {
+    await d.dir('workspace', [
+      d.dir('.dart_tool', [
+        d.file('package_config.json'),
+      ]),
+      d.dir('myapp', [])
+    ]).create();
+
+    expect(
+      findPackageConfig(d.fileUri('workspace')),
+      d.fileUri('workspace/.dart_tool/package_config.json'),
+    );
+    expect(
+      findPackageConfig(d.fileUri('workspace/')),
+      d.fileUri('workspace/.dart_tool/package_config.json'),
+    );
+    expect(
+      findPackageConfig(d.fileUri('workspace/myapp')),
+      d.fileUri('workspace/.dart_tool/package_config.json'),
+    );
+    expect(
+      findPackageConfig(d.fileUri('.')),
+      isNull,
+    );
+    expect(
+      findPackageConfig(d.fileUri('foo')),
+      isNull,
+    );
+  });
+}
diff --git a/pkgs/extension_discovery/test/test_descriptor.dart b/pkgs/extension_discovery/test/test_descriptor.dart
new file mode 100644
index 0000000..0bd4a63
--- /dev/null
+++ b/pkgs/extension_discovery/test/test_descriptor.dart
@@ -0,0 +1,56 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:convert' show JsonEncoder;
+import 'dart:io' show Platform, Process;
+
+import 'package:test/test.dart';
+import 'package:test_descriptor/test_descriptor.dart' as d;
+export 'package:test_descriptor/test_descriptor.dart';
+
+d.FileDescriptor json(String fileName, Object? json) =>
+    d.file(fileName, const JsonEncoder.withIndent('  ').convert(json));
+
+d.FileDescriptor pubspec(Map<String, Object?> pubspec) =>
+    json('pubspec.yaml', pubspec);
+
+Uri fileUri(String path) => Uri.file(d.path(path));
+Uri directoryUri(String path) => Uri.directory(d.path(path));
+
+Future<String> dart([
+  String? arg1,
+  String? arg2,
+  String? arg3,
+  String? arg4,
+  String? arg5,
+  String? arg6,
+  String? arg7,
+  String? arg8,
+]) async {
+  final arguments = [
+    if (arg1 != null) arg1,
+    if (arg2 != null) arg2,
+    if (arg3 != null) arg3,
+    if (arg4 != null) arg4,
+    if (arg5 != null) arg5,
+    if (arg6 != null) arg6,
+    if (arg7 != null) arg7,
+    if (arg8 != null) arg8,
+  ];
+  final result = await Process.run(
+    Platform.executable,
+    arguments,
+    workingDirectory: d.sandbox,
+  );
+  if (result.exitCode != 0) {
+    print(result.stderr);
+    print(result.stdout);
+  }
+  expect(result.exitCode, 0,
+      reason: 'failed executing "dart ${arguments.join(' ')}"');
+  return result.stdout as String;
+}
+
+Future<String> dartPubGet(String folder) async =>
+    await dart('pub', 'get', '-C', folder);
diff --git a/pkgs/extension_discovery/test/yaml_config_format_test.dart b/pkgs/extension_discovery/test/yaml_config_format_test.dart
new file mode 100644
index 0000000..0e3f568
--- /dev/null
+++ b/pkgs/extension_discovery/test/yaml_config_format_test.dart
@@ -0,0 +1,149 @@
+// Copyright (c) 2023, 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.
+
+import 'package:collection/collection.dart' show DeepCollectionEquality;
+
+import 'package:extension_discovery/src/yaml_config_format.dart';
+import 'package:test/test.dart';
+
+void _testInvalid(String name, String yaml, {String match = ''}) {
+  test(name, () {
+    expect(
+      () => parseYamlFromConfigFile(yaml),
+      throwsA(isFormatException.having(
+        (e) => e.message,
+        'message',
+        contains(match),
+      )),
+    );
+  });
+}
+
+void _testValid(String name, String yaml) {
+  test(name, () {
+    parseYamlFromConfigFile(yaml);
+  });
+}
+
+void main() {
+  group('parseYamlFromConfigFile', () {
+    group('root must be a map', () {
+      _testInvalid('empty string', '', match: 'map');
+      _testInvalid('null', 'null', match: 'map');
+      _testInvalid('list', '[]', match: 'map');
+      _testInvalid('number (1)', '42', match: 'map');
+      _testInvalid('number (2)', '42.2', match: 'map');
+      _testInvalid('bool (1)', 'true', match: 'map');
+      _testInvalid('bool (2)', 'false', match: 'map');
+      _testInvalid('string', '"hello world"', match: 'map');
+    });
+
+    _testInvalid('must not have alias', match: 'alias', '''
+      keyA: &myref
+        - value 1
+        - value 2
+      KeyB: *myref
+    ''');
+
+    // it works without aliases
+    _testValid('listed inside a map is fine', '''
+      keyA:
+        - value 1
+        - value 2
+      KeyB:
+        - value 1
+        - value 2
+    ''');
+
+    _testValid('comments are cool', '''
+      keyA:
+        - value 1 # this is fine
+        - value 2
+    ''');
+
+    _testInvalid(
+        'Top-level map with integer keys is not allowed', match: 'key', '''
+        42: "value"   # this is NOT fine
+        43: true
+    ''');
+
+    _testValid('Map with quoted integer keys is fine', '''
+        "42": "value"   # this is fine
+        '43': true
+    ''');
+
+    _testInvalid('Map with integer keys is not allowed', match: 'key', '''
+      keyA:
+        - value 1 # this is fine
+        - value 2
+      KeyB:
+        42: value 3 # this is NOT fine
+    ''');
+
+    _testInvalid('Map with list keys is not allowed', match: 'key', '''
+      keyA:
+        - [1, 2, 3] # this is fine, crazy but fine!
+      keyB:
+        [1, 2, 3]: value 3 # this is NOT fine
+    ''');
+
+    _testInvalid('Map with boolean keys is not allowed (1)', match: 'key', '''
+      keyA: true
+      keyB:
+        true: value 3 # this is NOT fine
+    ''');
+
+    _testInvalid('Map with boolean keys is not allowed (2)', match: 'key', '''
+      keyA: true
+      keyB:
+        false: value 3 # this is NOT fine
+    ''');
+
+    _testInvalid('Map with null keys is not allowed', match: 'key', '''
+      keyA: null # fine
+      keyB:
+        null: value 3 # this is NOT fine
+    ''');
+
+    _testValid('complex structures is fine', '''
+      keyA: |
+        multi-line
+        string
+      keyB: 42    # number
+      keyC: 42.2  # double
+      keyD: [1, 2]
+      keyE:
+      - 1
+      - 2
+      keyF:
+        k: "v"
+    ''');
+
+    test('complex structures matches the same JSON', () {
+      final yaml = '''
+        keyA: "hello"
+        keyB: 42    # number
+        keyC: 42.2  # double
+        keyD: [1, 2]
+        keyE:
+        - 1
+        - 2
+        keyF:
+          k: "v"
+      ''';
+      final data = parseYamlFromConfigFile(yaml);
+      expect(
+        const DeepCollectionEquality().equals(data, {
+          'keyA': 'hello',
+          'keyB': 42,
+          'keyC': 42.2,
+          'keyD': [1, 2],
+          'keyE': [1, 2],
+          'keyF': {'k': 'v'},
+        }),
+        isTrue,
+      );
+    });
+  });
+}
diff --git a/pkgs/file/.gitignore b/pkgs/file/.gitignore
new file mode 100644
index 0000000..ddfdca1
--- /dev/null
+++ b/pkgs/file/.gitignore
@@ -0,0 +1,5 @@
+.dart_tool/
+.packages
+.pub/
+build/
+pubspec.lock
diff --git a/pkgs/file/CHANGELOG.md b/pkgs/file/CHANGELOG.md
new file mode 100644
index 0000000..50c96c4
--- /dev/null
+++ b/pkgs/file/CHANGELOG.md
@@ -0,0 +1,242 @@
+## 7.0.1
+
+* Update the pubspec repository field to reflect the new package repository.
+
+## 7.0.0
+
+* Dart 3 fixes for class modifiers.
+* Require Dart 3.0.
+* `MemoryFileSystem` now treats empty paths as non-existent.
+* Fix `FileSystem.isLink`/`FileSystem.isLinkSync` to not follow symbolic links.
+* Make the return type of `MemoryFile.openRead` and `_ChrootFile.openRead` again
+  match the return type from `dart:io`.
+
+## 6.1.4
+
+* Populate the pubspec `repository` field.
+
+## 6.1.3
+
+* In classes that implement `File` methods `create`, `createSync` now take `bool exclusive = true` parameter. No functional changes.
+
+## 6.1.2
+
+* `MemoryFileSystem` now provides `opHandle`s for exists operations.
+
+## 6.1.1
+
+* `MemoryFile` now provides `opHandle`s for copy and open operations.
+
+## 6.1.0
+
+* Reading invalid UTF8 with the `MemoryFileSystem` now correctly throws a `FileSystemException` instead of a `FormatError`.
+* `MemoryFileSystem` now provides an `opHandle` to inspect read/write operations.
+* `MemoryFileSystem` now creates the temporary directory before returning in `createTemp`/`createTempSync`.
+
+## 6.0.1
+
+* Fix sound type error in memory backend when reading non-existent `MemoryDirectory`.
+
+## 6.0.0
+
+* First stable null safe release.
+
+## 6.0.0-nullsafety.4
+
+* Update upper bound of SDK constraint.
+
+## 6.0.0-nullsafety.3
+
+* Update upper bound of SDK constraint.
+
+## 6.0.0-nullsafety.2
+
+* Make `ForwardingFile.openRead`'s return type again match the return type from
+  `dart:io`.
+* Remove some unnecessary `Uint8List` conversions in `ForwardingFile`.
+
+## 6.0.0-nullsafety.1
+
+* Update to null safety.
+* Remove record/replay functionality.
+* Made `MemoryRandomAccessFile` and `MemoryFile.openWrite` handle the file
+  being removed or renamed while open.
+* Fixed incorrect formatting in `NoMatchingInvocationError.toString()`.
+* Fixed more test flakiness.
+* Enabled more tests.
+* Internal cleanup.
+* Remove implicit dynamic in preparation for null safety.
+* Remove dependency on Intl.
+
+## 5.2.1
+
+* systemTemp directories created by `MemoryFileSystem` will allot names
+  based on the file system instance instead of globally.
+* `MemoryFile.readAsLines()`/`readAsLinesSync()` no longer treat a final newline
+  in the file as the start of a new, empty line.
+* `RecordingFile.readAsLine()`/`readAsLinesSync()` now always record a final
+  newline.
+* `MemoryFile.flush()` now returns `Future<void>` instead of `Future<dynamic>`.
+* Fixed some test flakiness.
+* Enabled more tests.
+* Internal cleanup.
+
+## 5.2.0
+
+* Added a `MemoryRandomAccessFile` class and implemented
+  `MemoryFile.open()`/`openSync()`.
+
+## 5.1.0
+
+* Added a new `MemoryFileSystem` constructor to use a test clock
+
+## 5.0.10
+
+* Added example
+
+## 5.0.9
+
+* Fix lints for project health
+
+## 5.0.8
+
+* Return `Uint8List` rather than `List<int>`.
+
+## 5.0.7
+
+* Dart 2 fixes for `RecordingProxyMixin` and `ReplayProxyMixin`.
+
+## 5.0.6
+
+* Dart 2 fixes for `RecordingFile.open()`
+
+## 5.0.5
+
+* Dart 2 fixes
+
+## 5.0.4
+
+* Update SDK constraint to 2.0.0-dev.67.0, remove workaround in
+  recording_proxy_mixin.dart.
+* Fix usage within Dart 2 runtime mode in Dart 2.0.0-dev.61.0 and later.
+* Relax constraints on `package:test`
+
+## 5.0.3
+
+* Update `package:test` dependency to 1.0
+
+## 5.0.2
+
+* Declare compatibility with Dart 2 stable
+
+## 5.0.1
+
+* Remove upper case constants
+* Update SDK constraint to 2.0.0-dev.54.0.
+
+## 5.0.0
+
+* Moved `testing` library into a dedicated `package:file_testing` so that
+  libraries don't need to take on a transitive dependency on `package:test`
+  in order to use `package:file`.
+
+## 4.0.1
+
+* General library cleanup
+* Add `style` support in `MemoryFileSystem`, so that callers can choose to
+  have a memory file system with windows-like paths. [#68]
+  (https://github.com/google/file.dart/issues/68)
+
+## 4.0.0
+
+* Change method signature for `RecordingRandomAccessFile._close` to return a
+  `Future<void>` instead of `Future<RandomAccessFile>`. This follows a change in
+  dart:io, Dart SDK `2.0.0-dev.40`.
+
+## 3.0.0
+
+* Import `dart:io` unconditionally. More recent Dart SDK revisions allow
+  `dart:io` to be imported in a browser context, though if methods are actually
+  invoked, they will fail. This matches well with `package:file`, where users
+  can use the `memory` library and get in-memory implementations of the
+  `dart:io` interfaces.
+* Bump minimum Dart SDK to `1.24.0`
+
+## 2.3.7
+
+* Fix Dart 2 error.
+
+## 2.3.6
+
+* Relax sdk upper bound constraint to  '<2.0.0' to allow 'edge' dart sdk use.
+
+## 2.3.5
+
+* Fix internal use of a cast which fails on Dart 2.0 .
+
+## 2.3.4
+
+* Bumped maximum Dart SDK version to 2.0.0-dev.infinity
+
+## 2.3.3
+
+* Relaxes version requirements on `package:intl`
+
+## 2.3.2
+
+* Fixed `FileSystem.directory(Uri)`, `FileSystem.file(Uri)`, and
+  `FileSystem.link(Uri)` to consult the file system's path context when
+  converting the URI to a file path rather than using `Uri.toFilePath()`.
+
+## 2.3.1
+
+* Fixed `MemoryFileSystem` to make `File.writeAs...()` update the last modified
+  time of the file.
+
+## 2.3.0
+
+* Added the following convenience methods in `Directory`:
+  * `Directory.childDirectory(String basename)`
+  * `Directory.childFile(String basename)`
+  * `Directory.childLink(String basename)`
+
+## 2.2.0
+
+* Added `ErrorCodes` class, which holds errno values.
+
+## 2.1.0
+
+* Add support for new `dart:io` API methods added in Dart SDK 1.23
+
+## 2.0.1
+
+* Minor doc updates
+
+## 2.0.0
+
+* Improved `toString` implementations in file system entity classes
+* Added `ForwardingFileSystem` and associated forwarding classes to the
+  main `file` library
+* Removed `FileSystem.pathSeparator`, and added a more comprehensive
+  `FileSystem.path` property
+* Added `FileSystemEntity.basename` and `FileSystemEntity.dirname`
+* Added the `record_replay` library
+* Added the `testing` library
+
+## 1.0.1
+
+* Added `FileSystem.systemTempDirectory`
+* Added the ability to pass `Uri` and `FileSystemEntity` types to
+  `FileSystem.directory()`, `FileSystem.file()`, and `FileSystem.link()`
+* Added `FileSystem.pathSeparator`
+
+## 1.0.0
+
+* Unified interface to match dart:io API
+* Local file system implementation
+* In-memory file system implementation
+* Chroot file system implementation
+
+## 0.1.0
+
+* Initial version
diff --git a/pkgs/file/LICENSE b/pkgs/file/LICENSE
new file mode 100644
index 0000000..076334f
--- /dev/null
+++ b/pkgs/file/LICENSE
@@ -0,0 +1,26 @@
+Copyright 2017, the Dart project authors. All rights reserved.
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+    * Redistributions of source code must retain the above copyright
+      notice, this list of conditions and the following disclaimer.
+    * Redistributions in binary form must reproduce the above
+      copyright notice, this list of conditions and the following
+      disclaimer in the documentation and/or other materials provided
+      with the distribution.
+    * Neither the name of Google Inc. nor the names of its
+      contributors may be used to endorse or promote products derived
+      from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
\ No newline at end of file
diff --git a/pkgs/file/README.md b/pkgs/file/README.md
new file mode 100644
index 0000000..a63d6e6
--- /dev/null
+++ b/pkgs/file/README.md
@@ -0,0 +1,44 @@
+[![package:file](https://github.com/dart-lang/tools/actions/workflows/file.yml/badge.svg)](https://github.com/dart-lang/tools/actions/workflows/file.yml)
+[![pub package](https://img.shields.io/pub/v/file.svg)](https://pub.dev/packages/file)
+[![package publisher](https://img.shields.io/pub/publisher/file.svg)](https://pub.dev/packages/file/publisher)
+
+A generic file system abstraction for Dart.
+
+## Features
+
+Like `dart:io`, `package:file` supplies a rich Dart-idiomatic API for accessing
+a file system.
+
+Unlike `dart:io`, `package:file`:
+
+- Can be used to implement custom file systems.
+- Comes with an in-memory implementation out-of-the-box, making it super-easy to
+  test code that works with the file system.
+- Allows using multiple file systems simultaneously. A file system is a
+  first-class object. Instantiate however many you want and use them all.
+
+## Usage
+
+Implement your own custom file system:
+
+```dart
+import 'package:file/file.dart';
+
+class FooBarFileSystem implements FileSystem { ... }
+```
+
+Use the in-memory file system:
+
+```dart
+import 'package:file/memory.dart';
+
+var fs = MemoryFileSystem();
+```
+
+Use the local file system (requires dart:io access):
+
+```dart
+import 'package:file/local.dart';
+
+var fs = const LocalFileSystem();
+```
diff --git a/pkgs/file/analysis_options.yaml b/pkgs/file/analysis_options.yaml
new file mode 100644
index 0000000..8fbd2e4
--- /dev/null
+++ b/pkgs/file/analysis_options.yaml
@@ -0,0 +1,6 @@
+include: package:lints/recommended.yaml
+
+analyzer:
+  errors:
+    # Allow having TODOs in the code
+    todo: ignore
diff --git a/pkgs/file/example/main.dart b/pkgs/file/example/main.dart
new file mode 100644
index 0000000..7ca0bc7
--- /dev/null
+++ b/pkgs/file/example/main.dart
@@ -0,0 +1,14 @@
+// Copyright (c) 2019, 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.
+
+import 'package:file/file.dart';
+import 'package:file/memory.dart';
+
+Future<void> main() async {
+  final FileSystem fs = MemoryFileSystem();
+  final Directory tmp = await fs.systemTempDirectory.createTemp('example_');
+  final File outputFile = tmp.childFile('output');
+  await outputFile.writeAsString('Hello world!');
+  print(outputFile.readAsStringSync());
+}
diff --git a/pkgs/file/lib/chroot.dart b/pkgs/file/lib/chroot.dart
new file mode 100644
index 0000000..56d2bd5
--- /dev/null
+++ b/pkgs/file/lib/chroot.dart
@@ -0,0 +1,6 @@
+// Copyright (c) 2017, 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.
+
+/// A file system that provides a view into _another_ `FileSystem` via a path.
+export 'src/backends/chroot.dart';
diff --git a/pkgs/file/lib/file.dart b/pkgs/file/lib/file.dart
new file mode 100644
index 0000000..cdde9fe
--- /dev/null
+++ b/pkgs/file/lib/file.dart
@@ -0,0 +1,8 @@
+// Copyright (c) 2017, 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.
+
+/// Core interfaces containing the abstract `FileSystem` interface definition
+/// and all associated types used by `FileSystem`.
+export 'src/forwarding.dart';
+export 'src/interface.dart';
diff --git a/pkgs/file/lib/local.dart b/pkgs/file/lib/local.dart
new file mode 100644
index 0000000..74f506e
--- /dev/null
+++ b/pkgs/file/lib/local.dart
@@ -0,0 +1,7 @@
+// Copyright (c) 2017, 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.
+
+/// A local file system implementation. This relies on the use of `dart:io`
+/// and is thus not suitable for use in the browser.
+export 'src/backends/local.dart';
diff --git a/pkgs/file/lib/memory.dart b/pkgs/file/lib/memory.dart
new file mode 100644
index 0000000..c5705ef
--- /dev/null
+++ b/pkgs/file/lib/memory.dart
@@ -0,0 +1,8 @@
+// Copyright (c) 2017, 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.
+
+/// An implementation of `FileSystem` that exists entirely in memory with an
+/// internal representation loosely based on the Filesystem Hierarchy Standard.
+export 'src/backends/memory.dart';
+export 'src/backends/memory/operations.dart';
diff --git a/pkgs/file/lib/src/backends/chroot.dart b/pkgs/file/lib/src/backends/chroot.dart
new file mode 100644
index 0000000..6082e80
--- /dev/null
+++ b/pkgs/file/lib/src/backends/chroot.dart
@@ -0,0 +1,20 @@
+// Copyright (c) 2017, 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.
+
+library file.src.backends.chroot;
+
+import 'dart:convert';
+import 'dart:typed_data';
+
+import 'package:file/file.dart';
+import 'package:file/src/common.dart' as common;
+import 'package:file/src/io.dart' as io;
+import 'package:path/path.dart' as p;
+
+part 'chroot/chroot_directory.dart';
+part 'chroot/chroot_file.dart';
+part 'chroot/chroot_file_system.dart';
+part 'chroot/chroot_file_system_entity.dart';
+part 'chroot/chroot_link.dart';
+part 'chroot/chroot_random_access_file.dart';
diff --git a/pkgs/file/lib/src/backends/chroot/chroot_directory.dart b/pkgs/file/lib/src/backends/chroot/chroot_directory.dart
new file mode 100644
index 0000000..8fec7b1
--- /dev/null
+++ b/pkgs/file/lib/src/backends/chroot/chroot_directory.dart
@@ -0,0 +1,176 @@
+// Copyright (c) 2017, 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.
+
+part of file.src.backends.chroot;
+
+class _ChrootDirectory extends _ChrootFileSystemEntity<Directory, io.Directory>
+    with ForwardingDirectory<Directory>, common.DirectoryAddOnsMixin {
+  _ChrootDirectory(ChrootFileSystem fs, String path) : super(fs, path);
+
+  factory _ChrootDirectory.wrapped(
+    ChrootFileSystem fs,
+    Directory delegate, {
+    bool relative = false,
+  }) {
+    String localPath = fs._local(delegate.path, relative: relative);
+    return _ChrootDirectory(fs, localPath);
+  }
+
+  @override
+  FileSystemEntityType get expectedType => FileSystemEntityType.directory;
+
+  @override
+  io.Directory _rawDelegate(String path) => fileSystem.delegate.directory(path);
+
+  @override
+  Uri get uri => Uri.directory(path);
+
+  @override
+  Future<Directory> rename(String newPath) async {
+    if (_isLink) {
+      if (await fileSystem.type(path) != expectedType) {
+        throw common.notADirectory(path);
+      }
+      FileSystemEntityType type = await fileSystem.type(newPath);
+      if (type != FileSystemEntityType.notFound) {
+        if (type != expectedType) {
+          throw common.notADirectory(newPath);
+        }
+        if (!(await fileSystem
+            .directory(newPath)
+            .list(followLinks: false)
+            .isEmpty)) {
+          throw common.directoryNotEmpty(newPath);
+        }
+      }
+      String target = await fileSystem.link(path).target();
+      await fileSystem.link(path).delete();
+      await fileSystem.link(newPath).create(target);
+      return fileSystem.directory(newPath);
+    } else {
+      return wrap(await getDelegate(followLinks: true)
+          .rename(fileSystem._real(newPath)));
+    }
+  }
+
+  @override
+  Directory renameSync(String newPath) {
+    if (_isLink) {
+      if (fileSystem.typeSync(path) != expectedType) {
+        throw common.notADirectory(path);
+      }
+      FileSystemEntityType type = fileSystem.typeSync(newPath);
+      if (type != FileSystemEntityType.notFound) {
+        if (type != expectedType) {
+          throw common.notADirectory(newPath);
+        }
+        if (fileSystem
+            .directory(newPath)
+            .listSync(followLinks: false)
+            .isNotEmpty) {
+          throw common.directoryNotEmpty(newPath);
+        }
+      }
+      String target = fileSystem.link(path).targetSync();
+      fileSystem.link(path).deleteSync();
+      fileSystem.link(newPath).createSync(target);
+      return fileSystem.directory(newPath);
+    } else {
+      return wrap(
+          getDelegate(followLinks: true).renameSync(fileSystem._real(newPath)));
+    }
+  }
+
+  @override
+  Directory get absolute => _ChrootDirectory(fileSystem, _absolutePath);
+
+  @override
+  Directory get parent {
+    try {
+      return wrapDirectory(delegate.parent);
+    } on _ChrootJailException {
+      return this;
+    }
+  }
+
+  @override
+  Future<Directory> create({bool recursive = false}) async {
+    if (_isLink) {
+      switch (await fileSystem.type(path)) {
+        case FileSystemEntityType.notFound:
+          throw common.noSuchFileOrDirectory(path);
+        case FileSystemEntityType.file:
+          throw common.fileExists(path);
+        case FileSystemEntityType.directory:
+          // Nothing to do.
+          return this;
+        default:
+          throw AssertionError();
+      }
+    } else {
+      return wrap(await delegate.create(recursive: recursive));
+    }
+  }
+
+  @override
+  void createSync({bool recursive = false}) {
+    if (_isLink) {
+      switch (fileSystem.typeSync(path)) {
+        case FileSystemEntityType.notFound:
+          throw common.noSuchFileOrDirectory(path);
+        case FileSystemEntityType.file:
+          throw common.fileExists(path);
+        case FileSystemEntityType.directory:
+          // Nothing to do.
+          return;
+        default:
+          throw AssertionError();
+      }
+    } else {
+      delegate.createSync(recursive: recursive);
+    }
+  }
+
+  @override
+  Stream<FileSystemEntity> list({
+    bool recursive = false,
+    bool followLinks = true,
+  }) {
+    Directory delegate = this.delegate as Directory;
+    String dirname = delegate.path;
+    return delegate
+        .list(recursive: recursive, followLinks: followLinks)
+        .map((io.FileSystemEntity entity) => _denormalize(entity, dirname));
+  }
+
+  @override
+  List<FileSystemEntity> listSync({
+    bool recursive = false,
+    bool followLinks = true,
+  }) {
+    Directory delegate = this.delegate as Directory;
+    String dirname = delegate.path;
+    return delegate
+        .listSync(recursive: recursive, followLinks: followLinks)
+        .map((io.FileSystemEntity entity) => _denormalize(entity, dirname))
+        .toList();
+  }
+
+  FileSystemEntity _denormalize(io.FileSystemEntity entity, String dirname) {
+    p.Context ctx = fileSystem.path;
+    String relativePart = ctx.relative(entity.path, from: dirname);
+    String entityPath = ctx.join(path, relativePart);
+    if (entity is io.File) {
+      return _ChrootFile(fileSystem, entityPath);
+    } else if (entity is io.Directory) {
+      return _ChrootDirectory(fileSystem, entityPath);
+    } else if (entity is io.Link) {
+      return _ChrootLink(fileSystem, entityPath);
+    }
+    throw FileSystemException('Unsupported type: $entity', entity.path);
+  }
+
+  @override
+  String toString() => "ChrootDirectory: '$path'";
+}
diff --git a/pkgs/file/lib/src/backends/chroot/chroot_file.dart b/pkgs/file/lib/src/backends/chroot/chroot_file.dart
new file mode 100644
index 0000000..4b67bc1
--- /dev/null
+++ b/pkgs/file/lib/src/backends/chroot/chroot_file.dart
@@ -0,0 +1,339 @@
+// Copyright (c) 2017, 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.
+
+part of file.src.backends.chroot;
+
+typedef _SetupCallback = dynamic Function();
+
+class _ChrootFile extends _ChrootFileSystemEntity<File, io.File>
+    with ForwardingFile {
+  _ChrootFile(ChrootFileSystem fs, String path) : super(fs, path);
+
+  factory _ChrootFile.wrapped(
+    ChrootFileSystem fs,
+    io.File delegate, {
+    bool relative = false,
+  }) {
+    String localPath = fs._local(delegate.path, relative: relative);
+    return _ChrootFile(fs, localPath);
+  }
+
+  @override
+  FileSystemEntityType get expectedType => FileSystemEntityType.file;
+
+  @override
+  io.File _rawDelegate(String path) => fileSystem.delegate.file(path);
+
+  @override
+  Future<File> rename(String newPath) async {
+    _SetupCallback setUp = () async {};
+
+    if (await fileSystem.type(newPath, followLinks: false) ==
+        FileSystemEntityType.link) {
+      // The delegate file system will ensure that the link target references
+      // an actual file before allowing the rename, but we want the link target
+      // to be resolved with respect to this file system. Thus, we perform that
+      // validation here instead.
+      switch (await fileSystem.type(newPath)) {
+        case FileSystemEntityType.file:
+        case FileSystemEntityType.notFound:
+          // Validation passed; delete the link to keep the delegate file
+          // system's validation from getting in the way.
+          setUp = () async {
+            await fileSystem.link(newPath).delete();
+          };
+          break;
+        case FileSystemEntityType.directory:
+          throw common.isADirectory(newPath);
+        default:
+          // Should never happen.
+          throw AssertionError();
+      }
+    }
+
+    if (_isLink) {
+      switch (await fileSystem.type(path)) {
+        case FileSystemEntityType.notFound:
+          throw common.noSuchFileOrDirectory(path);
+        case FileSystemEntityType.directory:
+          throw common.isADirectory(path);
+        case FileSystemEntityType.file:
+          await setUp();
+          await fileSystem.delegate
+              .link(fileSystem._real(path))
+              .rename(fileSystem._real(newPath));
+          return _ChrootFile(fileSystem, newPath);
+        default:
+          throw AssertionError();
+      }
+    } else {
+      await setUp();
+      return wrap(await delegate.rename(fileSystem._real(newPath)));
+    }
+  }
+
+  @override
+  File renameSync(String newPath) {
+    _SetupCallback setUp = () {};
+
+    if (fileSystem.typeSync(newPath, followLinks: false) ==
+        FileSystemEntityType.link) {
+      // The delegate file system will ensure that the link target references
+      // an actual file before allowing the rename, but we want the link target
+      // to be resolved with respect to this file system. Thus, we perform that
+      // validation here instead.
+      switch (fileSystem.typeSync(newPath)) {
+        case FileSystemEntityType.file:
+        case FileSystemEntityType.notFound:
+          // Validation passed; delete the link to keep the delegate file
+          // system's validation from getting in the way.
+          setUp = () {
+            fileSystem.link(newPath).deleteSync();
+          };
+          break;
+        case FileSystemEntityType.directory:
+          throw common.isADirectory(newPath);
+        default:
+          // Should never happen.
+          throw AssertionError();
+      }
+    }
+
+    if (_isLink) {
+      switch (fileSystem.typeSync(path)) {
+        case FileSystemEntityType.notFound:
+          throw common.noSuchFileOrDirectory(path);
+        case FileSystemEntityType.directory:
+          throw common.isADirectory(path);
+        case FileSystemEntityType.file:
+          setUp();
+          fileSystem.delegate
+              .link(fileSystem._real(path))
+              .renameSync(fileSystem._real(newPath));
+          return _ChrootFile(fileSystem, newPath);
+        default:
+          throw AssertionError();
+      }
+    } else {
+      setUp();
+      return wrap(delegate.renameSync(fileSystem._real(newPath)));
+    }
+  }
+
+  @override
+  File get absolute => _ChrootFile(fileSystem, _absolutePath);
+
+  @override
+  Future<File> create({bool recursive = false, bool exclusive = false}) async {
+    String path = fileSystem._resolve(
+      this.path,
+      followLinks: false,
+      notFound: recursive ? _NotFoundBehavior.mkdir : _NotFoundBehavior.allow,
+    );
+
+    String real() => fileSystem._real(path, resolve: false);
+    Future<FileSystemEntityType> type() =>
+        fileSystem.delegate.type(real(), followLinks: false);
+
+    if (await type() == FileSystemEntityType.link) {
+      path = fileSystem._resolve(p.basename(path),
+          from: p.dirname(path), notFound: _NotFoundBehavior.allowAtTail);
+      switch (await type()) {
+        case FileSystemEntityType.notFound:
+          await _rawDelegate(real()).create();
+          return this;
+        case FileSystemEntityType.file:
+          // Nothing to do.
+          return this;
+        case FileSystemEntityType.directory:
+          throw common.isADirectory(path);
+        default:
+          throw AssertionError();
+      }
+    } else {
+      return wrap(await _rawDelegate(real()).create());
+    }
+  }
+
+  @override
+  void createSync({bool recursive = false, bool exclusive = false}) {
+    String path = fileSystem._resolve(
+      this.path,
+      followLinks: false,
+      notFound: recursive ? _NotFoundBehavior.mkdir : _NotFoundBehavior.allow,
+    );
+
+    String real() => fileSystem._real(path, resolve: false);
+    FileSystemEntityType type() =>
+        fileSystem.delegate.typeSync(real(), followLinks: false);
+
+    if (type() == FileSystemEntityType.link) {
+      path = fileSystem._resolve(p.basename(path),
+          from: p.dirname(path), notFound: _NotFoundBehavior.allowAtTail);
+      switch (type()) {
+        case FileSystemEntityType.notFound:
+          _rawDelegate(real()).createSync();
+          return;
+        case FileSystemEntityType.file:
+          // Nothing to do.
+          return;
+        case FileSystemEntityType.directory:
+          throw common.isADirectory(path);
+        default:
+          throw AssertionError();
+      }
+    } else {
+      _rawDelegate(real()).createSync();
+    }
+  }
+
+  @override
+  Future<File> copy(String newPath) async {
+    return wrap(await getDelegate(followLinks: true)
+        .copy(fileSystem._real(newPath, followLinks: true)));
+  }
+
+  @override
+  File copySync(String newPath) {
+    return wrap(getDelegate(followLinks: true)
+        .copySync(fileSystem._real(newPath, followLinks: true)));
+  }
+
+  @override
+  Future<int> length() => getDelegate(followLinks: true).length();
+
+  @override
+  int lengthSync() => getDelegate(followLinks: true).lengthSync();
+
+  @override
+  Future<DateTime> lastAccessed() =>
+      getDelegate(followLinks: true).lastAccessed();
+
+  @override
+  DateTime lastAccessedSync() =>
+      getDelegate(followLinks: true).lastAccessedSync();
+
+  @override
+  Future<dynamic> setLastAccessed(DateTime time) =>
+      getDelegate(followLinks: true).setLastAccessed(time);
+
+  @override
+  void setLastAccessedSync(DateTime time) =>
+      getDelegate(followLinks: true).setLastAccessedSync(time);
+
+  @override
+  Future<DateTime> lastModified() =>
+      getDelegate(followLinks: true).lastModified();
+
+  @override
+  DateTime lastModifiedSync() =>
+      getDelegate(followLinks: true).lastModifiedSync();
+
+  @override
+  Future<dynamic> setLastModified(DateTime time) =>
+      getDelegate(followLinks: true).setLastModified(time);
+
+  @override
+  void setLastModifiedSync(DateTime time) =>
+      getDelegate(followLinks: true).setLastModifiedSync(time);
+
+  @override
+  Future<RandomAccessFile> open({
+    FileMode mode = FileMode.read,
+  }) async =>
+      _ChrootRandomAccessFile(
+          path, await getDelegate(followLinks: true).open(mode: mode));
+
+  @override
+  RandomAccessFile openSync({FileMode mode = FileMode.read}) =>
+      _ChrootRandomAccessFile(
+          path, getDelegate(followLinks: true).openSync(mode: mode));
+
+  @override
+  Stream<List<int>> openRead([int? start, int? end]) =>
+      getDelegate(followLinks: true).openRead(start, end);
+
+  @override
+  IOSink openWrite({
+    FileMode mode = FileMode.write,
+    Encoding encoding = utf8,
+  }) =>
+      getDelegate(followLinks: true).openWrite(mode: mode, encoding: encoding);
+
+  @override
+  Future<Uint8List> readAsBytes() =>
+      getDelegate(followLinks: true).readAsBytes();
+
+  @override
+  Uint8List readAsBytesSync() =>
+      getDelegate(followLinks: true).readAsBytesSync();
+
+  @override
+  Future<String> readAsString({Encoding encoding = utf8}) =>
+      getDelegate(followLinks: true).readAsString(encoding: encoding);
+
+  @override
+  String readAsStringSync({Encoding encoding = utf8}) =>
+      getDelegate(followLinks: true).readAsStringSync(encoding: encoding);
+
+  @override
+  Future<List<String>> readAsLines({Encoding encoding = utf8}) =>
+      getDelegate(followLinks: true).readAsLines(encoding: encoding);
+
+  @override
+  List<String> readAsLinesSync({Encoding encoding = utf8}) =>
+      getDelegate(followLinks: true).readAsLinesSync(encoding: encoding);
+
+  @override
+  Future<File> writeAsBytes(
+    List<int> bytes, {
+    FileMode mode = FileMode.write,
+    bool flush = false,
+  }) async =>
+      wrap(await getDelegate(followLinks: true).writeAsBytes(
+        bytes,
+        mode: mode,
+        flush: flush,
+      ));
+
+  @override
+  void writeAsBytesSync(
+    List<int> bytes, {
+    FileMode mode = FileMode.write,
+    bool flush = false,
+  }) =>
+      getDelegate(followLinks: true)
+          .writeAsBytesSync(bytes, mode: mode, flush: flush);
+
+  @override
+  Future<File> writeAsString(
+    String contents, {
+    FileMode mode = FileMode.write,
+    Encoding encoding = utf8,
+    bool flush = false,
+  }) async =>
+      wrap(await getDelegate(followLinks: true).writeAsString(
+        contents,
+        mode: mode,
+        encoding: encoding,
+        flush: flush,
+      ));
+
+  @override
+  void writeAsStringSync(
+    String contents, {
+    FileMode mode = FileMode.write,
+    Encoding encoding = utf8,
+    bool flush = false,
+  }) =>
+      getDelegate(followLinks: true).writeAsStringSync(
+        contents,
+        mode: mode,
+        encoding: encoding,
+        flush: flush,
+      );
+
+  @override
+  String toString() => "ChrootFile: '$path'";
+}
diff --git a/pkgs/file/lib/src/backends/chroot/chroot_file_system.dart b/pkgs/file/lib/src/backends/chroot/chroot_file_system.dart
new file mode 100644
index 0000000..6889c98
--- /dev/null
+++ b/pkgs/file/lib/src/backends/chroot/chroot_file_system.dart
@@ -0,0 +1,391 @@
+// Copyright (c) 2017, 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.
+
+part of file.src.backends.chroot;
+
+const String _thisDir = '.';
+const String _parentDir = '..';
+
+/// File system that provides a view into _another_ [FileSystem] via a path.
+///
+/// This is similar in concept to the `chroot` operation in Linux operating
+/// systems. Such a modified file system cannot name or access files outside of
+/// the designated directory tree.
+///
+/// ## Example use:
+/// ```dart
+/// // Create a "file system" where the root directory is /tmp/some-dir.
+/// var fs = ChrootFileSystem(existingFileSystem, '/tmp/some-dir');
+/// ```
+///
+/// **Notes on usage**:
+///
+/// * This file system maintains its _own_ [currentDirectory], distinct from
+///   that of the underlying file system, and new instances automatically start
+///   at the root (i.e. `/`).
+///
+/// * This file system does _not_ leverage any underlying OS system calls (such
+///   as `chroot` itself), so the developer needs to take care to not assume any
+///   more of a secure environment than is actually provided. For instance, the
+///   underlying system is available via the [delegate] - which underscores this
+///   file system is intended to be a convenient abstraction, not a security
+///   measure.
+///
+/// * This file system _necessarily_ carries certain performance overhead due
+///   to the fact that symbolic links are resolved manually (not delegated).
+class ChrootFileSystem extends FileSystem {
+  /// Creates a new file system backed by [root] path in [delegate] file system.
+  ///
+  /// **NOTE**: [root] must be a _canonicalized_ path; see [p.canonicalize].
+  ChrootFileSystem(this.delegate, this.root) {
+    if (root != delegate.path.canonicalize(root)) {
+      throw ArgumentError.value(root, 'root', 'Must be canonical path');
+    }
+    _cwd = _localRoot;
+  }
+
+  /// Underlying file system.
+  final FileSystem delegate;
+
+  /// Directory in [delegate] file system that is treated as the root here.
+  final String root;
+
+  String? _systemTemp;
+
+  /// Path to the synthetic current working directory in this file system.
+  late String _cwd;
+
+  /// Gets the root path, as seen by entities in this file system.
+  String get _localRoot => delegate.path.rootPrefix(root);
+
+  @override
+  Directory directory(dynamic path) => _ChrootDirectory(this, getPath(path));
+
+  @override
+  File file(dynamic path) => _ChrootFile(this, getPath(path));
+
+  @override
+  Link link(dynamic path) => _ChrootLink(this, getPath(path));
+
+  @override
+  p.Context get path => p.Context(style: delegate.path.style, current: _cwd);
+
+  /// Gets the system temp directory. This directory will be created on-demand
+  /// in the local root of the file system. Once created, its location is fixed
+  /// for the life of the process.
+  @override
+  Directory get systemTempDirectory {
+    _systemTemp ??= directory(_localRoot).createTempSync('.tmp_').path;
+    return directory(_systemTemp)..createSync();
+  }
+
+  /// Creates a directory object pointing to the current working directory.
+  ///
+  /// **NOTE** This does _not_ proxy to the underlying file system's current
+  /// directory in any way; the state of this file system's current directory
+  /// is local to this file system.
+  @override
+  Directory get currentDirectory => directory(_cwd);
+
+  /// Sets the current working directory to the specified [path].
+  ///
+  /// **NOTE** This does _not_ proxy to the underlying file system's current
+  /// directory in any way; the state of this file system's current directory
+  /// is local to this file system.
+  /// Gets the path context for this file system given the current working dir.
+
+  @override
+  set currentDirectory(dynamic path) {
+    String value;
+    if (path is io.Directory) {
+      value = path.path;
+    } else if (path is String) {
+      value = path;
+    } else {
+      throw ArgumentError('Invalid type for "path": ${path?.runtimeType}');
+    }
+
+    value = _resolve(value, notFound: _NotFoundBehavior.throwError);
+    String realPath = _real(value, resolve: false);
+    switch (delegate.typeSync(realPath, followLinks: false)) {
+      case FileSystemEntityType.directory:
+        break;
+      case FileSystemEntityType.notFound:
+        throw common.noSuchFileOrDirectory(path as String);
+      default:
+        throw common.notADirectory(path as String);
+    }
+    assert(() {
+      p.Context ctx = delegate.path;
+      return ctx.isAbsolute(value) && value == ctx.canonicalize(value);
+    }());
+    _cwd = value;
+  }
+
+  @override
+  Future<FileStat> stat(String path) {
+    try {
+      path = _resolve(path);
+    } on FileSystemException {
+      return Future<FileStat>.value(const _NotFoundFileStat());
+    }
+    return delegate.stat(_real(path, resolve: false));
+  }
+
+  @override
+  FileStat statSync(String path) {
+    try {
+      path = _resolve(path);
+    } on FileSystemException {
+      return const _NotFoundFileStat();
+    }
+    return delegate.statSync(_real(path, resolve: false));
+  }
+
+  @override
+  Future<bool> identical(String path1, String path2) => delegate.identical(
+        _real(_resolve(path1, followLinks: false)),
+        _real(_resolve(path2, followLinks: false)),
+      );
+
+  @override
+  bool identicalSync(String path1, String path2) => delegate.identicalSync(
+        _real(_resolve(path1, followLinks: false)),
+        _real(_resolve(path2, followLinks: false)),
+      );
+
+  @override
+  bool get isWatchSupported => false;
+
+  @override
+  Future<FileSystemEntityType> type(String path, {bool followLinks = true}) {
+    String realPath;
+    try {
+      realPath = _real(path, followLinks: followLinks);
+    } on FileSystemException {
+      return Future<FileSystemEntityType>.value(FileSystemEntityType.notFound);
+    }
+    return delegate.type(realPath, followLinks: false);
+  }
+
+  @override
+  FileSystemEntityType typeSync(String path, {bool followLinks = true}) {
+    String realPath;
+    try {
+      realPath = _real(path, followLinks: followLinks);
+    } on FileSystemException {
+      return FileSystemEntityType.notFound;
+    }
+    return delegate.typeSync(realPath, followLinks: false);
+  }
+
+  /// Converts a [realPath] in the underlying file system to a local path here.
+  ///
+  /// If [relative] is set to `true`, then the resulting path will be relative
+  /// to [currentDirectory], otherwise the resulting path will be absolute.
+  ///
+  /// An exception is thrown if the path is outside of this file system's root
+  /// directory unless [keepInJail] is true, in which case this will instead
+  /// return the path of the root of this file system.
+  String _local(
+    String realPath, {
+    bool relative = false,
+    bool keepInJail = false,
+  }) {
+    assert(path.isAbsolute(realPath));
+    if (!realPath.startsWith(root)) {
+      if (keepInJail) {
+        return _localRoot;
+      }
+      throw _ChrootJailException();
+    }
+    // TODO(tvolkert): See if _context.relative() works here
+    String result = realPath.substring(root.length);
+    if (result.isEmpty) {
+      result = _localRoot;
+    }
+    if (relative) {
+      assert(result.startsWith(_cwd));
+      result = path.relative(result, from: _cwd);
+    }
+    return result;
+  }
+
+  /// Converts [localPath] in this file system to the real path in the delegate.
+  ///
+  /// The returned path will always be absolute.
+  ///
+  /// If [resolve] is true, symbolic links will be resolved in the local file
+  /// system _before_ converting the path to the delegate file system's
+  /// namespace, and if the tail element of the path is a symbolic link, it will
+  /// only be resolved if [followLinks] is true (where-as symbolic links found
+  /// in the middle of the path will always be resolved).
+  String _real(
+    String localPath, {
+    bool resolve = true,
+    bool followLinks = false,
+  }) {
+    if (resolve) {
+      localPath = _resolve(localPath, followLinks: followLinks);
+    } else {
+      assert(path.isAbsolute(localPath));
+    }
+    return '$root$localPath';
+  }
+
+  /// Resolves symbolic links on [path] and returns the resulting resolved path.
+  ///
+  /// The return value will always be an absolute path; if [path] is relative
+  /// it will be interpreted relative to [from] (or [currentDirectory] if
+  /// `null`).
+  ///
+  /// If the tail element is a symbolic link, then the link will be resolved
+  /// only if [followLinks] is `true`. Symbolic links found in the middle of
+  /// the path will always be resolved.
+  ///
+  /// If the path cannot be resolved, and [notFound] is:
+  ///   - [_NotFoundBehavior.throwError]: a [FileSystemException] is thrown.
+  ///   - [_NotFoundBehavior.mkdir]: the path will be created as needed.
+  ///   - [_NotFoundBehavior.allowAtTail]: a [FileSystemException] is thrown,
+  ///     unless only the *tail* path element cannot be resolved, in which case
+  ///     the resolution will halt at the tail element, and the partially
+  ///     resolved path will be returned.
+  ///   - [_NotFoundBehavior.allow] (the default), the resolution will halt and
+  ///     the partially resolved path will be returned.
+  String _resolve(
+    String path, {
+    String? from,
+    bool followLinks = true,
+    _NotFoundBehavior notFound = _NotFoundBehavior.allow,
+  }) {
+    if (path.isEmpty) {
+      throw common.noSuchFileOrDirectory(path);
+    }
+
+    p.Context ctx = this.path;
+    String root = _localRoot;
+    List<String> parts, ledger;
+    if (ctx.isAbsolute(path)) {
+      parts = ctx.split(path).sublist(1);
+      ledger = <String>[];
+    } else {
+      from ??= _cwd;
+      assert(ctx.isAbsolute(from));
+      parts = ctx.split(path);
+      ledger = ctx.split(from).sublist(1);
+    }
+
+    String getCurrentPath() => root + ctx.joinAll(ledger);
+    Set<String> breadcrumbs = <String>{};
+    while (parts.isNotEmpty) {
+      String segment = parts.removeAt(0);
+      if (segment == _thisDir) {
+        continue;
+      } else if (segment == _parentDir) {
+        if (ledger.isNotEmpty) {
+          ledger.removeLast();
+        }
+        continue;
+      }
+
+      ledger.add(segment);
+      String currentPath = getCurrentPath();
+      String realPath = _real(currentPath, resolve: false);
+
+      switch (delegate.typeSync(realPath, followLinks: false)) {
+        case FileSystemEntityType.directory:
+          breadcrumbs.clear();
+          break;
+        case FileSystemEntityType.file:
+          breadcrumbs.clear();
+          if (parts.isNotEmpty) {
+            throw common.notADirectory(currentPath);
+          }
+          break;
+        case FileSystemEntityType.notFound:
+          String returnEarly() {
+            ledger.addAll(parts);
+            return getCurrentPath();
+          }
+
+          switch (notFound) {
+            case _NotFoundBehavior.mkdir:
+              if (parts.isNotEmpty) {
+                delegate.directory(realPath).createSync();
+              }
+              break;
+            case _NotFoundBehavior.allow:
+              return returnEarly();
+            case _NotFoundBehavior.allowAtTail:
+              if (parts.isEmpty) {
+                return returnEarly();
+              }
+              throw common.noSuchFileOrDirectory(path);
+            case _NotFoundBehavior.throwError:
+              throw common.noSuchFileOrDirectory(path);
+          }
+          break;
+        case FileSystemEntityType.link:
+          if (parts.isEmpty && !followLinks) {
+            break;
+          }
+          if (!breadcrumbs.add(currentPath)) {
+            throw common.tooManyLevelsOfSymbolicLinks(path);
+          }
+          String target = delegate.link(realPath).targetSync();
+          if (ctx.isAbsolute(target)) {
+            ledger.clear();
+            parts.insertAll(0, ctx.split(target).sublist(1));
+          } else {
+            ledger.removeLast();
+            parts.insertAll(0, ctx.split(target));
+          }
+          break;
+        default:
+          throw AssertionError();
+      }
+    }
+
+    return getCurrentPath();
+  }
+}
+
+/// Thrown when a path is encountered that exists outside of the root path.
+class _ChrootJailException implements IOException {}
+
+/// What to do when `NOT_FOUND` paths are encountered while resolving.
+enum _NotFoundBehavior {
+  allow,
+  allowAtTail,
+  throwError,
+  mkdir,
+}
+
+/// A [FileStat] representing a `NOT_FOUND` entity.
+class _NotFoundFileStat implements FileStat {
+  const _NotFoundFileStat();
+
+  static final DateTime _empty = DateTime(0);
+
+  @override
+  DateTime get changed => _empty;
+
+  @override
+  DateTime get modified => _empty;
+
+  @override
+  DateTime get accessed => _empty;
+
+  @override
+  FileSystemEntityType get type => FileSystemEntityType.notFound;
+
+  @override
+  int get mode => 0;
+
+  @override
+  int get size => -1;
+
+  @override
+  String modeString() => '---------';
+}
diff --git a/pkgs/file/lib/src/backends/chroot/chroot_file_system_entity.dart b/pkgs/file/lib/src/backends/chroot/chroot_file_system_entity.dart
new file mode 100644
index 0000000..8e859ac
--- /dev/null
+++ b/pkgs/file/lib/src/backends/chroot/chroot_file_system_entity.dart
@@ -0,0 +1,169 @@
+// Copyright (c) 2017, 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.
+
+part of file.src.backends.chroot;
+
+abstract class _ChrootFileSystemEntity<T extends FileSystemEntity,
+    D extends io.FileSystemEntity> extends ForwardingFileSystemEntity<T, D> {
+  _ChrootFileSystemEntity(this.fileSystem, this.path);
+
+  @override
+  final ChrootFileSystem fileSystem;
+
+  @override
+  final String path;
+
+  @override
+  String get dirname => fileSystem.path.dirname(path);
+
+  @override
+  String get basename => fileSystem.path.basename(path);
+
+  @override
+  D get delegate => getDelegate();
+
+  /// Gets the delegate file system entity in the underlying file system that
+  /// corresponds to this entity's local file system path.
+  ///
+  /// If [followLinks] is true and this entity's path references a symbolic
+  /// link, then the path of the delegate entity will reference the ultimate
+  /// target of that symbolic link. Symbolic links in the middle of the path
+  /// will always be resolved in the delegate entity's path.
+  D getDelegate({bool followLinks = false}) =>
+      _rawDelegate(fileSystem._real(path, followLinks: followLinks));
+
+  /// Returns the expected type of this entity, which may differ from the type
+  /// of the entity that's found at the path specified by this entity.
+  FileSystemEntityType get expectedType;
+
+  /// Returns a delegate entity at the specified [realPath] (the path in the
+  /// underlying file system).
+  D _rawDelegate(String realPath);
+
+  /// Gets the path of this entity as an absolute path (unchanged if the
+  /// entity already specifies an absolute path).
+  String get _absolutePath => fileSystem.path.absolute(path);
+
+  /// Tells whether this entity's path references a symbolic link.
+  bool get _isLink =>
+      fileSystem.typeSync(path, followLinks: false) ==
+      FileSystemEntityType.link;
+
+  @override
+  Directory wrapDirectory(io.Directory delegate) =>
+      _ChrootDirectory.wrapped(fileSystem, delegate as Directory,
+          relative: !isAbsolute);
+
+  @override
+  File wrapFile(io.File delegate) =>
+      _ChrootFile.wrapped(fileSystem, delegate, relative: !isAbsolute);
+
+  @override
+  Link wrapLink(io.Link delegate) =>
+      _ChrootLink.wrapped(fileSystem, delegate, relative: !isAbsolute);
+
+  @override
+  Uri get uri => Uri.file(path);
+
+  @override
+  Future<bool> exists() => getDelegate(followLinks: true).exists();
+
+  @override
+  bool existsSync() => getDelegate(followLinks: true).existsSync();
+
+  @override
+  Future<String> resolveSymbolicLinks() async => resolveSymbolicLinksSync();
+
+  @override
+  String resolveSymbolicLinksSync() =>
+      fileSystem._resolve(path, notFound: _NotFoundBehavior.throwError);
+
+  @override
+  Future<FileStat> stat() {
+    D delegate;
+    try {
+      delegate = getDelegate(followLinks: true);
+    } on FileSystemException {
+      return Future<FileStat>.value(const _NotFoundFileStat());
+    }
+    return delegate.stat();
+  }
+
+  @override
+  FileStat statSync() {
+    D delegate;
+    try {
+      delegate = getDelegate(followLinks: true);
+    } on FileSystemException {
+      return const _NotFoundFileStat();
+    }
+    return delegate.statSync();
+  }
+
+  @override
+  Future<T> delete({bool recursive = false}) async {
+    String path = fileSystem._resolve(this.path,
+        followLinks: false, notFound: _NotFoundBehavior.throwError);
+
+    String real(String path) => fileSystem._real(path, resolve: false);
+    Future<FileSystemEntityType> type(String path) =>
+        fileSystem.delegate.type(real(path), followLinks: false);
+
+    if (await type(path) == FileSystemEntityType.link) {
+      if (expectedType == FileSystemEntityType.link) {
+        await fileSystem.delegate.link(real(path)).delete();
+      } else {
+        String resolvedPath = fileSystem._resolve(p.basename(path),
+            from: p.dirname(path), notFound: _NotFoundBehavior.allowAtTail);
+        if (!recursive && await type(resolvedPath) != expectedType) {
+          throw expectedType == FileSystemEntityType.file
+              ? common.isADirectory(path)
+              : common.notADirectory(path);
+        }
+        await fileSystem.delegate.link(real(path)).delete();
+      }
+      return this as T;
+    } else {
+      return wrap(
+          await _rawDelegate(real(path)).delete(recursive: recursive) as D);
+    }
+  }
+
+  @override
+  void deleteSync({bool recursive = false}) {
+    String path = fileSystem._resolve(this.path,
+        followLinks: false, notFound: _NotFoundBehavior.throwError);
+
+    String real(String path) => fileSystem._real(path, resolve: false);
+    FileSystemEntityType type(String path) =>
+        fileSystem.delegate.typeSync(real(path), followLinks: false);
+
+    if (type(path) == FileSystemEntityType.link) {
+      if (expectedType == FileSystemEntityType.link) {
+        fileSystem.delegate.link(real(path)).deleteSync();
+      } else {
+        String resolvedPath = fileSystem._resolve(p.basename(path),
+            from: p.dirname(path), notFound: _NotFoundBehavior.allowAtTail);
+        if (!recursive && type(resolvedPath) != expectedType) {
+          throw expectedType == FileSystemEntityType.file
+              ? common.isADirectory(path)
+              : common.notADirectory(path);
+        }
+        fileSystem.delegate.link(real(path)).deleteSync();
+      }
+    } else {
+      _rawDelegate(real(path)).deleteSync(recursive: recursive);
+    }
+  }
+
+  @override
+  Stream<FileSystemEvent> watch({
+    int events = FileSystemEvent.all,
+    bool recursive = false,
+  }) =>
+      throw UnsupportedError('watch is not supported on ChrootFileSystem');
+
+  @override
+  bool get isAbsolute => fileSystem.path.isAbsolute(path);
+}
diff --git a/pkgs/file/lib/src/backends/chroot/chroot_link.dart b/pkgs/file/lib/src/backends/chroot/chroot_link.dart
new file mode 100644
index 0000000..acbeda6
--- /dev/null
+++ b/pkgs/file/lib/src/backends/chroot/chroot_link.dart
@@ -0,0 +1,47 @@
+// Copyright (c) 2017, 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.
+
+part of file.src.backends.chroot;
+
+class _ChrootLink extends _ChrootFileSystemEntity<Link, io.Link>
+    with ForwardingLink {
+  _ChrootLink(ChrootFileSystem fs, String path) : super(fs, path);
+
+  factory _ChrootLink.wrapped(
+    ChrootFileSystem fs,
+    io.Link delegate, {
+    bool relative = false,
+  }) {
+    String localPath = fs._local(delegate.path, relative: relative);
+    return _ChrootLink(fs, localPath);
+  }
+
+  @override
+  Future<bool> exists() => delegate.exists();
+
+  @override
+  bool existsSync() => delegate.existsSync();
+
+  @override
+  Future<Link> rename(String newPath) async {
+    return wrap(await delegate.rename(fileSystem._real(newPath)));
+  }
+
+  @override
+  Link renameSync(String newPath) {
+    return wrap(delegate.renameSync(fileSystem._real(newPath)));
+  }
+
+  @override
+  FileSystemEntityType get expectedType => FileSystemEntityType.link;
+
+  @override
+  io.Link _rawDelegate(String path) => fileSystem.delegate.link(path);
+
+  @override
+  Link get absolute => _ChrootLink(fileSystem, _absolutePath);
+
+  @override
+  String toString() => "ChrootLink: '$path'";
+}
diff --git a/pkgs/file/lib/src/backends/chroot/chroot_random_access_file.dart b/pkgs/file/lib/src/backends/chroot/chroot_random_access_file.dart
new file mode 100644
index 0000000..4105ac8
--- /dev/null
+++ b/pkgs/file/lib/src/backends/chroot/chroot_random_access_file.dart
@@ -0,0 +1,15 @@
+// Copyright (c) 2020, 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.
+
+part of file.src.backends.chroot;
+
+class _ChrootRandomAccessFile with ForwardingRandomAccessFile {
+  _ChrootRandomAccessFile(this.path, this.delegate);
+
+  @override
+  final io.RandomAccessFile delegate;
+
+  @override
+  final String path;
+}
diff --git a/pkgs/file/lib/src/backends/local.dart b/pkgs/file/lib/src/backends/local.dart
new file mode 100644
index 0000000..1e92241
--- /dev/null
+++ b/pkgs/file/lib/src/backends/local.dart
@@ -0,0 +1,5 @@
+// Copyright (c) 2017, 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.
+
+export 'local/local_file_system.dart' show LocalFileSystem;
diff --git a/pkgs/file/lib/src/backends/local/local_directory.dart b/pkgs/file/lib/src/backends/local/local_directory.dart
new file mode 100644
index 0000000..e23e68f
--- /dev/null
+++ b/pkgs/file/lib/src/backends/local/local_directory.dart
@@ -0,0 +1,20 @@
+// Copyright (c) 2017, 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.
+
+import 'package:file/file.dart';
+import 'package:file/src/common.dart' as common;
+import 'package:file/src/io.dart' as io;
+
+import 'local_file_system_entity.dart';
+
+/// [Directory] implementation that forwards all calls to `dart:io`.
+class LocalDirectory extends LocalFileSystemEntity<LocalDirectory, io.Directory>
+    with ForwardingDirectory<LocalDirectory>, common.DirectoryAddOnsMixin {
+  /// Instantiates a new [LocalDirectory] tied to the specified file system
+  /// and delegating to the specified [delegate].
+  LocalDirectory(FileSystem fs, io.Directory delegate) : super(fs, delegate);
+
+  @override
+  String toString() => "LocalDirectory: '$path'";
+}
diff --git a/pkgs/file/lib/src/backends/local/local_file.dart b/pkgs/file/lib/src/backends/local/local_file.dart
new file mode 100644
index 0000000..36293ba
--- /dev/null
+++ b/pkgs/file/lib/src/backends/local/local_file.dart
@@ -0,0 +1,19 @@
+// Copyright (c) 2017, 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.
+
+import 'package:file/file.dart';
+import 'package:file/src/io.dart' as io;
+
+import 'local_file_system_entity.dart';
+
+/// [File] implementation that forwards all calls to `dart:io`.
+class LocalFile extends LocalFileSystemEntity<File, io.File>
+    with ForwardingFile {
+  /// Instantiates a new [LocalFile] tied to the specified file system
+  /// and delegating to the specified [delegate].
+  LocalFile(FileSystem fs, io.File delegate) : super(fs, delegate);
+
+  @override
+  String toString() => "LocalFile: '$path'";
+}
diff --git a/pkgs/file/lib/src/backends/local/local_file_system.dart b/pkgs/file/lib/src/backends/local/local_file_system.dart
new file mode 100644
index 0000000..635998e
--- /dev/null
+++ b/pkgs/file/lib/src/backends/local/local_file_system.dart
@@ -0,0 +1,72 @@
+// Copyright (c) 2017, 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.
+
+import 'package:file/src/io.dart' as io;
+import 'package:file/file.dart';
+import 'package:path/path.dart' as p;
+
+import 'local_directory.dart';
+import 'local_file.dart';
+import 'local_link.dart';
+
+/// A wrapper implementation around `dart:io`'s implementation.
+///
+/// Since this implementation of the [FileSystem] interface delegates to
+/// `dart:io`, is is not suitable for use in the browser.
+class LocalFileSystem extends FileSystem {
+  /// Creates a new `LocalFileSystem`.
+  const LocalFileSystem();
+
+  @override
+  Directory directory(dynamic path) =>
+      LocalDirectory(this, io.Directory(getPath(path)));
+
+  @override
+  File file(dynamic path) => LocalFile(this, io.File(getPath(path)));
+
+  @override
+  Link link(dynamic path) => LocalLink(this, io.Link(getPath(path)));
+
+  @override
+  p.Context get path => p.Context();
+
+  /// Gets the directory provided by the operating system for creating temporary
+  /// files and directories in. The location of the system temp directory is
+  /// platform-dependent, and may be set by an environment variable.
+  @override
+  Directory get systemTempDirectory =>
+      LocalDirectory(this, io.Directory.systemTemp);
+
+  @override
+  Directory get currentDirectory => directory(io.Directory.current.path);
+
+  @override
+  set currentDirectory(dynamic path) => io.Directory.current = path;
+
+  @override
+  Future<io.FileStat> stat(String path) => io.FileStat.stat(path);
+
+  @override
+  io.FileStat statSync(String path) => io.FileStat.statSync(path);
+
+  @override
+  Future<bool> identical(String path1, String path2) =>
+      io.FileSystemEntity.identical(path1, path2);
+
+  @override
+  bool identicalSync(String path1, String path2) =>
+      io.FileSystemEntity.identicalSync(path1, path2);
+
+  @override
+  bool get isWatchSupported => io.FileSystemEntity.isWatchSupported;
+
+  @override
+  Future<io.FileSystemEntityType> type(String path,
+          {bool followLinks = true}) =>
+      io.FileSystemEntity.type(path, followLinks: followLinks);
+
+  @override
+  io.FileSystemEntityType typeSync(String path, {bool followLinks = true}) =>
+      io.FileSystemEntity.typeSync(path, followLinks: followLinks);
+}
diff --git a/pkgs/file/lib/src/backends/local/local_file_system_entity.dart b/pkgs/file/lib/src/backends/local/local_file_system_entity.dart
new file mode 100644
index 0000000..ca4617b
--- /dev/null
+++ b/pkgs/file/lib/src/backends/local/local_file_system_entity.dart
@@ -0,0 +1,40 @@
+// Copyright (c) 2017, 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.
+
+import 'package:file/file.dart';
+import 'package:file/src/io.dart' as io;
+
+import 'local_directory.dart';
+import 'local_file.dart';
+import 'local_link.dart';
+
+/// [FileSystemEntity] implementation that forwards all calls to `dart:io`.
+abstract class LocalFileSystemEntity<T extends FileSystemEntity,
+    D extends io.FileSystemEntity> extends ForwardingFileSystemEntity<T, D> {
+  /// Instantiates a new [LocalFileSystemEntity] tied to the specified file
+  /// system and delegating to the specified [delegate].
+  LocalFileSystemEntity(this.fileSystem, this.delegate);
+
+  @override
+  final FileSystem fileSystem;
+
+  @override
+  final D delegate;
+
+  @override
+  String get dirname => fileSystem.path.dirname(path);
+
+  @override
+  String get basename => fileSystem.path.basename(path);
+
+  @override
+  Directory wrapDirectory(io.Directory delegate) =>
+      LocalDirectory(fileSystem, delegate);
+
+  @override
+  File wrapFile(io.File delegate) => LocalFile(fileSystem, delegate);
+
+  @override
+  Link wrapLink(io.Link delegate) => LocalLink(fileSystem, delegate);
+}
diff --git a/pkgs/file/lib/src/backends/local/local_link.dart b/pkgs/file/lib/src/backends/local/local_link.dart
new file mode 100644
index 0000000..fc67d5e
--- /dev/null
+++ b/pkgs/file/lib/src/backends/local/local_link.dart
@@ -0,0 +1,19 @@
+// Copyright (c) 2017, 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.
+
+import 'package:file/file.dart';
+import 'package:file/src/io.dart' as io;
+
+import 'local_file_system_entity.dart';
+
+/// [Link] implementation that forwards all calls to `dart:io`.
+class LocalLink extends LocalFileSystemEntity<Link, io.Link>
+    with ForwardingLink {
+  /// Instantiates a new [LocalLink] tied to the specified file system
+  /// and delegating to the specified [delegate].
+  LocalLink(FileSystem fs, io.Link delegate) : super(fs, delegate);
+
+  @override
+  String toString() => "LocalLink: '$path'";
+}
diff --git a/pkgs/file/lib/src/backends/memory.dart b/pkgs/file/lib/src/backends/memory.dart
new file mode 100644
index 0000000..428bc54
--- /dev/null
+++ b/pkgs/file/lib/src/backends/memory.dart
@@ -0,0 +1,6 @@
+// Copyright (c) 2017, 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.
+
+export 'memory/memory_file_system.dart' show MemoryFileSystem;
+export 'memory/style.dart' show FileSystemStyle, StyleableFileSystem;
diff --git a/pkgs/file/lib/src/backends/memory/clock.dart b/pkgs/file/lib/src/backends/memory/clock.dart
new file mode 100644
index 0000000..98d5434
--- /dev/null
+++ b/pkgs/file/lib/src/backends/memory/clock.dart
@@ -0,0 +1,52 @@
+// Copyright (c) 2018, 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.
+
+/// Interface describing clocks used by the [MemoryFileSystem].
+///
+/// The [MemoryFileSystem] uses a clock to determine the modification times of
+/// files that are created in that file system.
+abstract class Clock {
+  /// Abstract const constructor. This constructor enables subclasses to provide
+  /// const constructors so that they can be used in const expressions.
+  const Clock();
+
+  /// A real-time clock.
+  ///
+  /// Uses [DateTime.now] to reflect the actual time reported by the operating
+  /// system.
+  const factory Clock.realTime() = _RealtimeClock;
+
+  /// A monotonically-increasing test clock.
+  ///
+  /// Each time [now] is called, the time increases by one minute.
+  ///
+  /// The `start` argument can be used to set the seed time for the clock.
+  /// The first value will be that time plus one minute.
+  /// By default, `start` is midnight on the first of January, 2000.
+  factory Clock.monotonicTest() = _MonotonicTestClock;
+
+  /// Returns the value of the clock.
+  DateTime get now;
+}
+
+class _RealtimeClock extends Clock {
+  const _RealtimeClock();
+
+  @override
+  DateTime get now => DateTime.now();
+}
+
+class _MonotonicTestClock extends Clock {
+  _MonotonicTestClock({
+    DateTime? start,
+  }) : _current = start ?? DateTime(2000);
+
+  DateTime _current;
+
+  @override
+  DateTime get now {
+    _current = _current.add(const Duration(minutes: 1));
+    return _current;
+  }
+}
diff --git a/pkgs/file/lib/src/backends/memory/common.dart b/pkgs/file/lib/src/backends/memory/common.dart
new file mode 100644
index 0000000..80e3c38
--- /dev/null
+++ b/pkgs/file/lib/src/backends/memory/common.dart
@@ -0,0 +1,15 @@
+// Copyright (c) 2018, 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.
+
+import 'package:file/src/common.dart' as common;
+
+/// Generates a path to use in error messages.
+typedef PathGenerator = dynamic Function();
+
+/// Throws a `FileSystemException` if [object] is null.
+void checkExists(Object? object, PathGenerator path) {
+  if (object == null) {
+    throw common.noSuchFileOrDirectory(path() as String);
+  }
+}
diff --git a/pkgs/file/lib/src/backends/memory/memory_directory.dart b/pkgs/file/lib/src/backends/memory/memory_directory.dart
new file mode 100644
index 0000000..95fe542
--- /dev/null
+++ b/pkgs/file/lib/src/backends/memory/memory_directory.dart
@@ -0,0 +1,184 @@
+// Copyright (c) 2017, 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.
+
+import 'package:file/file.dart';
+import 'package:file/src/common.dart' as common;
+import 'package:file/src/io.dart' as io;
+import 'package:meta/meta.dart';
+
+import 'common.dart';
+import 'memory_file.dart';
+import 'memory_file_system_entity.dart';
+import 'memory_link.dart';
+import 'node.dart';
+import 'operations.dart';
+import 'style.dart';
+import 'utils.dart' as utils;
+
+// Tracks a unique name for system temp directories, per filesystem
+// instance.
+final Expando<int> _systemTempCounter = Expando<int>();
+
+/// Internal implementation of [Directory].
+class MemoryDirectory extends MemoryFileSystemEntity
+    with common.DirectoryAddOnsMixin
+    implements Directory {
+  /// Instantiates a new [MemoryDirectory].
+  MemoryDirectory(NodeBasedFileSystem fileSystem, String path)
+      : super(fileSystem, path);
+
+  @override
+  io.FileSystemEntityType get expectedType => io.FileSystemEntityType.directory;
+
+  @override
+  Uri get uri {
+    return Uri.directory(path,
+        windows: fileSystem.style == FileSystemStyle.windows);
+  }
+
+  @override
+  bool existsSync() {
+    fileSystem.opHandle.call(path, FileSystemOp.exists);
+    return backingOrNull?.stat.type == expectedType;
+  }
+
+  @override
+  Future<Directory> create({bool recursive = false}) async {
+    createSync(recursive: recursive);
+    return this;
+  }
+
+  @override
+  void createSync({bool recursive = false}) {
+    fileSystem.opHandle(path, FileSystemOp.create);
+    Node? node = internalCreateSync(
+      followTailLink: true,
+      visitLinks: true,
+      createChild: (DirectoryNode parent, bool isFinalSegment) {
+        if (recursive || isFinalSegment) {
+          return DirectoryNode(parent);
+        }
+        return null;
+      },
+    );
+    if (node?.type != expectedType) {
+      // There was an existing non-directory node at this object's path
+      throw common.notADirectory(path);
+    }
+  }
+
+  @override
+  Future<Directory> createTemp([String? prefix]) async =>
+      createTempSync(prefix);
+
+  @override
+  Directory createTempSync([String? prefix]) {
+    prefix = '${prefix ?? ''}rand';
+    String fullPath = fileSystem.path.join(path, prefix);
+    String dirname = fileSystem.path.dirname(fullPath);
+    String basename = fileSystem.path.basename(fullPath);
+    DirectoryNode? node = fileSystem.findNode(dirname) as DirectoryNode?;
+    checkExists(node, () => dirname);
+    utils.checkIsDir(node!, () => dirname);
+    int tempCounter = _systemTempCounter[fileSystem] ?? 0;
+    String name() => '$basename$tempCounter';
+    while (node.children.containsKey(name())) {
+      tempCounter++;
+    }
+    _systemTempCounter[fileSystem] = tempCounter;
+    DirectoryNode tempDir = DirectoryNode(node);
+    node.children[name()] = tempDir;
+    return MemoryDirectory(fileSystem, fileSystem.path.join(dirname, name()))
+      ..createSync();
+  }
+
+  @override
+  Future<Directory> rename(String newPath) async => renameSync(newPath);
+
+  @override
+  Directory renameSync(String newPath) => internalRenameSync<DirectoryNode>(
+        newPath,
+        validateOverwriteExistingEntity: (DirectoryNode existingNode) {
+          if (existingNode.children.isNotEmpty) {
+            throw common.directoryNotEmpty(newPath);
+          }
+        },
+      ) as Directory;
+
+  @override
+  Directory get parent =>
+      (backingOrNull?.isRoot ?? false) ? this : super.parent;
+
+  @override
+  Directory get absolute => super.absolute as Directory;
+
+  @override
+  Stream<FileSystemEntity> list({
+    bool recursive = false,
+    bool followLinks = true,
+  }) =>
+      Stream<FileSystemEntity>.fromIterable(listSync(
+        recursive: recursive,
+        followLinks: followLinks,
+      ));
+
+  @override
+  List<FileSystemEntity> listSync({
+    bool recursive = false,
+    bool followLinks = true,
+  }) {
+    DirectoryNode node = backing as DirectoryNode;
+    List<FileSystemEntity> listing = <FileSystemEntity>[];
+    List<_PendingListTask> tasks = <_PendingListTask>[
+      _PendingListTask(
+        node,
+        path.endsWith(fileSystem.path.separator)
+            ? path.substring(0, path.length - 1)
+            : path,
+        <LinkNode>{},
+      ),
+    ];
+    while (tasks.isNotEmpty) {
+      _PendingListTask task = tasks.removeLast();
+      task.dir.children.forEach((String name, Node child) {
+        Set<LinkNode> breadcrumbs = Set<LinkNode>.from(task.breadcrumbs);
+        String childPath = fileSystem.path.join(task.path, name);
+        while (followLinks &&
+            utils.isLink(child) &&
+            breadcrumbs.add(child as LinkNode)) {
+          Node? referent = child.referentOrNull;
+          if (referent != null) {
+            child = referent;
+          }
+        }
+        if (utils.isDirectory(child)) {
+          listing.add(MemoryDirectory(fileSystem, childPath));
+          if (recursive) {
+            tasks.add(_PendingListTask(
+                child as DirectoryNode, childPath, breadcrumbs));
+          }
+        } else if (utils.isLink(child)) {
+          listing.add(MemoryLink(fileSystem, childPath));
+        } else if (utils.isFile(child)) {
+          listing.add(MemoryFile(fileSystem, childPath));
+        }
+      });
+    }
+    return listing;
+  }
+
+  @override
+  @protected
+  Directory clone(String path) => MemoryDirectory(fileSystem, path);
+
+  @override
+  String toString() => "MemoryDirectory: '$path'";
+}
+
+class _PendingListTask {
+  _PendingListTask(this.dir, this.path, this.breadcrumbs);
+  final DirectoryNode dir;
+  final String path;
+  final Set<LinkNode> breadcrumbs;
+}
diff --git a/pkgs/file/lib/src/backends/memory/memory_file.dart b/pkgs/file/lib/src/backends/memory/memory_file.dart
new file mode 100644
index 0000000..ba4faab
--- /dev/null
+++ b/pkgs/file/lib/src/backends/memory/memory_file.dart
@@ -0,0 +1,470 @@
+// Copyright (c) 2017, 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.
+
+import 'dart:async';
+import 'dart:convert';
+import 'dart:math' as math show min;
+import 'dart:typed_data';
+
+import 'package:file/file.dart';
+import 'package:file/src/backends/memory/operations.dart';
+import 'package:file/src/common.dart' as common;
+import 'package:file/src/io.dart' as io;
+import 'package:meta/meta.dart';
+
+import 'common.dart';
+import 'memory_file_system_entity.dart';
+import 'memory_random_access_file.dart';
+import 'node.dart';
+import 'utils.dart' as utils;
+
+/// Internal implementation of [File].
+class MemoryFile extends MemoryFileSystemEntity implements File {
+  /// Instantiates a new [MemoryFile].
+  const MemoryFile(NodeBasedFileSystem fileSystem, String path)
+      : super(fileSystem, path);
+
+  FileNode get _resolvedBackingOrCreate {
+    Node? node = backingOrNull;
+    if (node == null) {
+      node = _doCreate();
+    } else {
+      node = utils.isLink(node)
+          ? utils.resolveLinks(node as LinkNode, () => path)
+          : node;
+      utils.checkType(expectedType, node.type, () => path);
+    }
+    return node as FileNode;
+  }
+
+  @override
+  io.FileSystemEntityType get expectedType => io.FileSystemEntityType.file;
+
+  @override
+  bool existsSync() {
+    fileSystem.opHandle.call(path, FileSystemOp.exists);
+    return backingOrNull?.stat.type == expectedType;
+  }
+
+  @override
+  Future<File> create({bool recursive = false, bool exclusive = false}) async {
+    createSync(recursive: recursive, exclusive: exclusive);
+    return this;
+  }
+
+  // TODO(dartbug.com/49647): Pass `exclusive` through after it lands.
+  @override
+  void createSync({bool recursive = false, bool exclusive = false}) {
+    fileSystem.opHandle(path, FileSystemOp.create);
+    _doCreate(recursive: recursive /*, exclusive: exclusive*/);
+  }
+
+  Node? _doCreate({bool recursive = false}) {
+    Node? node = internalCreateSync(
+      followTailLink: true,
+      createChild: (DirectoryNode parent, bool isFinalSegment) {
+        if (isFinalSegment) {
+          return FileNode(parent);
+        } else if (recursive) {
+          return DirectoryNode(parent);
+        }
+        return null;
+      },
+    );
+    if (node?.type != expectedType) {
+      // There was an existing non-file entity at this object's path
+      assert(node?.type == FileSystemEntityType.directory);
+      throw common.isADirectory(path);
+    }
+    return node;
+  }
+
+  @override
+  Future<File> rename(String newPath) async => renameSync(newPath);
+
+  @override
+  File renameSync(String newPath) => internalRenameSync(
+        newPath,
+        followTailLink: true,
+        checkType: (Node node) {
+          FileSystemEntityType actualType = node.stat.type;
+          if (actualType != expectedType) {
+            throw actualType == FileSystemEntityType.notFound
+                ? common.noSuchFileOrDirectory(path)
+                : common.isADirectory(path);
+          }
+        },
+      ) as File;
+
+  @override
+  Future<File> copy(String newPath) async => copySync(newPath);
+
+  @override
+  File copySync(String newPath) {
+    fileSystem.opHandle(path, FileSystemOp.copy);
+    FileNode sourceNode = resolvedBacking as FileNode;
+    fileSystem.findNode(
+      newPath,
+      segmentVisitor: (
+        DirectoryNode parent,
+        String childName,
+        Node? child,
+        int currentSegment,
+        int finalSegment,
+      ) {
+        if (currentSegment == finalSegment) {
+          if (child != null) {
+            if (utils.isLink(child)) {
+              List<String> ledger = <String>[];
+              child = utils.resolveLinks(child as LinkNode, () => newPath,
+                  ledger: ledger);
+              checkExists(child, () => newPath);
+              parent = child.parent;
+              childName = ledger.last;
+              assert(parent.children.containsKey(childName));
+            }
+            utils.checkType(expectedType, child.type, () => newPath);
+            parent.children.remove(childName);
+          }
+          FileNode newNode = FileNode(parent);
+          newNode.copyFrom(sourceNode);
+          parent.children[childName] = newNode;
+        }
+        return child;
+      },
+    );
+    return clone(newPath);
+  }
+
+  @override
+  Future<int> length() async => lengthSync();
+
+  @override
+  int lengthSync() => (resolvedBacking as FileNode).size;
+
+  @override
+  File get absolute => super.absolute as File;
+
+  @override
+  Future<DateTime> lastAccessed() async => lastAccessedSync();
+
+  @override
+  DateTime lastAccessedSync() => (resolvedBacking as FileNode).stat.accessed;
+
+  @override
+  Future<dynamic> setLastAccessed(DateTime time) async =>
+      setLastAccessedSync(time);
+
+  @override
+  void setLastAccessedSync(DateTime time) {
+    FileNode node = resolvedBacking as FileNode;
+    node.accessed = time.millisecondsSinceEpoch;
+  }
+
+  @override
+  Future<DateTime> lastModified() async => lastModifiedSync();
+
+  @override
+  DateTime lastModifiedSync() => (resolvedBacking as FileNode).stat.modified;
+
+  @override
+  Future<dynamic> setLastModified(DateTime time) async =>
+      setLastModifiedSync(time);
+
+  @override
+  void setLastModifiedSync(DateTime time) {
+    FileNode node = resolvedBacking as FileNode;
+    node.modified = time.millisecondsSinceEpoch;
+  }
+
+  @override
+  Future<io.RandomAccessFile> open(
+          {io.FileMode mode = io.FileMode.read}) async =>
+      openSync(mode: mode);
+
+  @override
+  io.RandomAccessFile openSync({io.FileMode mode = io.FileMode.read}) {
+    fileSystem.opHandle(path, FileSystemOp.open);
+    if (utils.isWriteMode(mode) && !existsSync()) {
+      // [resolvedBacking] requires that the file already exists, so we must
+      // create it here first.
+      createSync();
+    }
+
+    return MemoryRandomAccessFile(path, resolvedBacking as FileNode, mode);
+  }
+
+  @override
+  Stream<List<int>> openRead([int? start, int? end]) {
+    fileSystem.opHandle(path, FileSystemOp.open);
+    try {
+      FileNode node = resolvedBacking as FileNode;
+      Uint8List content = node.content;
+      if (start != null) {
+        content = end == null
+            ? content.sublist(start)
+            : content.sublist(start, math.min(end, content.length));
+      }
+      return Stream.value(content);
+    } catch (e) {
+      return Stream.error(e);
+    }
+  }
+
+  @override
+  io.IOSink openWrite({
+    io.FileMode mode = io.FileMode.write,
+    Encoding encoding = utf8,
+  }) {
+    fileSystem.opHandle(path, FileSystemOp.open);
+    if (!utils.isWriteMode(mode)) {
+      throw ArgumentError.value(mode, 'mode',
+          'Must be either WRITE, APPEND, WRITE_ONLY, or WRITE_ONLY_APPEND');
+    }
+    return _FileSink.fromFile(this, mode, encoding);
+  }
+
+  @override
+  Future<Uint8List> readAsBytes() async => readAsBytesSync();
+
+  @override
+  Uint8List readAsBytesSync() {
+    fileSystem.opHandle(path, FileSystemOp.read);
+    return Uint8List.fromList((resolvedBacking as FileNode).content);
+  }
+
+  @override
+  Future<String> readAsString({Encoding encoding = utf8}) async =>
+      readAsStringSync(encoding: encoding);
+
+  @override
+  String readAsStringSync({Encoding encoding = utf8}) {
+    try {
+      return encoding.decode(readAsBytesSync());
+    } on FormatException catch (err) {
+      throw FileSystemException(err.message, path);
+    }
+  }
+
+  @override
+  Future<List<String>> readAsLines({Encoding encoding = utf8}) async =>
+      readAsLinesSync(encoding: encoding);
+
+  @override
+  List<String> readAsLinesSync({Encoding encoding = utf8}) {
+    String str = readAsStringSync(encoding: encoding);
+
+    if (str.isEmpty) {
+      return <String>[];
+    }
+
+    final List<String> lines = str.split('\n');
+    if (str.endsWith('\n')) {
+      // A final newline should not create an additional line.
+      lines.removeLast();
+    }
+
+    return lines;
+  }
+
+  @override
+  Future<File> writeAsBytes(
+    List<int> bytes, {
+    io.FileMode mode = io.FileMode.write,
+    bool flush = false,
+  }) async {
+    writeAsBytesSync(bytes, mode: mode, flush: flush);
+    return this;
+  }
+
+  @override
+  void writeAsBytesSync(
+    List<int> bytes, {
+    io.FileMode mode = io.FileMode.write,
+    bool flush = false,
+  }) {
+    if (!utils.isWriteMode(mode)) {
+      throw common.badFileDescriptor(path);
+    }
+    FileNode node = _resolvedBackingOrCreate;
+    _truncateIfNecessary(node, mode);
+    fileSystem.opHandle(path, FileSystemOp.write);
+    node.write(bytes);
+    node.touch();
+  }
+
+  @override
+  Future<File> writeAsString(
+    String contents, {
+    io.FileMode mode = io.FileMode.write,
+    Encoding encoding = utf8,
+    bool flush = false,
+  }) async {
+    writeAsStringSync(contents, mode: mode, encoding: encoding, flush: flush);
+    return this;
+  }
+
+  @override
+  void writeAsStringSync(
+    String contents, {
+    io.FileMode mode = io.FileMode.write,
+    Encoding encoding = utf8,
+    bool flush = false,
+  }) =>
+      writeAsBytesSync(encoding.encode(contents), mode: mode, flush: flush);
+
+  @override
+  @protected
+  File clone(String path) => MemoryFile(fileSystem, path);
+
+  void _truncateIfNecessary(FileNode node, io.FileMode mode) {
+    if (mode == io.FileMode.write || mode == io.FileMode.writeOnly) {
+      node.clear();
+    }
+  }
+
+  @override
+  String toString() => "MemoryFile: '$path'";
+}
+
+/// Implementation of an [io.IOSink] that's backed by a [FileNode].
+class _FileSink implements io.IOSink {
+  factory _FileSink.fromFile(
+    MemoryFile file,
+    io.FileMode mode,
+    Encoding encoding,
+  ) {
+    late FileNode node;
+    Exception? deferredException;
+
+    // Resolve the backing immediately to ensure that the [FileNode] we write
+    // to is the same as when [openWrite] was called.  This can matter if the
+    // file is moved or removed while open.
+    try {
+      node = file._resolvedBackingOrCreate;
+    } on Exception catch (e) {
+      // For behavioral consistency with [LocalFile], do not report failures
+      // immediately.
+      deferredException = e;
+    }
+
+    Future<FileNode> future = Future<FileNode>.microtask(() {
+      if (deferredException != null) {
+        throw deferredException;
+      }
+      file._truncateIfNecessary(node, mode);
+      return node;
+    });
+    return _FileSink._(future, encoding);
+  }
+
+  _FileSink._(Future<FileNode> node, this.encoding) : _pendingWrites = node;
+
+  final Completer<void> _completer = Completer<void>();
+
+  Future<FileNode> _pendingWrites;
+  Completer<void>? _streamCompleter;
+  bool _isClosed = false;
+
+  @override
+  Encoding encoding;
+
+  bool get isStreaming => !(_streamCompleter?.isCompleted ?? true);
+
+  @override
+  void add(List<int> data) {
+    _checkNotStreaming();
+    if (_isClosed) {
+      throw StateError('StreamSink is closed');
+    }
+
+    _addData(data);
+  }
+
+  @override
+  void write(Object? obj) => add(encoding.encode(obj?.toString() ?? 'null'));
+
+  @override
+  void writeAll(Iterable<dynamic> objects, [String separator = '']) {
+    bool firstIter = true;
+    for (dynamic obj in objects) {
+      if (!firstIter) {
+        write(separator);
+      }
+      firstIter = false;
+      write(obj);
+    }
+  }
+
+  @override
+  void writeln([Object? obj = '']) {
+    write(obj);
+    write('\n');
+  }
+
+  @override
+  void writeCharCode(int charCode) => write(String.fromCharCode(charCode));
+
+  @override
+  void addError(Object error, [StackTrace? stackTrace]) {
+    _checkNotStreaming();
+    _completer.completeError(error, stackTrace);
+  }
+
+  @override
+  Future<void> addStream(Stream<List<int>> stream) {
+    _checkNotStreaming();
+    _streamCompleter = Completer<void>();
+
+    stream.listen(
+      (List<int> data) => _addData(data),
+      cancelOnError: true,
+      onError: (Object error, StackTrace stackTrace) {
+        _streamCompleter!.completeError(error, stackTrace);
+        _streamCompleter = null;
+      },
+      onDone: () {
+        _streamCompleter!.complete();
+        _streamCompleter = null;
+      },
+    );
+    return _streamCompleter!.future;
+  }
+
+  @override
+  Future<void> flush() {
+    _checkNotStreaming();
+    return _pendingWrites;
+  }
+
+  @override
+  Future<void> close() {
+    _checkNotStreaming();
+    if (!_isClosed) {
+      _isClosed = true;
+      _pendingWrites.then(
+        (_) => _completer.complete(),
+        onError: (Object error, StackTrace stackTrace) =>
+            _completer.completeError(error, stackTrace),
+      );
+    }
+    return _completer.future;
+  }
+
+  @override
+  Future<void> get done => _completer.future;
+
+  void _addData(List<int> data) {
+    _pendingWrites = _pendingWrites.then((FileNode node) {
+      node.write(data);
+      return node;
+    });
+  }
+
+  void _checkNotStreaming() {
+    if (isStreaming) {
+      throw StateError('StreamSink is bound to a stream');
+    }
+  }
+}
diff --git a/pkgs/file/lib/src/backends/memory/memory_file_stat.dart b/pkgs/file/lib/src/backends/memory/memory_file_stat.dart
new file mode 100644
index 0000000..94f86d1
--- /dev/null
+++ b/pkgs/file/lib/src/backends/memory/memory_file_stat.dart
@@ -0,0 +1,68 @@
+// Copyright (c) 2017, 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.
+
+import 'package:file/src/io.dart' as io;
+
+/// Internal implementation of [io.FileStat].
+class MemoryFileStat implements io.FileStat {
+  /// Creates a new [MemoryFileStat] with the specified properties.
+  const MemoryFileStat(
+    this.changed,
+    this.modified,
+    this.accessed,
+    this.type,
+    this.mode,
+    this.size,
+  );
+
+  MemoryFileStat._internalNotFound()
+      : changed = DateTime(0),
+        modified = DateTime(0),
+        accessed = DateTime(0),
+        type = io.FileSystemEntityType.notFound,
+        mode = 0,
+        size = -1;
+
+  /// Shared instance representing a non-existent entity.
+  static final MemoryFileStat notFound = MemoryFileStat._internalNotFound();
+
+  @override
+  final DateTime changed;
+
+  @override
+  final DateTime modified;
+
+  @override
+  final DateTime accessed;
+
+  @override
+  final io.FileSystemEntityType type;
+
+  @override
+  final int mode;
+
+  @override
+  final int size;
+
+  @override
+  String modeString() {
+    int permissions = mode & 0xFFF;
+    List<String> codes = const <String>[
+      '---',
+      '--x',
+      '-w-',
+      '-wx',
+      'r--',
+      'r-x',
+      'rw-',
+      'rwx',
+    ];
+    List<String> result = <String>[];
+    result
+      ..add(codes[(permissions >> 6) & 0x7])
+      ..add(codes[(permissions >> 3) & 0x7])
+      ..add(codes[permissions & 0x7]);
+    return result.join();
+  }
+}
diff --git a/pkgs/file/lib/src/backends/memory/memory_file_system.dart b/pkgs/file/lib/src/backends/memory/memory_file_system.dart
new file mode 100644
index 0000000..f3cdaee
--- /dev/null
+++ b/pkgs/file/lib/src/backends/memory/memory_file_system.dart
@@ -0,0 +1,282 @@
+// Copyright (c) 2017, 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.
+
+import 'package:file/file.dart';
+import 'package:file/src/backends/memory/operations.dart';
+import 'package:file/src/io.dart' as io;
+import 'package:path/path.dart' as p;
+
+import 'clock.dart';
+import 'common.dart';
+import 'memory_directory.dart';
+import 'memory_file.dart';
+import 'memory_file_stat.dart';
+import 'memory_link.dart';
+import 'node.dart';
+import 'style.dart';
+import 'utils.dart' as utils;
+
+const String _thisDir = '.';
+const String _parentDir = '..';
+
+void _defaultOpHandle(String context, FileSystemOp operation) {}
+
+/// An implementation of [FileSystem] that exists entirely in memory with an
+/// internal representation loosely based on the Filesystem Hierarchy Standard.
+///
+/// [MemoryFileSystem] is suitable for mocking and tests, as well as for
+/// caching or staging before writing or reading to a live system.
+///
+/// This implementation of the [FileSystem] interface does not directly use
+/// any `dart:io` APIs; it merely uses the library's enum values and interfaces.
+/// As such, it is suitable for use in the browser.
+abstract class MemoryFileSystem implements StyleableFileSystem {
+  /// Creates a new `MemoryFileSystem`.
+  ///
+  /// The file system will be empty, and the current directory will be the
+  /// root directory.
+  ///
+  /// The clock will be a real-time clock; file modification times will
+  /// reflect the real time as reported by the operating system.
+  ///
+  /// If [style] is specified, the file system will use the specified path
+  /// style. The default is [FileSystemStyle.posix].
+  factory MemoryFileSystem({
+    FileSystemStyle style = FileSystemStyle.posix,
+    void Function(String context, FileSystemOp operation) opHandle =
+        _defaultOpHandle,
+  }) =>
+      _MemoryFileSystem(
+        style: style,
+        clock: const Clock.realTime(),
+        opHandle: opHandle,
+      );
+
+  /// Creates a new `MemoryFileSystem` that has a fake clock.
+  ///
+  /// The file system will be empty, and the current directory will be the
+  /// root directory.
+  ///
+  /// The clock will increase monotonically each time it is used, disconnected
+  /// from any real-world clock.
+  ///
+  /// If [style] is specified, the file system will use the specified path
+  /// style. The default is [FileSystemStyle.posix].
+  factory MemoryFileSystem.test({
+    FileSystemStyle style = FileSystemStyle.posix,
+    void Function(String context, FileSystemOp operation) opHandle =
+        _defaultOpHandle,
+  }) =>
+      _MemoryFileSystem(
+        style: style,
+        clock: Clock.monotonicTest(),
+        opHandle: opHandle,
+      );
+}
+
+/// Internal implementation of [MemoryFileSystem].
+class _MemoryFileSystem extends FileSystem
+    implements MemoryFileSystem, NodeBasedFileSystem {
+  _MemoryFileSystem({
+    this.style = FileSystemStyle.posix,
+    required this.clock,
+    this.opHandle = _defaultOpHandle,
+  }) : _context = style.contextFor(style.root) {
+    _root = RootNode(this);
+  }
+
+  RootNode? _root;
+  String? _systemTemp;
+  p.Context _context;
+
+  @override
+  final Function(String context, FileSystemOp operation) opHandle;
+
+  @override
+  final Clock clock;
+
+  @override
+  final FileSystemStyle style;
+
+  @override
+  RootNode? get root => _root;
+
+  @override
+  String get cwd => _context.current;
+
+  @override
+  Directory directory(dynamic path) => MemoryDirectory(this, getPath(path));
+
+  @override
+  File file(dynamic path) => MemoryFile(this, getPath(path));
+
+  @override
+  Link link(dynamic path) => MemoryLink(this, getPath(path));
+
+  @override
+  p.Context get path => _context;
+
+  /// Gets the system temp directory. This directory will be created on-demand
+  /// in the root of the file system. Once created, its location is fixed for
+  /// the life of the process.
+  @override
+  Directory get systemTempDirectory {
+    _systemTemp ??= directory(style.root).createTempSync('.tmp_').path;
+    return directory(_systemTemp)..createSync();
+  }
+
+  @override
+  Directory get currentDirectory => directory(cwd);
+
+  @override
+  set currentDirectory(dynamic path) {
+    String value;
+    if (path is io.Directory) {
+      value = path.path;
+    } else if (path is String) {
+      value = path;
+    } else {
+      throw ArgumentError('Invalid type for "path": ${path?.runtimeType}');
+    }
+
+    value = directory(value).resolveSymbolicLinksSync();
+    Node? node = findNode(value);
+    checkExists(node, () => value);
+    utils.checkIsDir(node!, () => value);
+    assert(_context.isAbsolute(value));
+    _context = style.contextFor(value);
+  }
+
+  @override
+  Future<io.FileStat> stat(String path) async => statSync(path);
+
+  @override
+  io.FileStat statSync(String path) {
+    try {
+      return findNode(path)?.stat ?? MemoryFileStat.notFound;
+    } on io.FileSystemException {
+      return MemoryFileStat.notFound;
+    }
+  }
+
+  @override
+  Future<bool> identical(String path1, String path2) async =>
+      identicalSync(path1, path2);
+
+  @override
+  bool identicalSync(String path1, String path2) {
+    Node? node1 = findNode(path1);
+    checkExists(node1, () => path1);
+    Node? node2 = findNode(path2);
+    checkExists(node2, () => path2);
+    return node1 != null && node1 == node2;
+  }
+
+  @override
+  bool get isWatchSupported => false;
+
+  @override
+  Future<io.FileSystemEntityType> type(
+    String path, {
+    bool followLinks = true,
+  }) async =>
+      typeSync(path, followLinks: followLinks);
+
+  @override
+  io.FileSystemEntityType typeSync(String path, {bool followLinks = true}) {
+    Node? node;
+    try {
+      node = findNode(path, followTailLink: followLinks);
+    } on io.FileSystemException {
+      node = null;
+    }
+    if (node == null) {
+      return io.FileSystemEntityType.notFound;
+    }
+    return node.type;
+  }
+
+  /// Gets the node backing for the current working directory. Note that this
+  /// can return null if the directory has been deleted or moved from under our
+  /// feet.
+  DirectoryNode? get _current => findNode(cwd) as DirectoryNode?;
+
+  @override
+  Node? findNode(
+    String path, {
+    Node? reference,
+    SegmentVisitor? segmentVisitor,
+    bool visitLinks = false,
+    List<String>? pathWithSymlinks,
+    bool followTailLink = false,
+  }) {
+    if (path.isEmpty) {
+      return null;
+    } else if (_context.isAbsolute(path)) {
+      reference = _root;
+      path = path.substring(style.drive.length);
+    } else {
+      reference ??= _current;
+    }
+
+    List<String> parts = path.split(style.separator)
+      ..removeWhere(utils.isEmpty);
+    DirectoryNode? directory = reference?.directory;
+    Node? child = directory;
+
+    int finalSegment = parts.length - 1;
+    for (int i = 0; i <= finalSegment; i++) {
+      String basename = parts[i];
+      assert(basename.isNotEmpty);
+
+      switch (basename) {
+        case _thisDir:
+          child = directory;
+          break;
+        case _parentDir:
+          child = directory?.parent;
+          directory = directory?.parent;
+          break;
+        default:
+          child = directory?.children[basename];
+      }
+
+      if (pathWithSymlinks != null) {
+        pathWithSymlinks.add(basename);
+      }
+
+      // Generates a subpath for the current segment.
+      String subpath() => parts.sublist(0, i + 1).join(_context.separator);
+
+      if (utils.isLink(child) && (i < finalSegment || followTailLink)) {
+        if (visitLinks || segmentVisitor == null) {
+          if (segmentVisitor != null) {
+            child =
+                segmentVisitor(directory!, basename, child, i, finalSegment);
+          }
+          child = utils.resolveLinks(child as LinkNode, subpath,
+              ledger: pathWithSymlinks);
+        } else {
+          child = utils.resolveLinks(
+            child as LinkNode,
+            subpath,
+            ledger: pathWithSymlinks,
+            tailVisitor: (DirectoryNode parent, String childName, Node? child) {
+              return segmentVisitor(parent, childName, child, i, finalSegment);
+            },
+          );
+        }
+      } else if (segmentVisitor != null) {
+        child = segmentVisitor(directory!, basename, child, i, finalSegment);
+      }
+
+      if (i < finalSegment) {
+        checkExists(child, subpath);
+        utils.checkIsDir(child!, subpath);
+        directory = child as DirectoryNode;
+      }
+    }
+    return child;
+  }
+}
diff --git a/pkgs/file/lib/src/backends/memory/memory_file_system_entity.dart b/pkgs/file/lib/src/backends/memory/memory_file_system_entity.dart
new file mode 100644
index 0000000..ad987d7
--- /dev/null
+++ b/pkgs/file/lib/src/backends/memory/memory_file_system_entity.dart
@@ -0,0 +1,309 @@
+// Copyright (c) 2017, 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.
+
+import 'package:file/file.dart';
+import 'package:file/src/common.dart' as common;
+import 'package:file/src/io.dart' as io;
+import 'package:meta/meta.dart';
+
+import 'common.dart';
+import 'memory_directory.dart';
+import 'node.dart';
+import 'operations.dart';
+import 'style.dart';
+import 'utils.dart' as utils;
+
+/// Validator function for use with `_renameSync`. This will be invoked if the
+/// rename would overwrite an existing entity at the new path. If this operation
+/// should not be allowed, this function is expected to throw a
+/// [io.FileSystemException]. The lack of such an exception will be interpreted
+/// as the overwrite being permissible.
+typedef RenameOverwriteValidator<T extends Node> = void Function(
+    T existingNode);
+
+/// Base class for all in-memory file system entity types.
+abstract class MemoryFileSystemEntity implements FileSystemEntity {
+  /// Constructor for subclasses.
+  const MemoryFileSystemEntity(this.fileSystem, this.path);
+
+  @override
+  final NodeBasedFileSystem fileSystem;
+
+  @override
+  final String path;
+
+  @override
+  String get dirname => fileSystem.path.dirname(path);
+
+  @override
+  String get basename => fileSystem.path.basename(path);
+
+  /// Returns the expected type of this entity, which may differ from the type
+  /// of the node that's found at the path specified by this entity.
+  io.FileSystemEntityType get expectedType;
+
+  /// Gets the node that backs this file system entity, or null if this
+  /// entity does not exist.
+  @protected
+  Node? get backingOrNull {
+    try {
+      return fileSystem.findNode(path);
+    } on io.FileSystemException {
+      return null;
+    }
+  }
+
+  /// Gets the node that backs this file system entity. Throws a
+  /// [io.FileSystemException] if this entity doesn't exist.
+  ///
+  /// The type of the node is not guaranteed to match [expectedType].
+  @protected
+  Node get backing {
+    Node? node = fileSystem.findNode(path);
+    checkExists(node, () => path);
+    return node!;
+  }
+
+  /// Gets the node that backs this file system entity, or if that node is
+  /// a symbolic link, the target node. This also will check that the type of
+  /// the node (after symlink resolution) matches [expectedType]. If the type
+  /// doesn't match, this will throw a [io.FileSystemException].
+  @protected
+  Node get resolvedBacking {
+    Node node = backing;
+    node = utils.isLink(node)
+        ? utils.resolveLinks(node as LinkNode, () => path)
+        : node;
+    utils.checkType(expectedType, node.type, () => path);
+    return node;
+  }
+
+  /// Checks the expected type of this file system entity against the specified
+  /// node's `stat` type, throwing a [FileSystemException] if the types don't
+  /// match. Note that since this checks the node's `stat` type, symbolic links
+  /// will be resolved to their target type for the purpose of this validation.
+  ///
+  /// Protected methods that accept a `checkType` argument will default to this
+  /// method if the `checkType` argument is unspecified.
+  @protected
+  void defaultCheckType(Node node) {
+    utils.checkType(expectedType, node.stat.type, () => path);
+  }
+
+  @override
+  Uri get uri {
+    return Uri.file(path, windows: fileSystem.style == FileSystemStyle.windows);
+  }
+
+  @override
+  Future<bool> exists() async => existsSync();
+
+  @override
+  Future<String> resolveSymbolicLinks() async => resolveSymbolicLinksSync();
+
+  @override
+  String resolveSymbolicLinksSync() {
+    if (path.isEmpty) {
+      throw common.noSuchFileOrDirectory(path);
+    }
+    List<String> ledger = <String>[];
+    if (isAbsolute) {
+      ledger.add(fileSystem.style.drive);
+    }
+    Node? node = fileSystem.findNode(path,
+        pathWithSymlinks: ledger, followTailLink: true);
+    checkExists(node, () => path);
+    String resolved = ledger.join(fileSystem.path.separator);
+    if (resolved == fileSystem.style.drive) {
+      resolved = fileSystem.style.root;
+    } else if (!fileSystem.path.isAbsolute(resolved)) {
+      resolved = fileSystem.cwd + fileSystem.path.separator + resolved;
+    }
+    return fileSystem.path.normalize(resolved);
+  }
+
+  @override
+  Future<io.FileStat> stat() => fileSystem.stat(path);
+
+  @override
+  io.FileStat statSync() => fileSystem.statSync(path);
+
+  @override
+  Future<FileSystemEntity> delete({bool recursive = false}) async {
+    deleteSync(recursive: recursive);
+    return this;
+  }
+
+  @override
+  void deleteSync({bool recursive = false}) =>
+      internalDeleteSync(recursive: recursive);
+
+  @override
+  Stream<io.FileSystemEvent> watch({
+    int events = io.FileSystemEvent.all,
+    bool recursive = false,
+  }) =>
+      throw UnsupportedError('Watching not supported in MemoryFileSystem');
+
+  @override
+  bool get isAbsolute => fileSystem.path.isAbsolute(path);
+
+  @override
+  FileSystemEntity get absolute {
+    String absolutePath = path;
+    if (!fileSystem.path.isAbsolute(absolutePath)) {
+      absolutePath = fileSystem.path.join(fileSystem.cwd, absolutePath);
+    }
+    return clone(absolutePath);
+  }
+
+  @override
+  Directory get parent => MemoryDirectory(fileSystem, dirname);
+
+  /// Helper method for subclasses wishing to synchronously create this entity.
+  /// This method will traverse the path to this entity one segment at a time,
+  /// calling [createChild] for each segment whose child does not already exist.
+  ///
+  /// When [createChild] is invoked:
+  /// - `parent` will be the parent node for the current segment and is
+  ///   guaranteed to be non-null.
+  /// - `isFinalSegment` will indicate whether the current segment is the tail
+  ///   segment, which in turn indicates that this is the segment into which to
+  ///   create the node for this entity.
+  ///
+  /// This method returns with the backing node for the entity at this [path].
+  /// If an entity already existed at this path, [createChild] will not be
+  /// invoked at all, and this method will return with the backing node for the
+  /// existing entity (whose type may differ from this entity's type).
+  ///
+  /// If [followTailLink] is true and the result node is a link, this will
+  /// resolve it to its target prior to returning it.
+  @protected
+  Node? internalCreateSync({
+    required Node? Function(DirectoryNode parent, bool isFinalSegment)
+        createChild,
+    bool followTailLink = false,
+    bool visitLinks = false,
+  }) {
+    return fileSystem.findNode(
+      path,
+      followTailLink: followTailLink,
+      visitLinks: visitLinks,
+      segmentVisitor: (
+        DirectoryNode parent,
+        String childName,
+        Node? child,
+        int currentSegment,
+        int finalSegment,
+      ) {
+        if (child == null) {
+          assert(!parent.children.containsKey(childName));
+          child = createChild(parent, currentSegment == finalSegment);
+          if (child != null) {
+            parent.children[childName] = child;
+          }
+        }
+        return child;
+      },
+    );
+  }
+
+  /// Helper method for subclasses wishing to synchronously rename this entity.
+  /// This method will look for an existing file system entity at the location
+  /// identified by [newPath], and if it finds an existing entity, it will check
+  /// the following:
+  ///
+  /// - If the entity is of a different type than this entity, the operation
+  ///   will fail, and a [io.FileSystemException] will be thrown.
+  /// - If the caller has specified [validateOverwriteExistingEntity], then that
+  ///   method will be invoked and passed the node backing of the existing
+  ///   entity that would overwritten by the rename action. That callback is
+  ///   expected to throw a [io.FileSystemException] if overwriting the existing
+  ///   entity is not allowed.
+  ///
+  /// If the previous two checks pass, or if there was no existing entity at
+  /// the specified location, this will perform the rename.
+  ///
+  /// If [newPath] cannot be traversed to because its directory does not exist,
+  /// a [io.FileSystemException] will be thrown.
+  ///
+  /// If [followTailLink] is true and there is an existing link at the location
+  /// identified by [newPath], this will resolve the link to its target prior
+  /// to running the validation checks above.
+  ///
+  /// If [checkType] is specified, it will be used to validate that the file
+  /// system entity that exists at [path] is of the expected type. By default,
+  /// [defaultCheckType] is used to perform this validation.
+  @protected
+  FileSystemEntity internalRenameSync<T extends Node>(
+    String newPath, {
+    RenameOverwriteValidator<T>? validateOverwriteExistingEntity,
+    bool followTailLink = false,
+    utils.TypeChecker? checkType,
+  }) {
+    Node node = backing;
+    (checkType ?? defaultCheckType)(node);
+    fileSystem.findNode(
+      newPath,
+      segmentVisitor: (
+        DirectoryNode parent,
+        String childName,
+        Node? child,
+        int currentSegment,
+        int finalSegment,
+      ) {
+        if (currentSegment == finalSegment) {
+          if (child != null) {
+            if (followTailLink) {
+              FileSystemEntityType childType = child.stat.type;
+              if (childType != FileSystemEntityType.notFound) {
+                utils.checkType(expectedType, child.stat.type, () => newPath);
+              }
+            } else {
+              utils.checkType(expectedType, child.type, () => newPath);
+            }
+            if (validateOverwriteExistingEntity != null) {
+              validateOverwriteExistingEntity(child as T);
+            }
+            parent.children.remove(childName);
+          }
+          node.parent.children.remove(basename);
+          parent.children[childName] = node;
+          node.parent = parent;
+        }
+        return child;
+      },
+    );
+    return clone(newPath);
+  }
+
+  /// Deletes this entity from the node tree.
+  ///
+  /// If [checkType] is specified, it will be used to validate that the file
+  /// system entity that exists at [path] is of the expected type. By default,
+  /// [defaultCheckType] is used to perform this validation.
+  @protected
+  void internalDeleteSync({
+    bool recursive = false,
+    utils.TypeChecker? checkType,
+  }) {
+    fileSystem.opHandle(path, FileSystemOp.delete);
+    Node node = backing;
+    if (!recursive) {
+      if (node is DirectoryNode && node.children.isNotEmpty) {
+        throw common.directoryNotEmpty(path);
+      }
+      (checkType ?? defaultCheckType)(node);
+    }
+    // Once we remove this reference, the node and all its children will be
+    // garbage collected; we don't need to explicitly delete all children in
+    // the recursive:true case.
+    node.parent.children.remove(basename);
+  }
+
+  /// Creates a new entity with the same type as this entity but with the
+  /// specified path.
+  @protected
+  FileSystemEntity clone(String path);
+}
diff --git a/pkgs/file/lib/src/backends/memory/memory_link.dart b/pkgs/file/lib/src/backends/memory/memory_link.dart
new file mode 100644
index 0000000..7d5afb4
--- /dev/null
+++ b/pkgs/file/lib/src/backends/memory/memory_link.dart
@@ -0,0 +1,113 @@
+// Copyright (c) 2017, 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.
+
+import 'package:file/file.dart';
+import 'package:file/src/common.dart' as common;
+import 'package:file/src/io.dart' as io;
+import 'package:meta/meta.dart';
+
+import 'memory_file_system_entity.dart';
+import 'node.dart';
+import 'operations.dart';
+import 'utils.dart' as utils;
+
+/// Internal implementation of [Link].
+class MemoryLink extends MemoryFileSystemEntity implements Link {
+  /// Instantiates a new [MemoryLink].
+  const MemoryLink(NodeBasedFileSystem fileSystem, String path)
+      : super(fileSystem, path);
+
+  @override
+  io.FileSystemEntityType get expectedType => io.FileSystemEntityType.link;
+
+  @override
+  bool existsSync() {
+    fileSystem.opHandle.call(path, FileSystemOp.exists);
+    return backingOrNull?.type == expectedType;
+  }
+
+  @override
+  Future<Link> rename(String newPath) async => renameSync(newPath);
+
+  @override
+  Link renameSync(String newPath) => internalRenameSync(
+        newPath,
+        checkType: (Node node) {
+          if (node.type != expectedType) {
+            throw node.type == FileSystemEntityType.directory
+                ? common.isADirectory(newPath)
+                : common.invalidArgument(newPath);
+          }
+        },
+      ) as Link;
+
+  @override
+  Future<Link> create(String target, {bool recursive = false}) async {
+    createSync(target, recursive: recursive);
+    return this;
+  }
+
+  @override
+  void createSync(String target, {bool recursive = false}) {
+    bool preexisting = true;
+    fileSystem.opHandle(path, FileSystemOp.create);
+    internalCreateSync(
+        createChild: (DirectoryNode parent, bool isFinalSegment) {
+      if (isFinalSegment) {
+        preexisting = false;
+        return LinkNode(parent, target);
+      } else if (recursive) {
+        return DirectoryNode(parent);
+      }
+      return null;
+    });
+    if (preexisting) {
+      // Per the spec, this is an error.
+      throw common.fileExists(path);
+    }
+  }
+
+  @override
+  Future<Link> update(String target) async {
+    updateSync(target);
+    return this;
+  }
+
+  @override
+  void updateSync(String target) {
+    Node node = backing;
+    utils.checkType(expectedType, node.type, () => path);
+    (node as LinkNode).target = target;
+  }
+
+  @override
+  void deleteSync({bool recursive = false}) => internalDeleteSync(
+        recursive: recursive,
+        checkType: (Node node) =>
+            utils.checkType(expectedType, node.type, () => path),
+      );
+
+  @override
+  Future<String> target() async => targetSync();
+
+  @override
+  String targetSync() {
+    Node node = backing;
+    if (node.type != expectedType) {
+      // Note: this may change; https://github.com/dart-lang/sdk/issues/28204
+      throw common.noSuchFileOrDirectory(path);
+    }
+    return (node as LinkNode).target;
+  }
+
+  @override
+  Link get absolute => super.absolute as Link;
+
+  @override
+  @protected
+  Link clone(String path) => MemoryLink(fileSystem, path);
+
+  @override
+  String toString() => "MemoryLink: '$path'";
+}
diff --git a/pkgs/file/lib/src/backends/memory/memory_random_access_file.dart b/pkgs/file/lib/src/backends/memory/memory_random_access_file.dart
new file mode 100644
index 0000000..d4fe73d
--- /dev/null
+++ b/pkgs/file/lib/src/backends/memory/memory_random_access_file.dart
@@ -0,0 +1,390 @@
+// Copyright (c) 2020, 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.
+
+import 'dart:convert';
+import 'dart:math' as math show min;
+import 'dart:typed_data';
+
+import 'package:file/src/common.dart' as common;
+import 'package:file/src/io.dart' as io;
+
+import 'memory_file.dart';
+import 'node.dart';
+import 'utils.dart' as utils;
+
+/// A [MemoryFileSystem]-backed implementation of [io.RandomAccessFile].
+class MemoryRandomAccessFile implements io.RandomAccessFile {
+  /// Constructs a [MemoryRandomAccessFile].
+  ///
+  /// This should be used only by [MemoryFile.open] or [MemoryFile.openSync].
+  MemoryRandomAccessFile(this.path, this._node, this._mode) {
+    switch (_mode) {
+      case io.FileMode.read:
+        break;
+      case io.FileMode.write:
+      case io.FileMode.writeOnly:
+        truncateSync(0);
+        break;
+      case io.FileMode.append:
+      case io.FileMode.writeOnlyAppend:
+        _position = lengthSync();
+        break;
+      default:
+        // [FileMode] provides no way of retrieving its value or name.
+        throw UnimplementedError('Unsupported FileMode');
+    }
+  }
+
+  @override
+  final String path;
+
+  final FileNode _node;
+  final io.FileMode _mode;
+
+  bool _isOpen = true;
+  int _position = 0;
+
+  /// Whether an asynchronous operation is pending.
+  ///
+  /// See [_asyncWrapper] for details.
+  bool get _asyncOperationPending => __asyncOperationPending;
+
+  set _asyncOperationPending(bool value) {
+    assert(__asyncOperationPending != value);
+    __asyncOperationPending = value;
+  }
+
+  bool __asyncOperationPending = false;
+
+  /// Throws a [io.FileSystemException] if an operation is attempted on a file
+  /// that is not open.
+  void _checkOpen() {
+    if (!_isOpen) {
+      throw io.FileSystemException('File closed', path);
+    }
+  }
+
+  /// Throws a [io.FileSystemException] if attempting to read from a file that
+  /// has not been opened for reading.
+  void _checkReadable(String operation) {
+    switch (_mode) {
+      case io.FileMode.read:
+      case io.FileMode.write:
+      case io.FileMode.append:
+        return;
+      case io.FileMode.writeOnly:
+      case io.FileMode.writeOnlyAppend:
+      default:
+        throw io.FileSystemException(
+            '$operation failed', path, common.badFileDescriptor(path).osError);
+    }
+  }
+
+  /// Throws a [io.FileSystemException] if attempting to read from a file that
+  /// has not been opened for writing.
+  void _checkWritable(String operation) {
+    if (utils.isWriteMode(_mode)) {
+      return;
+    }
+
+    throw io.FileSystemException(
+        '$operation failed', path, common.badFileDescriptor(path).osError);
+  }
+
+  /// Throws a [io.FileSystemException] if attempting to perform an operation
+  /// while an asynchronous operation is already in progress.
+  ///
+  /// See [_asyncWrapper] for details.
+  void _checkAsync() {
+    if (_asyncOperationPending) {
+      throw io.FileSystemException(
+          'An async operation is currently pending', path);
+    }
+  }
+
+  /// Wraps a synchronous function to make it appear asynchronous.
+  ///
+  /// [_asyncOperationPending], [_checkAsync], and [_asyncWrapper] are used to
+  /// mimic [RandomAccessFile]'s enforcement that only one asynchronous
+  /// operation is pending for a [RandomAccessFile] instance.  Since
+  /// [MemoryFileSystem]-based classes are likely to be used in tests, fidelity
+  /// is important to catch errors that might occur in production.
+  ///
+  /// [_asyncWrapper] does not call [f] directly since setting and unsetting
+  /// [_asyncOperationPending] synchronously would not be meaningful.  We
+  /// instead execute [f] through a [Future.delayed] callback to better simulate
+  /// asynchrony.
+  Future<R> _asyncWrapper<R>(R Function() f) async {
+    _checkAsync();
+
+    _asyncOperationPending = true;
+    try {
+      return await Future<R>.delayed(
+        Duration.zero,
+        () {
+          // Temporarily reset [_asyncOpPending] in case [f]'s has its own
+          // checks for pending asynchronous operations.
+          _asyncOperationPending = false;
+          try {
+            return f();
+          } finally {
+            _asyncOperationPending = true;
+          }
+        },
+      );
+    } finally {
+      _asyncOperationPending = false;
+    }
+  }
+
+  @override
+  Future<void> close() async => _asyncWrapper(closeSync);
+
+  @override
+  void closeSync() {
+    _checkOpen();
+    _isOpen = false;
+  }
+
+  @override
+  Future<io.RandomAccessFile> flush() async {
+    await _asyncWrapper(flushSync);
+    return this;
+  }
+
+  @override
+  void flushSync() {
+    _checkOpen();
+    _checkAsync();
+  }
+
+  @override
+  Future<int> length() => _asyncWrapper(lengthSync);
+
+  @override
+  int lengthSync() {
+    _checkOpen();
+    _checkAsync();
+    return _node.size;
+  }
+
+  @override
+  Future<io.RandomAccessFile> lock([
+    io.FileLock mode = io.FileLock.exclusive,
+    int start = 0,
+    int end = -1,
+  ]) async {
+    await _asyncWrapper(() => lockSync(mode, start, end));
+    return this;
+  }
+
+  @override
+  void lockSync([
+    io.FileLock mode = io.FileLock.exclusive,
+    int start = 0,
+    int end = -1,
+  ]) {
+    _checkOpen();
+    _checkAsync();
+    // TODO(jamesderlin): Implement, https://github.com/google/file.dart/issues/140
+    throw UnimplementedError('TODO');
+  }
+
+  @override
+  Future<int> position() => _asyncWrapper(positionSync);
+
+  @override
+  int positionSync() {
+    _checkOpen();
+    _checkAsync();
+    return _position;
+  }
+
+  @override
+  Future<Uint8List> read(int bytes) => _asyncWrapper(() => readSync(bytes));
+
+  @override
+  Uint8List readSync(int bytes) {
+    _checkOpen();
+    _checkAsync();
+    _checkReadable('read');
+    // TODO(jamesderlin): Check for integer overflow.
+    final int end = math.min(_position + bytes, lengthSync());
+    final Uint8List copy = _node.content.sublist(_position, end);
+    _position = end;
+    return copy;
+  }
+
+  @override
+  Future<int> readByte() => _asyncWrapper(readByteSync);
+
+  @override
+  int readByteSync() {
+    _checkOpen();
+    _checkAsync();
+    _checkReadable('readByte');
+
+    if (_position >= lengthSync()) {
+      return -1;
+    }
+    return _node.content[_position++];
+  }
+
+  @override
+  Future<int> readInto(List<int> buffer, [int start = 0, int? end]) =>
+      _asyncWrapper(() => readIntoSync(buffer, start, end));
+
+  @override
+  int readIntoSync(List<int> buffer, [int start = 0, int? end]) {
+    _checkOpen();
+    _checkAsync();
+    _checkReadable('readInto');
+
+    end = RangeError.checkValidRange(start, end, buffer.length);
+
+    final int length = lengthSync();
+    int i;
+    for (i = start; i < end && _position < length; i += 1, _position += 1) {
+      buffer[i] = _node.content[_position];
+    }
+    return i - start;
+  }
+
+  @override
+  Future<io.RandomAccessFile> setPosition(int position) async {
+    await _asyncWrapper(() => setPositionSync(position));
+    return this;
+  }
+
+  @override
+  void setPositionSync(int position) {
+    _checkOpen();
+    _checkAsync();
+
+    if (position < 0) {
+      throw io.FileSystemException(
+          'setPosition failed', path, common.invalidArgument(path).osError);
+    }
+
+    // Empirical testing indicates that setting the position to be beyond the
+    // end of the file is legal and will zero-fill upon the next write.
+    _position = position;
+  }
+
+  @override
+  Future<io.RandomAccessFile> truncate(int length) async {
+    await _asyncWrapper(() => truncateSync(length));
+    return this;
+  }
+
+  @override
+  void truncateSync(int length) {
+    _checkOpen();
+    _checkAsync();
+
+    if (length < 0 || !utils.isWriteMode(_mode)) {
+      throw io.FileSystemException(
+          'truncate failed', path, common.invalidArgument(path).osError);
+    }
+
+    final int oldLength = lengthSync();
+    if (length < oldLength) {
+      _node.truncate(length);
+
+      // [_position] is intentionally left untouched to match the observed
+      // behavior of [RandomAccessFile].
+    } else if (length > oldLength) {
+      _node.write(Uint8List(length - oldLength));
+    }
+    assert(lengthSync() == length);
+  }
+
+  @override
+  Future<io.RandomAccessFile> unlock([int start = 0, int end = -1]) async {
+    await _asyncWrapper(() => unlockSync(start, end));
+    return this;
+  }
+
+  @override
+  void unlockSync([int start = 0, int end = -1]) {
+    _checkOpen();
+    _checkAsync();
+    // TODO(jamesderlin): Implement, https://github.com/google/file.dart/issues/140
+    throw UnimplementedError('TODO');
+  }
+
+  @override
+  Future<io.RandomAccessFile> writeByte(int value) async {
+    await _asyncWrapper(() => writeByteSync(value));
+    return this;
+  }
+
+  @override
+  int writeByteSync(int value) {
+    _checkOpen();
+    _checkAsync();
+    _checkWritable('writeByte');
+
+    // [Uint8List] will truncate values to 8-bits automatically, so we don't
+    // need to check [value].
+
+    int length = lengthSync();
+    if (_position >= length) {
+      // If [_position] is out of bounds, [RandomAccessFile] zero-fills the
+      // file.
+      truncateSync(_position + 1);
+      length = lengthSync();
+    }
+    assert(_position < length);
+    _node.content[_position++] = value;
+
+    // Despite what the documentation states, [RandomAccessFile.writeByteSync]
+    // always seems to return 1, even if we had to extend the file for an out of
+    // bounds write.  See https://github.com/dart-lang/sdk/issues/42298.
+    return 1;
+  }
+
+  @override
+  Future<io.RandomAccessFile> writeFrom(
+    List<int> buffer, [
+    int start = 0,
+    int? end,
+  ]) async {
+    await _asyncWrapper(() => writeFromSync(buffer, start, end));
+    return this;
+  }
+
+  @override
+  void writeFromSync(List<int> buffer, [int start = 0, int? end]) {
+    _checkOpen();
+    _checkAsync();
+    _checkWritable('writeFrom');
+
+    end = RangeError.checkValidRange(start, end, buffer.length);
+
+    final int writeByteCount = end - start;
+    final int endPosition = _position + writeByteCount;
+
+    if (endPosition > lengthSync()) {
+      truncateSync(endPosition);
+    }
+
+    _node.content.setRange(_position, endPosition, buffer, start);
+    _position = endPosition;
+  }
+
+  @override
+  Future<io.RandomAccessFile> writeString(
+    String string, {
+    Encoding encoding = utf8,
+  }) async {
+    await _asyncWrapper(() => writeStringSync(string, encoding: encoding));
+    return this;
+  }
+
+  @override
+  void writeStringSync(String string, {Encoding encoding = utf8}) {
+    writeFromSync(encoding.encode(string));
+  }
+}
diff --git a/pkgs/file/lib/src/backends/memory/node.dart b/pkgs/file/lib/src/backends/memory/node.dart
new file mode 100644
index 0000000..ae4d3f7
--- /dev/null
+++ b/pkgs/file/lib/src/backends/memory/node.dart
@@ -0,0 +1,358 @@
+// Copyright (c) 2017, 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.
+
+import 'dart:typed_data';
+
+import 'package:file/file.dart';
+import 'package:file/src/backends/memory/operations.dart';
+import 'package:file/src/io.dart' as io;
+
+import 'clock.dart';
+import 'common.dart';
+import 'memory_file_stat.dart';
+import 'style.dart';
+
+/// Visitor callback for use with [NodeBasedFileSystem.findNode].
+///
+/// [parent] is the parent node of the current path segment and is guaranteed
+/// to be non-null.
+///
+/// [childName] is the basename of the entity at the current path segment. It
+/// is guaranteed to be non-null.
+///
+/// [childNode] is the node at the current path segment. It will be
+/// non-null only if such an entity exists. The return value of this callback
+/// will be used as the value of this node, which allows this callback to
+/// do things like recursively create or delete folders.
+///
+/// [currentSegment] is the index of the current segment within the overall
+/// path that's being walked by [NodeBasedFileSystem.findNode].
+///
+/// [finalSegment] is the index of the final segment that will be walked by
+/// [NodeBasedFileSystem.findNode].
+typedef SegmentVisitor = Node? Function(
+  DirectoryNode parent,
+  String childName,
+  Node? childNode,
+  int currentSegment,
+  int finalSegment,
+);
+
+/// A [FileSystem] whose internal structure is made up of a tree of [Node]
+/// instances, rooted at a single node.
+abstract class NodeBasedFileSystem implements StyleableFileSystem {
+  /// An optional handle to hook into common file system operations.
+  void Function(String context, FileSystemOp operation) get opHandle;
+
+  /// The root node.
+  RootNode? get root;
+
+  /// The path of the current working directory.
+  String get cwd;
+
+  /// The clock to use when finding the current time (e.g. to set the creation
+  /// time of a new node).
+  Clock get clock;
+
+  /// Gets the backing node of the entity at the specified path. If the tail
+  /// element of the path does not exist, this will return null. If the tail
+  /// element cannot be reached because its directory does not exist, a
+  /// [io.FileSystemException] will be thrown.
+  ///
+  /// If [path] is a relative path, it will be resolved relative to
+  /// [reference], or the current working directory ([cwd]) if [reference] is
+  /// null. If [path] is an absolute path, [reference] will be ignored.
+  ///
+  /// If the last element in [path] represents a symbolic link, this will
+  /// return the [LinkNode] node for the link (it will not return the
+  /// node to which the link points), unless [followTailLink] is true.
+  /// Directory links in the _middle_ of the path will be followed in order to
+  /// find the node regardless of the value of [followTailLink].
+  ///
+  /// If [segmentVisitor] is specified, it will be invoked for every path
+  /// segment visited along the way starting where the reference (root folder
+  /// if the path is absolute) is the parent. For each segment, the return value
+  /// of [segmentVisitor] will be used as the backing node of that path
+  /// segment, thus allowing callers to create nodes on demand in the
+  /// specified path. Note that `..` and `.` segments may cause the visitor to
+  /// get invoked with the same node multiple times. When [segmentVisitor] is
+  /// invoked, for each path segment that resolves to a link node, the visitor
+  /// will visit the actual link node if [visitLinks] is true; otherwise it
+  /// will visit the target of the link node.
+  ///
+  /// If [pathWithSymlinks] is specified, the path to the node with symbolic
+  /// links explicitly broken out will be appended to the buffer. `..` and `.`
+  /// path segments will *not* be resolved and are left to the caller.
+  Node? findNode(
+    String path, {
+    Node reference,
+    SegmentVisitor segmentVisitor,
+    bool visitLinks = false,
+    List<String> pathWithSymlinks,
+    bool followTailLink = false,
+  });
+}
+
+/// A class that represents the actual storage of an existent file system
+/// entity (whereas classes [File], [Directory], and [Link] represent less
+/// concrete entities that may or may not yet exist).
+///
+/// This data structure is loosely based on a Unix-style file system inode
+/// (hence the name).
+abstract class Node {
+  /// Constructs a new [Node] as a child of the specified parent.
+  Node(this._parent) {
+    if (_parent == null && !isRoot) {
+      throw const io.FileSystemException('All nodes must have a parent.');
+    }
+  }
+
+  DirectoryNode? _parent;
+
+  /// Gets the directory that holds this node.
+  DirectoryNode get parent => _parent!;
+
+  /// Reparents this node to live in the specified directory.
+  set parent(DirectoryNode parent) {
+    DirectoryNode ancestor = parent;
+    while (!ancestor.isRoot) {
+      if (ancestor == this) {
+        throw const io.FileSystemException(
+            'A directory cannot be its own ancestor.');
+      }
+      ancestor = ancestor.parent;
+    }
+    _parent = parent;
+  }
+
+  /// Returns the type of the file system entity that this node represents.
+  io.FileSystemEntityType get type;
+
+  /// Returns the POSIX stat information for this file system object.
+  io.FileStat get stat;
+
+  /// Returns the closest directory in the ancestry hierarchy starting with
+  /// this node. For directory nodes, it returns the node itself; for other
+  /// nodes, it returns the parent node.
+  DirectoryNode get directory => _parent!;
+
+  /// Tells if this node is a root node.
+  bool get isRoot => false;
+
+  /// Returns the file system responsible for this node.
+  NodeBasedFileSystem get fs => _parent!.fs;
+}
+
+/// Base class that represents the backing for those nodes that have
+/// substance (namely, node types that will not redirect to other types when
+/// you call [stat] on them).
+abstract class RealNode extends Node {
+  /// Constructs a new [RealNode] as a child of the specified [parent].
+  RealNode(DirectoryNode? parent) : super(parent) {
+    int now = clock.now.millisecondsSinceEpoch;
+    changed = now;
+    modified = now;
+    accessed = now;
+  }
+
+  /// See [NodeBasedFileSystem.clock].
+  Clock get clock => parent.clock;
+
+  /// Last changed time in milliseconds since the Epoch.
+  late int changed;
+
+  /// Last modified time in milliseconds since the Epoch.
+  late int modified;
+
+  /// Last accessed time in milliseconds since the Epoch.
+  late int accessed;
+
+  /// Bitmask representing the file read/write/execute mode.
+  int mode = 0x777;
+
+  @override
+  io.FileStat get stat {
+    return MemoryFileStat(
+      DateTime.fromMillisecondsSinceEpoch(changed),
+      DateTime.fromMillisecondsSinceEpoch(modified),
+      DateTime.fromMillisecondsSinceEpoch(accessed),
+      type,
+      mode,
+      size,
+    );
+  }
+
+  /// The size of the file system entity in bytes.
+  int get size;
+
+  /// Updates the last modified time of the node.
+  void touch() {
+    modified = clock.now.millisecondsSinceEpoch;
+  }
+}
+
+/// Class that represents the backing for an in-memory directory.
+class DirectoryNode extends RealNode {
+  /// Constructs a new [DirectoryNode] as a child of the specified [parent].
+  DirectoryNode(DirectoryNode? parent) : super(parent);
+
+  /// Child nodes, indexed by their basename.
+  final Map<String, Node> children = <String, Node>{};
+
+  @override
+  io.FileSystemEntityType get type => io.FileSystemEntityType.directory;
+
+  @override
+  DirectoryNode get directory => this;
+
+  @override
+  int get size => 0;
+}
+
+/// Class that represents the backing for the root of the in-memory file system.
+class RootNode extends DirectoryNode {
+  /// Constructs a new [RootNode] tied to the specified file system.
+  RootNode(this.fs)
+      : assert(fs.root == null),
+        super(null);
+
+  @override
+  final NodeBasedFileSystem fs;
+
+  @override
+  Clock get clock => fs.clock;
+
+  @override
+  DirectoryNode get parent => this;
+
+  @override
+  bool get isRoot => true;
+
+  @override
+  set parent(DirectoryNode parent) =>
+      throw UnsupportedError('Cannot set the parent of the root directory.');
+}
+
+/// Class that represents the backing for an in-memory regular file.
+class FileNode extends RealNode {
+  /// Constructs a new [FileNode] as a child of the specified [parent].
+  FileNode(DirectoryNode parent) : super(parent);
+
+  /// File contents in bytes.
+  Uint8List get content => _content;
+  Uint8List _content = Uint8List(0);
+
+  @override
+  io.FileSystemEntityType get type => io.FileSystemEntityType.file;
+
+  @override
+  int get size => _content.length;
+
+  /// Appends the specified bytes to the end of this node's [content].
+  void write(List<int> bytes) {
+    Uint8List existing = _content;
+    _content = Uint8List(existing.length + bytes.length);
+    _content.setRange(0, existing.length, existing);
+    _content.setRange(existing.length, _content.length, bytes);
+  }
+
+  /// Truncates this node's [content] to the specified length.
+  ///
+  /// [length] must be in the range \[0, [size]\].
+  void truncate(int length) {
+    assert(length >= 0);
+    assert(length <= _content.length);
+    _content = _content.sublist(0, length);
+  }
+
+  /// Clears the [content] of the node.
+  void clear() {
+    _content = Uint8List(0);
+  }
+
+  /// Copies data from [source] into this node. The [modified] and [changed]
+  /// fields will be reset as opposed to copied to indicate that this file
+  /// has been modified and changed.
+  void copyFrom(FileNode source) {
+    modified = changed = clock.now.millisecondsSinceEpoch;
+    accessed = source.accessed;
+    mode = source.mode;
+    _content = Uint8List.fromList(source.content);
+  }
+}
+
+/// Class that represents the backing for an in-memory symbolic link.
+class LinkNode extends Node {
+  /// Constructs a new [LinkNode] as a child of the specified [parent] and
+  /// linking to the specified [target] path.
+  LinkNode(DirectoryNode parent, this.target)
+      : assert(target.isNotEmpty),
+        super(parent);
+
+  /// The path to which this link points.
+  String target;
+
+  /// A marker used to detect circular link references.
+  bool _reentrant = false;
+
+  /// Gets the node backing for this link's target. Throws a
+  /// [FileSystemException] if this link references a non-existent file
+  /// system entity.
+  ///
+  /// If [tailVisitor] is specified, it will be invoked for the tail path
+  /// segment of this link's target, and its return value will be used as the
+  /// return value of this method. If the tail path segment of this link's
+  /// target cannot be traversed into, a [FileSystemException] will be thrown,
+  /// and [tailVisitor] will not be invoked.
+  Node getReferent({
+    Node? Function(DirectoryNode parent, String childName, Node? child)?
+        tailVisitor,
+  }) {
+    Node? referent = fs.findNode(
+      target,
+      reference: this,
+      segmentVisitor: (
+        DirectoryNode parent,
+        String childName,
+        Node? child,
+        int currentSegment,
+        int finalSegment,
+      ) {
+        if (tailVisitor != null && currentSegment == finalSegment) {
+          child = tailVisitor(parent, childName, child);
+        }
+        return child;
+      },
+    );
+    checkExists(referent, () => target);
+    return referent!;
+  }
+
+  /// Gets the node backing for this link's target, or null if this link
+  /// references a non-existent file system entity.
+  Node? get referentOrNull {
+    try {
+      return getReferent();
+    } on io.FileSystemException {
+      return null;
+    }
+  }
+
+  @override
+  io.FileSystemEntityType get type => io.FileSystemEntityType.link;
+
+  @override
+  io.FileStat get stat {
+    if (_reentrant) {
+      return MemoryFileStat.notFound;
+    }
+    _reentrant = true;
+    try {
+      Node? node = referentOrNull;
+      return node == null ? MemoryFileStat.notFound : node.stat;
+    } finally {
+      _reentrant = false;
+    }
+  }
+}
diff --git a/pkgs/file/lib/src/backends/memory/operations.dart b/pkgs/file/lib/src/backends/memory/operations.dart
new file mode 100644
index 0000000..9fc7462
--- /dev/null
+++ b/pkgs/file/lib/src/backends/memory/operations.dart
@@ -0,0 +1,86 @@
+// Copyright (c) 2017, 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.
+
+/// A file system operation used by the [MemoryFileSytem] to allow
+/// tests to insert errors for certain operations.
+///
+/// This is not implemented as an enum to allow new values to be added in a
+/// backwards compatible manner.
+class FileSystemOp {
+  const FileSystemOp._(this._value);
+
+  // This field added to ensure const values can be different.
+  // ignore: unused_field
+  final int _value;
+
+  /// A file system operation used for all read methods.
+  ///
+  /// * [FileSystemEntity.readAsString]
+  /// * [FileSystemEntity.readAsStringSync]
+  /// * [FileSystemEntity.readAsBytes]
+  /// * [FileSystemEntity.readAsBytesSync]
+  static const FileSystemOp read = FileSystemOp._(0);
+
+  /// A file system operation used for all write methods.
+  ///
+  /// * [FileSystemEntity.writeAsString]
+  /// * [FileSystemEntity.writeAsStringSync]
+  /// * [FileSystemEntity.writeAsBytes]
+  /// * [FileSystemEntity.writeAsBytesSync]
+  static const FileSystemOp write = FileSystemOp._(1);
+
+  /// A file system operation used for all delete methods.
+  ///
+  /// * [FileSystemEntity.delete]
+  /// * [FileSystemEntity.deleteSync]
+  static const FileSystemOp delete = FileSystemOp._(2);
+
+  /// A file system operation used for all create methods.
+  ///
+  /// * [FileSystemEntity.create]
+  /// * [FileSystemEntity.createSync]
+  static const FileSystemOp create = FileSystemOp._(3);
+
+  /// A file operation used for all open methods.
+  ///
+  /// * [File.open]
+  /// * [File.openSync]
+  /// * [File.openRead]
+  /// * [File.openWrite]
+  static const FileSystemOp open = FileSystemOp._(4);
+
+  /// A file operation used for all copy methods.
+  ///
+  /// * [File.copy]
+  /// * [File.copySync]
+  static const FileSystemOp copy = FileSystemOp._(5);
+
+  /// A file system operation used for all exists methods.
+  ///
+  /// * [FileSystemEntity.exists]
+  /// * [FileSystemEntity.existsSync]
+  static const FileSystemOp exists = FileSystemOp._(6);
+
+  @override
+  String toString() {
+    switch (_value) {
+      case 0:
+        return 'FileSystemOp.read';
+      case 1:
+        return 'FileSystemOp.write';
+      case 2:
+        return 'FileSystemOp.delete';
+      case 3:
+        return 'FileSystemOp.create';
+      case 4:
+        return 'FileSystemOp.open';
+      case 5:
+        return 'FileSystemOp.copy';
+      case 6:
+        return 'FileSystemOp.exists';
+      default:
+        throw StateError('Invalid FileSytemOp type: $this');
+    }
+  }
+}
diff --git a/pkgs/file/lib/src/backends/memory/style.dart b/pkgs/file/lib/src/backends/memory/style.dart
new file mode 100644
index 0000000..701c9d0
--- /dev/null
+++ b/pkgs/file/lib/src/backends/memory/style.dart
@@ -0,0 +1,98 @@
+// Copyright (c) 2018, 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.
+
+import 'package:file/file.dart';
+import 'package:path/path.dart' as p;
+
+/// Class that represents the path style that a memory file system should
+/// adopt.
+///
+/// This is primarily useful if you want to test how your code will behave
+/// when faced with particular paths or particular path separator characters.
+/// For instance, you may want to test that your code will work on Windows,
+/// while still using a memory file system in order to gain hermeticity in your
+/// tests.
+abstract class FileSystemStyle {
+  const FileSystemStyle._();
+
+  /// Mimics the Unix file system style.
+  ///
+  /// * This style does not have the notion of drives
+  /// * All file system paths are rooted at `/`
+  /// * The path separator is `/`
+  ///
+  /// An example path in this style is `/path/to/file`.
+  static const FileSystemStyle posix = _Posix();
+
+  /// Mimics the Windows file system style.
+  ///
+  /// * This style mounts its root folder on a single root drive (`C:`)
+  /// * All file system paths are rooted at `C:\`
+  /// * The path separator is `\`
+  ///
+  /// An example path in this style is `C:\path\to\file`.
+  static const FileSystemStyle windows = _Windows();
+
+  /// The drive upon which the root directory is mounted.
+  ///
+  /// While real-world file systems that have the notion of drives will support
+  /// multiple drives per system, memory file system will only support one
+  /// root drive.
+  ///
+  /// This will be the empty string for styles that don't have the notion of
+  /// drives (e.g. [posix]).
+  String get drive;
+
+  /// The String that represents the delineation between a directory and its
+  /// children.
+  String get separator;
+
+  /// The string that represents the root of the file system.
+  ///
+  /// Memory file system is always single-rooted.
+  String get root => '$drive$separator';
+
+  /// Gets an object useful for manipulating paths in this style.
+  ///
+  /// Relative path manipulations will be relative to the specified [path].
+  p.Context contextFor(String path);
+}
+
+class _Posix extends FileSystemStyle {
+  const _Posix() : super._();
+
+  @override
+  String get drive => '';
+
+  @override
+  String get separator {
+    return p.Style.posix.separator; // ignore: deprecated_member_use
+  }
+
+  @override
+  p.Context contextFor(String path) =>
+      p.Context(style: p.Style.posix, current: path);
+}
+
+class _Windows extends FileSystemStyle {
+  const _Windows() : super._();
+
+  @override
+  String get drive => 'C:';
+
+  @override
+  String get separator {
+    return p.Style.windows.separator; // ignore: deprecated_member_use
+  }
+
+  @override
+  p.Context contextFor(String path) =>
+      p.Context(style: p.Style.windows, current: path);
+}
+
+/// A file system that supports different styles.
+abstract class StyleableFileSystem implements FileSystem {
+  /// The style used by this file system.
+  FileSystemStyle get style;
+}
diff --git a/pkgs/file/lib/src/backends/memory/utils.dart b/pkgs/file/lib/src/backends/memory/utils.dart
new file mode 100644
index 0000000..eec9980
--- /dev/null
+++ b/pkgs/file/lib/src/backends/memory/utils.dart
@@ -0,0 +1,117 @@
+// Copyright (c) 2017, 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.
+
+import 'package:file/file.dart';
+import 'package:file/src/common.dart' as common;
+import 'package:file/src/io.dart' as io;
+
+import 'common.dart';
+import 'node.dart';
+
+/// Checks if `node.type` returns [io.FileSystemEntityType.FILE].
+bool isFile(Node? node) => node?.type == io.FileSystemEntityType.file;
+
+/// Checks if `node.type` returns [io.FileSystemEntityType.DIRECTORY].
+bool isDirectory(Node? node) => node?.type == io.FileSystemEntityType.directory;
+
+/// Checks if `node.type` returns [io.FileSystemEntityType.LINK].
+bool isLink(Node? node) => node?.type == io.FileSystemEntityType.link;
+
+/// Validator function that is expected to throw a [FileSystemException] if
+/// the node does not represent the type that is expected in any given context.
+typedef TypeChecker = void Function(Node node);
+
+/// Throws a [io.FileSystemException] if [node] is not a directory.
+void checkIsDir(Node node, PathGenerator path) {
+  if (!isDirectory(node)) {
+    throw common.notADirectory(path() as String);
+  }
+}
+
+/// Throws a [io.FileSystemException] if [expectedType] doesn't match
+/// [actualType].
+void checkType(
+  FileSystemEntityType expectedType,
+  FileSystemEntityType actualType,
+  PathGenerator path,
+) {
+  if (expectedType != actualType) {
+    switch (expectedType) {
+      case FileSystemEntityType.directory:
+        throw common.notADirectory(path() as String);
+      case FileSystemEntityType.file:
+        assert(actualType == FileSystemEntityType.directory);
+        throw common.isADirectory(path() as String);
+      case FileSystemEntityType.link:
+        throw common.invalidArgument(path() as String);
+      default:
+        // Should not happen
+        throw AssertionError();
+    }
+  }
+}
+
+/// Tells if the specified file mode represents a write mode.
+bool isWriteMode(io.FileMode mode) =>
+    mode == io.FileMode.write ||
+    mode == io.FileMode.append ||
+    mode == io.FileMode.writeOnly ||
+    mode == io.FileMode.writeOnlyAppend;
+
+/// Tells whether the given string is empty.
+bool isEmpty(String str) => str.isEmpty;
+
+/// Returns the node ultimately referred to by [link]. This will resolve
+/// the link references (following chains of links as necessary) and return
+/// the node at the end of the link chain.
+///
+/// If a loop in the link chain is found, this will throw a
+/// [FileSystemException], calling [path] to generate the path.
+///
+/// If [ledger] is specified, the resolved path to the terminal node will be
+/// appended to the ledger (or overwritten in the ledger if a link target
+/// specified an absolute path). The path will not be normalized, meaning
+/// `..` and `.` path segments may be present.
+///
+/// If [tailVisitor] is specified, it will be invoked for the tail element of
+/// the last link in the symbolic link chain, and its return value will be the
+/// return value of this method (thus allowing callers to create the entity
+/// at the end of the chain on demand).
+Node resolveLinks(
+  LinkNode link,
+  PathGenerator path, {
+  List<String>? ledger,
+  Node? Function(DirectoryNode parent, String childName, Node? child)?
+      tailVisitor,
+}) {
+  // Record a breadcrumb trail to guard against symlink loops.
+  Set<LinkNode> breadcrumbs = <LinkNode>{};
+
+  Node node = link;
+  while (isLink(node)) {
+    link = node as LinkNode;
+    if (!breadcrumbs.add(link)) {
+      throw common.tooManyLevelsOfSymbolicLinks(path() as String);
+    }
+    if (ledger != null) {
+      if (link.fs.path.isAbsolute(link.target)) {
+        ledger.clear();
+      } else if (ledger.isNotEmpty) {
+        ledger.removeLast();
+      }
+      ledger.addAll(link.target.split(link.fs.path.separator));
+    }
+    node = link.getReferent(
+      tailVisitor: (DirectoryNode parent, String childName, Node? child) {
+        if (tailVisitor != null && !isLink(child)) {
+          // Only invoke [tailListener] on the final resolution pass.
+          child = tailVisitor(parent, childName, child);
+        }
+        return child;
+      },
+    );
+  }
+
+  return node;
+}
diff --git a/pkgs/file/lib/src/common.dart b/pkgs/file/lib/src/common.dart
new file mode 100644
index 0000000..6706ec9
--- /dev/null
+++ b/pkgs/file/lib/src/common.dart
@@ -0,0 +1,70 @@
+// Copyright (c) 2017, 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.
+
+import 'interface.dart';
+
+/// Returns a 'No such file or directory' [FileSystemException].
+FileSystemException noSuchFileOrDirectory(String path) {
+  return _fsException(path, 'No such file or directory', ErrorCodes.ENOENT);
+}
+
+/// Returns a 'Not a directory' [FileSystemException].
+FileSystemException notADirectory(String path) {
+  return _fsException(path, 'Not a directory', ErrorCodes.ENOTDIR);
+}
+
+/// Returns a 'Is a directory' [FileSystemException].
+FileSystemException isADirectory(String path) {
+  return _fsException(path, 'Is a directory', ErrorCodes.EISDIR);
+}
+
+/// Returns a 'Directory not empty' [FileSystemException].
+FileSystemException directoryNotEmpty(String path) {
+  return _fsException(path, 'Directory not empty', ErrorCodes.ENOTEMPTY);
+}
+
+/// Returns a 'File exists' [FileSystemException].
+FileSystemException fileExists(String path) {
+  return _fsException(path, 'File exists', ErrorCodes.EEXIST);
+}
+
+/// Returns a 'Invalid argument' [FileSystemException].
+FileSystemException invalidArgument(String path) {
+  return _fsException(path, 'Invalid argument', ErrorCodes.EINVAL);
+}
+
+/// Returns a 'Too many levels of symbolic links' [FileSystemException].
+FileSystemException tooManyLevelsOfSymbolicLinks(String path) {
+  // TODO(tvolkert): Switch to ErrorCodes.EMLINK
+  return _fsException(
+      path, 'Too many levels of symbolic links', ErrorCodes.ELOOP);
+}
+
+/// Returns a 'Bad file descriptor' [FileSystemException].
+FileSystemException badFileDescriptor(String path) {
+  return _fsException(path, 'Bad file descriptor', ErrorCodes.EBADF);
+}
+
+FileSystemException _fsException(String path, String msg, int errorCode) {
+  return FileSystemException(msg, path, OSError(msg, errorCode));
+}
+
+/// Mixin containing implementations of [Directory] methods that are common
+/// to all implementations.
+mixin DirectoryAddOnsMixin implements Directory {
+  @override
+  Directory childDirectory(String basename) {
+    return fileSystem.directory(fileSystem.path.join(path, basename));
+  }
+
+  @override
+  File childFile(String basename) {
+    return fileSystem.file(fileSystem.path.join(path, basename));
+  }
+
+  @override
+  Link childLink(String basename) {
+    return fileSystem.link(fileSystem.path.join(path, basename));
+  }
+}
diff --git a/pkgs/file/lib/src/forwarding.dart b/pkgs/file/lib/src/forwarding.dart
new file mode 100644
index 0000000..9566a30
--- /dev/null
+++ b/pkgs/file/lib/src/forwarding.dart
@@ -0,0 +1,10 @@
+// Copyright (c) 2017, 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.
+
+export 'forwarding/forwarding_directory.dart';
+export 'forwarding/forwarding_file.dart';
+export 'forwarding/forwarding_file_system.dart';
+export 'forwarding/forwarding_file_system_entity.dart';
+export 'forwarding/forwarding_link.dart';
+export 'forwarding/forwarding_random_access_file.dart';
diff --git a/pkgs/file/lib/src/forwarding/forwarding_directory.dart b/pkgs/file/lib/src/forwarding/forwarding_directory.dart
new file mode 100644
index 0000000..dba0c8e
--- /dev/null
+++ b/pkgs/file/lib/src/forwarding/forwarding_directory.dart
@@ -0,0 +1,57 @@
+// Copyright (c) 2017, 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.
+
+import 'package:file/src/io.dart' as io;
+import 'package:file/file.dart';
+
+/// A directory that forwards all methods and properties to a delegate.
+mixin ForwardingDirectory<T extends Directory>
+    implements ForwardingFileSystemEntity<T, io.Directory>, Directory {
+  @override
+  T wrap(io.Directory delegate) => wrapDirectory(delegate) as T;
+
+  @override
+  Future<Directory> create({bool recursive = false}) async =>
+      wrap(await delegate.create(recursive: recursive));
+
+  @override
+  void createSync({bool recursive = false}) =>
+      delegate.createSync(recursive: recursive);
+
+  @override
+  Future<Directory> createTemp([String? prefix]) async =>
+      wrap(await delegate.createTemp(prefix));
+
+  @override
+  Directory createTempSync([String? prefix]) =>
+      wrap(delegate.createTempSync(prefix));
+
+  @override
+  Stream<FileSystemEntity> list({
+    bool recursive = false,
+    bool followLinks = true,
+  }) =>
+      delegate.list(recursive: recursive, followLinks: followLinks).map(_wrap);
+
+  @override
+  List<FileSystemEntity> listSync({
+    bool recursive = false,
+    bool followLinks = true,
+  }) =>
+      delegate
+          .listSync(recursive: recursive, followLinks: followLinks)
+          .map(_wrap)
+          .toList();
+
+  FileSystemEntity _wrap(io.FileSystemEntity entity) {
+    if (entity is io.File) {
+      return wrapFile(entity);
+    } else if (entity is io.Directory) {
+      return wrapDirectory(entity);
+    } else if (entity is io.Link) {
+      return wrapLink(entity);
+    }
+    throw FileSystemException('Unsupported type: $entity', entity.path);
+  }
+}
diff --git a/pkgs/file/lib/src/forwarding/forwarding_file.dart b/pkgs/file/lib/src/forwarding/forwarding_file.dart
new file mode 100644
index 0000000..49c211d
--- /dev/null
+++ b/pkgs/file/lib/src/forwarding/forwarding_file.dart
@@ -0,0 +1,156 @@
+// Copyright (c) 2017, 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.
+
+import 'dart:convert';
+import 'dart:typed_data';
+
+import 'package:file/src/io.dart' as io;
+import 'package:file/file.dart';
+
+/// A file that forwards all methods and properties to a delegate.
+mixin ForwardingFile
+    implements ForwardingFileSystemEntity<File, io.File>, File {
+  @override
+  ForwardingFile wrap(io.File delegate) => wrapFile(delegate) as ForwardingFile;
+
+  // TODO(dartbug.com/49647): Pass `exclusive` through after it lands.
+  @override
+  Future<File> create({bool recursive = false, bool exclusive = false}) async =>
+      wrap(await delegate.create(
+          recursive: recursive /*, exclusive: exclusive*/));
+
+  // TODO(dartbug.com/49647): Pass `exclusive` through after it lands.
+  @override
+  void createSync({bool recursive = false, bool exclusive = false}) =>
+      delegate.createSync(recursive: recursive /*, exclusive: exclusive*/);
+
+  @override
+  Future<File> copy(String newPath) async => wrap(await delegate.copy(newPath));
+
+  @override
+  File copySync(String newPath) => wrap(delegate.copySync(newPath));
+
+  @override
+  Future<int> length() => delegate.length();
+
+  @override
+  int lengthSync() => delegate.lengthSync();
+
+  @override
+  Future<DateTime> lastAccessed() => delegate.lastAccessed();
+
+  @override
+  DateTime lastAccessedSync() => delegate.lastAccessedSync();
+
+  @override
+  Future<dynamic> setLastAccessed(DateTime time) =>
+      delegate.setLastAccessed(time);
+
+  @override
+  void setLastAccessedSync(DateTime time) => delegate.setLastAccessedSync(time);
+
+  @override
+  Future<DateTime> lastModified() => delegate.lastModified();
+
+  @override
+  DateTime lastModifiedSync() => delegate.lastModifiedSync();
+
+  @override
+  Future<dynamic> setLastModified(DateTime time) =>
+      delegate.setLastModified(time);
+
+  @override
+  void setLastModifiedSync(DateTime time) => delegate.setLastModifiedSync(time);
+
+  @override
+  Future<RandomAccessFile> open({
+    FileMode mode = FileMode.read,
+  }) =>
+      delegate.open(mode: mode);
+
+  @override
+  RandomAccessFile openSync({FileMode mode = FileMode.read}) =>
+      delegate.openSync(mode: mode);
+
+  @override
+  Stream<List<int>> openRead([int? start, int? end]) =>
+      delegate.openRead(start, end);
+
+  @override
+  IOSink openWrite({
+    FileMode mode = FileMode.write,
+    Encoding encoding = utf8,
+  }) =>
+      delegate.openWrite(mode: mode, encoding: encoding);
+
+  @override
+  Future<Uint8List> readAsBytes() => delegate.readAsBytes();
+
+  @override
+  Uint8List readAsBytesSync() => delegate.readAsBytesSync();
+
+  @override
+  Future<String> readAsString({Encoding encoding = utf8}) =>
+      delegate.readAsString(encoding: encoding);
+
+  @override
+  String readAsStringSync({Encoding encoding = utf8}) =>
+      delegate.readAsStringSync(encoding: encoding);
+
+  @override
+  Future<List<String>> readAsLines({Encoding encoding = utf8}) =>
+      delegate.readAsLines(encoding: encoding);
+
+  @override
+  List<String> readAsLinesSync({Encoding encoding = utf8}) =>
+      delegate.readAsLinesSync(encoding: encoding);
+
+  @override
+  Future<File> writeAsBytes(
+    List<int> bytes, {
+    FileMode mode = FileMode.write,
+    bool flush = false,
+  }) async =>
+      wrap(await delegate.writeAsBytes(
+        bytes,
+        mode: mode,
+        flush: flush,
+      ));
+
+  @override
+  void writeAsBytesSync(
+    List<int> bytes, {
+    FileMode mode = FileMode.write,
+    bool flush = false,
+  }) =>
+      delegate.writeAsBytesSync(bytes, mode: mode, flush: flush);
+
+  @override
+  Future<File> writeAsString(
+    String contents, {
+    FileMode mode = FileMode.write,
+    Encoding encoding = utf8,
+    bool flush = false,
+  }) async =>
+      wrap(await delegate.writeAsString(
+        contents,
+        mode: mode,
+        encoding: encoding,
+        flush: flush,
+      ));
+
+  @override
+  void writeAsStringSync(
+    String contents, {
+    FileMode mode = FileMode.write,
+    Encoding encoding = utf8,
+    bool flush = false,
+  }) =>
+      delegate.writeAsStringSync(
+        contents,
+        mode: mode,
+        encoding: encoding,
+        flush: flush,
+      );
+}
diff --git a/pkgs/file/lib/src/forwarding/forwarding_file_system.dart b/pkgs/file/lib/src/forwarding/forwarding_file_system.dart
new file mode 100644
index 0000000..d864db9
--- /dev/null
+++ b/pkgs/file/lib/src/forwarding/forwarding_file_system.dart
@@ -0,0 +1,66 @@
+// Copyright (c) 2017, 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.
+
+import 'package:file/src/io.dart' as io;
+import 'package:file/file.dart';
+import 'package:meta/meta.dart';
+import 'package:path/path.dart' as p;
+
+/// A file system that forwards all methods and properties to a delegate.
+abstract class ForwardingFileSystem extends FileSystem {
+  /// Creates a new [ForwardingFileSystem] that forwards all methods and
+  /// properties to the specified [delegate].
+  ForwardingFileSystem(this.delegate);
+
+  /// The file system to which this file system will forward all activity.
+  @protected
+  final FileSystem delegate;
+
+  @override
+  Directory directory(dynamic path) => delegate.directory(path);
+
+  @override
+  File file(dynamic path) => delegate.file(path);
+
+  @override
+  Link link(dynamic path) => delegate.link(path);
+
+  @override
+  p.Context get path => delegate.path;
+
+  @override
+  Directory get systemTempDirectory => delegate.systemTempDirectory;
+
+  @override
+  Directory get currentDirectory => delegate.currentDirectory;
+
+  @override
+  set currentDirectory(dynamic path) => delegate.currentDirectory = path;
+
+  @override
+  Future<io.FileStat> stat(String path) => delegate.stat(path);
+
+  @override
+  io.FileStat statSync(String path) => delegate.statSync(path);
+
+  @override
+  Future<bool> identical(String path1, String path2) =>
+      delegate.identical(path1, path2);
+
+  @override
+  bool identicalSync(String path1, String path2) =>
+      delegate.identicalSync(path1, path2);
+
+  @override
+  bool get isWatchSupported => delegate.isWatchSupported;
+
+  @override
+  Future<io.FileSystemEntityType> type(String path,
+          {bool followLinks = true}) =>
+      delegate.type(path, followLinks: followLinks);
+
+  @override
+  io.FileSystemEntityType typeSync(String path, {bool followLinks = true}) =>
+      delegate.typeSync(path, followLinks: followLinks);
+}
diff --git a/pkgs/file/lib/src/forwarding/forwarding_file_system_entity.dart b/pkgs/file/lib/src/forwarding/forwarding_file_system_entity.dart
new file mode 100644
index 0000000..3c41b39
--- /dev/null
+++ b/pkgs/file/lib/src/forwarding/forwarding_file_system_entity.dart
@@ -0,0 +1,96 @@
+// Copyright (c) 2017, 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.
+
+import 'package:file/src/io.dart' as io;
+import 'package:file/file.dart';
+import 'package:meta/meta.dart';
+
+/// A file system entity that forwards all methods and properties to a delegate.
+abstract class ForwardingFileSystemEntity<T extends FileSystemEntity,
+    D extends io.FileSystemEntity> implements FileSystemEntity {
+  /// The entity to which this entity will forward all methods and properties.
+  @protected
+  D get delegate;
+
+  /// Creates a new entity with the same file system and same type as this
+  /// entity but backed by the specified delegate.
+  @protected
+  T wrap(D delegate);
+
+  /// Creates a new directory with the same file system as this entity and
+  /// backed by the specified delegate.
+  @protected
+  Directory wrapDirectory(io.Directory delegate);
+
+  /// Creates a new file with the same file system as this entity and
+  /// backed by the specified delegate.
+  @protected
+  File wrapFile(io.File delegate);
+
+  /// Creates a new link with the same file system as this entity and
+  /// backed by the specified delegate.
+  @protected
+  Link wrapLink(io.Link delegate);
+
+  @override
+  Uri get uri => delegate.uri;
+
+  @override
+  Future<bool> exists() => delegate.exists();
+
+  @override
+  bool existsSync() => delegate.existsSync();
+
+  @override
+  Future<T> rename(String newPath) async =>
+      wrap(await delegate.rename(newPath) as D);
+
+  @override
+  T renameSync(String newPath) => wrap(delegate.renameSync(newPath) as D);
+
+  @override
+  Future<String> resolveSymbolicLinks() => delegate.resolveSymbolicLinks();
+
+  @override
+  String resolveSymbolicLinksSync() => delegate.resolveSymbolicLinksSync();
+
+  @override
+  Future<io.FileStat> stat() => delegate.stat();
+
+  @override
+  io.FileStat statSync() => delegate.statSync();
+
+  @override
+  Future<T> delete({bool recursive = false}) async =>
+      wrap(await delegate.delete(recursive: recursive) as D);
+
+  @override
+  void deleteSync({bool recursive = false}) =>
+      delegate.deleteSync(recursive: recursive);
+
+  @override
+  Stream<FileSystemEvent> watch({
+    int events = FileSystemEvent.all,
+    bool recursive = false,
+  }) =>
+      delegate.watch(events: events, recursive: recursive);
+
+  @override
+  bool get isAbsolute => delegate.isAbsolute;
+
+  @override
+  T get absolute => wrap(delegate.absolute as D);
+
+  @override
+  Directory get parent => wrapDirectory(delegate.parent);
+
+  @override
+  String get path => delegate.path;
+
+  @override
+  String get basename => fileSystem.path.basename(path);
+
+  @override
+  String get dirname => fileSystem.path.dirname(path);
+}
diff --git a/pkgs/file/lib/src/forwarding/forwarding_link.dart b/pkgs/file/lib/src/forwarding/forwarding_link.dart
new file mode 100644
index 0000000..7a60ecb
--- /dev/null
+++ b/pkgs/file/lib/src/forwarding/forwarding_link.dart
@@ -0,0 +1,34 @@
+// Copyright (c) 2017, 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.
+
+import 'package:file/src/io.dart' as io;
+import 'package:file/file.dart';
+
+/// A link that forwards all methods and properties to a delegate.
+mixin ForwardingLink
+    implements ForwardingFileSystemEntity<Link, io.Link>, Link {
+  @override
+  ForwardingLink wrap(io.Link delegate) => wrapLink(delegate) as ForwardingLink;
+
+  @override
+  Future<Link> create(String target, {bool recursive = false}) async =>
+      wrap(await delegate.create(target, recursive: recursive));
+
+  @override
+  void createSync(String target, {bool recursive = false}) =>
+      delegate.createSync(target, recursive: recursive);
+
+  @override
+  Future<Link> update(String target) async =>
+      wrap(await delegate.update(target));
+
+  @override
+  void updateSync(String target) => delegate.updateSync(target);
+
+  @override
+  Future<String> target() => delegate.target();
+
+  @override
+  String targetSync() => delegate.targetSync();
+}
diff --git a/pkgs/file/lib/src/forwarding/forwarding_random_access_file.dart b/pkgs/file/lib/src/forwarding/forwarding_random_access_file.dart
new file mode 100644
index 0000000..9dd4079
--- /dev/null
+++ b/pkgs/file/lib/src/forwarding/forwarding_random_access_file.dart
@@ -0,0 +1,149 @@
+// Copyright (c) 2020, 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.
+
+import 'dart:convert';
+import 'dart:typed_data';
+
+import 'package:file/src/io.dart' as io;
+import 'package:meta/meta.dart';
+
+/// A [RandomAccessFile] implementation that forwards all methods and properties
+/// to a delegate.
+mixin ForwardingRandomAccessFile implements io.RandomAccessFile {
+  /// The entity to which this entity will forward all methods and properties.
+  @protected
+  io.RandomAccessFile get delegate;
+
+  @override
+  String get path => delegate.path;
+
+  @override
+  Future<void> close() => delegate.close();
+
+  @override
+  void closeSync() => delegate.closeSync();
+
+  @override
+  Future<io.RandomAccessFile> flush() async {
+    await delegate.flush();
+    return this;
+  }
+
+  @override
+  void flushSync() => delegate.flushSync();
+
+  @override
+  Future<int> length() => delegate.length();
+
+  @override
+  int lengthSync() => delegate.lengthSync();
+
+  @override
+  Future<io.RandomAccessFile> lock([
+    io.FileLock mode = io.FileLock.exclusive,
+    int start = 0,
+    int end = -1,
+  ]) async {
+    await delegate.lock(mode, start, end);
+    return this;
+  }
+
+  @override
+  void lockSync([
+    io.FileLock mode = io.FileLock.exclusive,
+    int start = 0,
+    int end = -1,
+  ]) =>
+      delegate.lockSync(mode, start, end);
+
+  @override
+  Future<int> position() => delegate.position();
+
+  @override
+  int positionSync() => delegate.positionSync();
+
+  @override
+  Future<Uint8List> read(int bytes) => delegate.read(bytes);
+
+  @override
+  Uint8List readSync(int bytes) => delegate.readSync(bytes);
+
+  @override
+  Future<int> readByte() => delegate.readByte();
+
+  @override
+  int readByteSync() => delegate.readByteSync();
+
+  @override
+  Future<int> readInto(List<int> buffer, [int start = 0, int? end]) =>
+      delegate.readInto(buffer, start, end);
+
+  @override
+  int readIntoSync(List<int> buffer, [int start = 0, int? end]) =>
+      delegate.readIntoSync(buffer, start, end);
+
+  @override
+  Future<io.RandomAccessFile> setPosition(int position) async {
+    await delegate.setPosition(position);
+    return this;
+  }
+
+  @override
+  void setPositionSync(int position) => delegate.setPositionSync(position);
+
+  @override
+  Future<io.RandomAccessFile> truncate(int length) async {
+    await delegate.truncate(length);
+    return this;
+  }
+
+  @override
+  void truncateSync(int length) => delegate.truncateSync(length);
+
+  @override
+  Future<io.RandomAccessFile> unlock([int start = 0, int end = -1]) async {
+    await delegate.unlock(start, end);
+    return this;
+  }
+
+  @override
+  void unlockSync([int start = 0, int end = -1]) =>
+      delegate.unlockSync(start, end);
+
+  @override
+  Future<io.RandomAccessFile> writeByte(int value) async {
+    await delegate.writeByte(value);
+    return this;
+  }
+
+  @override
+  int writeByteSync(int value) => delegate.writeByteSync(value);
+
+  @override
+  Future<io.RandomAccessFile> writeFrom(
+    List<int> buffer, [
+    int start = 0,
+    int? end,
+  ]) async {
+    await delegate.writeFrom(buffer, start, end);
+    return this;
+  }
+
+  @override
+  void writeFromSync(List<int> buffer, [int start = 0, int? end]) =>
+      delegate.writeFromSync(buffer, start, end);
+
+  @override
+  Future<io.RandomAccessFile> writeString(
+    String string, {
+    Encoding encoding = utf8,
+  }) async {
+    await delegate.writeString(string, encoding: encoding);
+    return this;
+  }
+
+  @override
+  void writeStringSync(String string, {Encoding encoding = utf8}) =>
+      delegate.writeStringSync(string, encoding: encoding);
+}
diff --git a/pkgs/file/lib/src/interface.dart b/pkgs/file/lib/src/interface.dart
new file mode 100644
index 0000000..4662e35
--- /dev/null
+++ b/pkgs/file/lib/src/interface.dart
@@ -0,0 +1,13 @@
+// Copyright (c) 2017, 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.
+
+library file.src.interface;
+
+export 'interface/directory.dart';
+export 'interface/error_codes.dart';
+export 'interface/file.dart';
+export 'interface/file_system.dart';
+export 'interface/file_system_entity.dart';
+export 'interface/link.dart';
+export 'io.dart' hide Directory, File, FileSystemEntity, Link;
diff --git a/pkgs/file/lib/src/interface/directory.dart b/pkgs/file/lib/src/interface/directory.dart
new file mode 100644
index 0000000..e62ad8c
--- /dev/null
+++ b/pkgs/file/lib/src/interface/directory.dart
@@ -0,0 +1,51 @@
+// Copyright (c) 2017, 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.
+
+import '../io.dart' as io;
+
+import 'file.dart';
+import 'file_system_entity.dart';
+import 'link.dart';
+
+/// A reference to a directory on the file system.
+abstract class Directory implements FileSystemEntity, io.Directory {
+  // Override method definitions to codify the return type covariance.
+  @override
+  Future<Directory> create({bool recursive = false});
+
+  @override
+  Future<Directory> createTemp([String? prefix]);
+
+  @override
+  Directory createTempSync([String? prefix]);
+
+  @override
+  Future<Directory> rename(String newPath);
+
+  @override
+  Directory renameSync(String newPath);
+
+  @override
+  Directory get absolute;
+
+  @override
+  Stream<FileSystemEntity> list(
+      {bool recursive = false, bool followLinks = true});
+
+  @override
+  List<FileSystemEntity> listSync(
+      {bool recursive = false, bool followLinks = true});
+
+  /// Returns a reference to a [Directory] that exists as a child of this
+  /// directory and has the specified [basename].
+  Directory childDirectory(String basename);
+
+  /// Returns a reference to a [File] that exists as a child of this directory
+  /// and has the specified [basename].
+  File childFile(String basename);
+
+  /// Returns a reference to a [Link] that exists as a child of this directory
+  /// and has the specified [basename].
+  Link childLink(String basename);
+}
diff --git a/pkgs/file/lib/src/interface/error_codes.dart b/pkgs/file/lib/src/interface/error_codes.dart
new file mode 100644
index 0000000..8943538
--- /dev/null
+++ b/pkgs/file/lib/src/interface/error_codes.dart
@@ -0,0 +1,585 @@
+// Copyright (c) 2017, 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.
+
+import 'error_codes_internal.dart'
+    if (dart.library.io) 'error_codes_dart_io.dart';
+
+/// Operating system error codes.
+// TODO(tvolkert): Remove (https://github.com/dart-lang/sdk/issues/28860)
+class ErrorCodes {
+  ErrorCodes._();
+
+  /// Argument list too long
+  // ignore: non_constant_identifier_names
+  static int get E2BIG => _platform((_Codes codes) => codes.e2big);
+
+  /// Permission denied
+  // ignore: non_constant_identifier_names
+  static int get EACCES => _platform((_Codes codes) => codes.eacces);
+
+  /// Try again
+  // ignore: non_constant_identifier_names
+  static int get EAGAIN => _platform((_Codes codes) => codes.eagain);
+
+  /// Bad file number
+  // ignore: non_constant_identifier_names
+  static int get EBADF => _platform((_Codes codes) => codes.ebadf);
+
+  /// Device or resource busy
+  // ignore: non_constant_identifier_names
+  static int get EBUSY => _platform((_Codes codes) => codes.ebusy);
+
+  /// No child processes
+  // ignore: non_constant_identifier_names
+  static int get ECHILD => _platform((_Codes codes) => codes.echild);
+
+  /// Resource deadlock would occur
+  // ignore: non_constant_identifier_names
+  static int get EDEADLK => _platform((_Codes codes) => codes.edeadlk);
+
+  /// Math argument out of domain of func
+  // ignore: non_constant_identifier_names
+  static int get EDOM => _platform((_Codes codes) => codes.edom);
+
+  /// File exists
+  // ignore: non_constant_identifier_names
+  static int get EEXIST => _platform((_Codes codes) => codes.eexist);
+
+  /// Bad address
+  // ignore: non_constant_identifier_names
+  static int get EFAULT => _platform((_Codes codes) => codes.efault);
+
+  /// File too large
+  // ignore: non_constant_identifier_names
+  static int get EFBIG => _platform((_Codes codes) => codes.efbig);
+
+  /// Illegal byte sequence
+  // ignore: non_constant_identifier_names
+  static int get EILSEQ => _platform((_Codes codes) => codes.eilseq);
+
+  /// Interrupted system call
+  // ignore: non_constant_identifier_names
+  static int get EINTR => _platform((_Codes codes) => codes.eintr);
+
+  /// Invalid argument
+  // ignore: non_constant_identifier_names
+  static int get EINVAL => _platform((_Codes codes) => codes.einval);
+
+  /// I/O error
+  // ignore: non_constant_identifier_names
+  static int get EIO => _platform((_Codes codes) => codes.eio);
+
+  /// Is a directory
+  // ignore: non_constant_identifier_names
+  static int get EISDIR => _platform((_Codes codes) => codes.eisdir);
+
+  /// Too many levels of symbolic links
+  // ignore: non_constant_identifier_names
+  static int get ELOOP => _platform((_Codes codes) => codes.eloop);
+
+  /// Too many open files
+  // ignore: non_constant_identifier_names
+  static int get EMFILE => _platform((_Codes codes) => codes.emfile);
+
+  /// Too many links
+  // ignore: non_constant_identifier_names
+  static int get EMLINK => _platform((_Codes codes) => codes.emlink);
+
+  /// File name too long
+  // ignore: non_constant_identifier_names
+  static int get ENAMETOOLONG =>
+      _platform((_Codes codes) => codes.enametoolong);
+
+  /// File table overflow
+  // ignore: non_constant_identifier_names
+  static int get ENFILE => _platform((_Codes codes) => codes.enfile);
+
+  /// No such device
+  // ignore: non_constant_identifier_names
+  static int get ENODEV => _platform((_Codes codes) => codes.enodev);
+
+  /// No such file or directory
+  // ignore: non_constant_identifier_names
+  static int get ENOENT => _platform((_Codes codes) => codes.enoent);
+
+  /// Exec format error
+  // ignore: non_constant_identifier_names
+  static int get ENOEXEC => _platform((_Codes codes) => codes.enoexec);
+
+  /// No record locks available
+  // ignore: non_constant_identifier_names
+  static int get ENOLCK => _platform((_Codes codes) => codes.enolck);
+
+  /// Out of memory
+  // ignore: non_constant_identifier_names
+  static int get ENOMEM => _platform((_Codes codes) => codes.enomem);
+
+  /// No space left on device
+  // ignore: non_constant_identifier_names
+  static int get ENOSPC => _platform((_Codes codes) => codes.enospc);
+
+  /// Function not implemented
+  // ignore: non_constant_identifier_names
+  static int get ENOSYS => _platform((_Codes codes) => codes.enosys);
+
+  /// Not a directory
+  // ignore: non_constant_identifier_names
+  static int get ENOTDIR => _platform((_Codes codes) => codes.enotdir);
+
+  /// Directory not empty
+  // ignore: non_constant_identifier_names
+  static int get ENOTEMPTY => _platform((_Codes codes) => codes.enotempty);
+
+  /// Not a typewriter
+  // ignore: non_constant_identifier_names
+  static int get ENOTTY => _platform((_Codes codes) => codes.enotty);
+
+  /// No such device or address
+  // ignore: non_constant_identifier_names
+  static int get ENXIO => _platform((_Codes codes) => codes.enxio);
+
+  /// Operation not permitted
+  // ignore: non_constant_identifier_names
+  static int get EPERM => _platform((_Codes codes) => codes.eperm);
+
+  /// Broken pipe
+  // ignore: non_constant_identifier_names
+  static int get EPIPE => _platform((_Codes codes) => codes.epipe);
+
+  /// Math result not representable
+  // ignore: non_constant_identifier_names
+  static int get ERANGE => _platform((_Codes codes) => codes.erange);
+
+  /// Read-only file system
+  // ignore: non_constant_identifier_names
+  static int get EROFS => _platform((_Codes codes) => codes.erofs);
+
+  /// Illegal seek
+  // ignore: non_constant_identifier_names
+  static int get ESPIPE => _platform((_Codes codes) => codes.espipe);
+
+  /// No such process
+  // ignore: non_constant_identifier_names
+  static int get ESRCH => _platform((_Codes codes) => codes.esrch);
+
+  /// Cross-device link
+  // ignore: non_constant_identifier_names
+  static int get EXDEV => _platform((_Codes codes) => codes.exdev);
+
+  static int _platform(int Function(_Codes codes) getCode) {
+    _Codes codes = (_platforms[operatingSystem] ?? _platforms['linux'])!;
+    return getCode(codes);
+  }
+}
+
+const Map<String, _Codes> _platforms = <String, _Codes>{
+  'linux': _LinuxCodes(),
+  'macos': _MacOSCodes(),
+  'windows': _WindowsCodes(),
+};
+
+abstract class _Codes {
+  int get e2big;
+  int get eacces;
+  int get eagain;
+  int get ebadf;
+  int get ebusy;
+  int get echild;
+  int get edeadlk;
+  int get edom;
+  int get eexist;
+  int get efault;
+  int get efbig;
+  int get eilseq;
+  int get eintr;
+  int get einval;
+  int get eio;
+  int get eisdir;
+  int get eloop;
+  int get emfile;
+  int get emlink;
+  int get enametoolong;
+  int get enfile;
+  int get enodev;
+  int get enoent;
+  int get enoexec;
+  int get enolck;
+  int get enomem;
+  int get enospc;
+  int get enosys;
+  int get enotdir;
+  int get enotempty;
+  int get enotty;
+  int get enxio;
+  int get eperm;
+  int get epipe;
+  int get erange;
+  int get erofs;
+  int get espipe;
+  int get esrch;
+  int get exdev;
+}
+
+class _LinuxCodes implements _Codes {
+  const _LinuxCodes();
+
+  @override
+  int get e2big => 7;
+
+  @override
+  int get eacces => 13;
+
+  @override
+  int get eagain => 11;
+
+  @override
+  int get ebadf => 9;
+
+  @override
+  int get ebusy => 16;
+
+  @override
+  int get echild => 10;
+
+  @override
+  int get edeadlk => 35;
+
+  @override
+  int get edom => 33;
+
+  @override
+  int get eexist => 17;
+
+  @override
+  int get efault => 14;
+
+  @override
+  int get efbig => 27;
+
+  @override
+  int get eilseq => 84;
+
+  @override
+  int get eintr => 4;
+
+  @override
+  int get einval => 22;
+
+  @override
+  int get eio => 5;
+
+  @override
+  int get eisdir => 21;
+
+  @override
+  int get eloop => 40;
+
+  @override
+  int get emfile => 24;
+
+  @override
+  int get emlink => 31;
+
+  @override
+  int get enametoolong => 36;
+
+  @override
+  int get enfile => 23;
+
+  @override
+  int get enodev => 19;
+
+  @override
+  int get enoent => 2;
+
+  @override
+  int get enoexec => 8;
+
+  @override
+  int get enolck => 37;
+
+  @override
+  int get enomem => 12;
+
+  @override
+  int get enospc => 28;
+
+  @override
+  int get enosys => 38;
+
+  @override
+  int get enotdir => 20;
+
+  @override
+  int get enotempty => 39;
+
+  @override
+  int get enotty => 25;
+
+  @override
+  int get enxio => 6;
+
+  @override
+  int get eperm => 1;
+
+  @override
+  int get epipe => 32;
+
+  @override
+  int get erange => 34;
+
+  @override
+  int get erofs => 30;
+
+  @override
+  int get espipe => 29;
+
+  @override
+  int get esrch => 3;
+
+  @override
+  int get exdev => 18;
+}
+
+class _MacOSCodes implements _Codes {
+  const _MacOSCodes();
+
+  @override
+  int get e2big => 7;
+
+  @override
+  int get eacces => 13;
+
+  @override
+  int get eagain => 35;
+
+  @override
+  int get ebadf => 9;
+
+  @override
+  int get ebusy => 16;
+
+  @override
+  int get echild => 10;
+
+  @override
+  int get edeadlk => 11;
+
+  @override
+  int get edom => 33;
+
+  @override
+  int get eexist => 17;
+
+  @override
+  int get efault => 14;
+
+  @override
+  int get efbig => 27;
+
+  @override
+  int get eilseq => 92;
+
+  @override
+  int get eintr => 4;
+
+  @override
+  int get einval => 22;
+
+  @override
+  int get eio => 5;
+
+  @override
+  int get eisdir => 21;
+
+  @override
+  int get eloop => 62;
+
+  @override
+  int get emfile => 24;
+
+  @override
+  int get emlink => 31;
+
+  @override
+  int get enametoolong => 63;
+
+  @override
+  int get enfile => 23;
+
+  @override
+  int get enodev => 19;
+
+  @override
+  int get enoent => 2;
+
+  @override
+  int get enoexec => 8;
+
+  @override
+  int get enolck => 77;
+
+  @override
+  int get enomem => 12;
+
+  @override
+  int get enospc => 28;
+
+  @override
+  int get enosys => 78;
+
+  @override
+  int get enotdir => 20;
+
+  @override
+  int get enotempty => 66;
+
+  @override
+  int get enotty => 25;
+
+  @override
+  int get enxio => 6;
+
+  @override
+  int get eperm => 1;
+
+  @override
+  int get epipe => 32;
+
+  @override
+  int get erange => 34;
+
+  @override
+  int get erofs => 30;
+
+  @override
+  int get espipe => 29;
+
+  @override
+  int get esrch => 3;
+
+  @override
+  int get exdev => 18;
+}
+
+class _WindowsCodes implements _Codes {
+  const _WindowsCodes();
+
+  @override
+  int get e2big => 7;
+
+  @override
+  int get eacces => 13;
+
+  @override
+  int get eagain => 11;
+
+  @override
+  int get ebadf => 9;
+
+  @override
+  int get ebusy => 16;
+
+  @override
+  int get echild => 10;
+
+  @override
+  int get edeadlk => 36;
+
+  @override
+  int get edom => 33;
+
+  @override
+  int get eexist => 17;
+
+  @override
+  int get efault => 14;
+
+  @override
+  int get efbig => 27;
+
+  @override
+  int get eilseq => 42;
+
+  @override
+  int get eintr => 4;
+
+  @override
+  int get einval => 22;
+
+  @override
+  int get eio => 5;
+
+  @override
+  int get eisdir => 21;
+
+  @override
+  int get eloop => -1;
+
+  @override
+  int get emfile => 24;
+
+  @override
+  int get emlink => 31;
+
+  @override
+  int get enametoolong => 38;
+
+  @override
+  int get enfile => 23;
+
+  @override
+  int get enodev => 19;
+
+  @override
+  int get enoent => 2;
+
+  @override
+  int get enoexec => 8;
+
+  @override
+  int get enolck => 39;
+
+  @override
+  int get enomem => 12;
+
+  @override
+  int get enospc => 28;
+
+  @override
+  int get enosys => 40;
+
+  @override
+  int get enotdir => 20;
+
+  @override
+  int get enotempty => 41;
+
+  @override
+  int get enotty => 25;
+
+  @override
+  int get enxio => 6;
+
+  @override
+  int get eperm => 1;
+
+  @override
+  int get epipe => 32;
+
+  @override
+  int get erange => 34;
+
+  @override
+  int get erofs => 30;
+
+  @override
+  int get espipe => 29;
+
+  @override
+  int get esrch => 3;
+
+  @override
+  int get exdev => 18;
+}
diff --git a/pkgs/file/lib/src/interface/error_codes_dart_io.dart b/pkgs/file/lib/src/interface/error_codes_dart_io.dart
new file mode 100644
index 0000000..3f0a97f
--- /dev/null
+++ b/pkgs/file/lib/src/interface/error_codes_dart_io.dart
@@ -0,0 +1,10 @@
+// Copyright (c) 2017, 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.
+
+import 'dart:io' show Platform;
+
+/// If we have `dart:io` available, we pull the current operating system from
+/// the [Platform] class, so we'll get errno values that match our current
+/// operating system.
+final String operatingSystem = Platform.operatingSystem;
diff --git a/pkgs/file/lib/src/interface/error_codes_internal.dart b/pkgs/file/lib/src/interface/error_codes_internal.dart
new file mode 100644
index 0000000..0a9d7dc
--- /dev/null
+++ b/pkgs/file/lib/src/interface/error_codes_internal.dart
@@ -0,0 +1,8 @@
+// Copyright (c) 2017, 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.
+
+/// In environments that don't have `dart:io`, we can't access the Platform
+/// class to determine what platform we're on, so we just pretend we're on
+/// Linux, meaning we'll get errno values that match Linux's errno.h.
+const String operatingSystem = 'linux';
diff --git a/pkgs/file/lib/src/interface/file.dart b/pkgs/file/lib/src/interface/file.dart
new file mode 100644
index 0000000..87417c6
--- /dev/null
+++ b/pkgs/file/lib/src/interface/file.dart
@@ -0,0 +1,41 @@
+// Copyright (c) 2017, 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.
+
+import 'dart:convert';
+
+import '../io.dart' as io;
+
+import 'file_system_entity.dart';
+
+/// A reference to a file on the file system.
+abstract class File implements FileSystemEntity, io.File {
+  // Override method definitions to codify the return type covariance.
+  @override
+  Future<File> create({bool recursive = false, bool exclusive = false});
+
+  @override
+  Future<File> rename(String newPath);
+
+  @override
+  File renameSync(String newPath);
+
+  @override
+  Future<File> copy(String newPath);
+
+  @override
+  File copySync(String newPath);
+
+  @override
+  File get absolute;
+
+  @override
+  Future<File> writeAsBytes(List<int> bytes,
+      {io.FileMode mode = io.FileMode.write, bool flush = false});
+
+  @override
+  Future<File> writeAsString(String contents,
+      {io.FileMode mode = io.FileMode.write,
+      Encoding encoding = utf8,
+      bool flush = false});
+}
diff --git a/pkgs/file/lib/src/interface/file_system.dart b/pkgs/file/lib/src/interface/file_system.dart
new file mode 100644
index 0000000..4fd528d
--- /dev/null
+++ b/pkgs/file/lib/src/interface/file_system.dart
@@ -0,0 +1,163 @@
+// Copyright (c) 2017, 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.
+
+import 'package:meta/meta.dart';
+import 'package:path/path.dart' as p;
+
+import '../io.dart' as io;
+
+import 'directory.dart';
+import 'file.dart';
+import 'file_system_entity.dart';
+import 'link.dart';
+
+/// A generic representation of a file system.
+///
+/// Note that this class uses `dart:io` only inasmuch as it deals in the types
+/// exposed by the `dart:io` library. Subclasses should document their level of
+/// dependence on the library (and the associated implications of using that
+/// implementation in the browser).
+abstract class FileSystem {
+  /// Creates a new `FileSystem`.
+  const FileSystem();
+
+  /// Returns a reference to a [Directory] at [path].
+  ///
+  /// [path] can be either a [`String`], a [`Uri`], or a [`FileSystemEntity`].
+  Directory directory(dynamic path);
+
+  /// Returns a reference to a [File] at [path].
+  ///
+  /// [path] can be either a [`String`], a [`Uri`], or a [`FileSystemEntity`].
+  File file(dynamic path);
+
+  /// Returns a reference to a [Link] at [path].
+  ///
+  /// [path] can be either a [`String`], a [`Uri`], or a [`FileSystemEntity`].
+  Link link(dynamic path);
+
+  /// An object for manipulating paths in this file system.
+  p.Context get path;
+
+  /// Gets the system temp directory.
+  ///
+  /// It is left to file system implementations to decide how to define the
+  /// "system temp directory".
+  Directory get systemTempDirectory;
+
+  /// Creates a directory object pointing to the current working directory.
+  Directory get currentDirectory;
+
+  /// Sets the current working directory to the specified [path].
+  ///
+  /// The new value set can be either a [Directory] or a [String].
+  ///
+  /// Relative paths will be resolved by the underlying file system
+  /// implementation (meaning it is up to the underlying implementation to
+  /// decide whether to support relative paths).
+  set currentDirectory(dynamic path);
+
+  /// Asynchronously calls the operating system's stat() function on [path].
+  /// Returns a Future which completes with a [io.FileStat] object containing
+  /// the data returned by stat().
+  /// If the call fails, completes the future with a [io.FileStat] object with
+  /// .type set to FileSystemEntityType.NOT_FOUND and the other fields invalid.
+  Future<io.FileStat> stat(String path);
+
+  /// Calls the operating system's stat() function on [path].
+  /// Returns a [io.FileStat] object containing the data returned by stat().
+  /// If the call fails, returns a [io.FileStat] object with .type set to
+  /// FileSystemEntityType.NOT_FOUND and the other fields invalid.
+  io.FileStat statSync(String path);
+
+  /// Checks whether two paths refer to the same object in the
+  /// file system. Returns a [Future<bool>] that completes with the result.
+  ///
+  /// Comparing a link to its target returns false, as does comparing two links
+  /// that point to the same target.  To check the target of a link, use
+  /// Link.target explicitly to fetch it.  Directory links appearing
+  /// inside a path are followed, though, to find the file system object.
+  ///
+  /// Completes the returned Future with an error if one of the paths points
+  /// to an object that does not exist.
+  Future<bool> identical(String path1, String path2);
+
+  /// Synchronously checks whether two paths refer to the same object in the
+  /// file system.
+  ///
+  /// Comparing a link to its target returns false, as does comparing two links
+  /// that point to the same target.  To check the target of a link, use
+  /// Link.target explicitly to fetch it.  Directory links appearing
+  /// inside a path are followed, though, to find the file system object.
+  ///
+  /// Throws an error if one of the paths points to an object that does not
+  /// exist.
+  bool identicalSync(String path1, String path2);
+
+  /// Tests if [FileSystemEntity.watch] is supported on the current system.
+  bool get isWatchSupported;
+
+  /// Finds the type of file system object that a [path] points to. Returns
+  /// a Future<FileSystemEntityType> that completes with the result.
+  ///
+  /// [io.FileSystemEntityType.LINK] will only be returned if [followLinks] is
+  /// `false`, and [path] points to a link
+  ///
+  /// If the [path] does not point to a file system object or an error occurs
+  /// then [io.FileSystemEntityType.notFound] is returned.
+  Future<io.FileSystemEntityType> type(String path, {bool followLinks = true});
+
+  /// Syncronously finds the type of file system object that a [path] points
+  /// to. Returns a [io.FileSystemEntityType].
+  ///
+  /// [io.FileSystemEntityType.LINK] will only be returned if [followLinks] is
+  /// `false`, and [path] points to a link
+  ///
+  /// If the [path] does not point to a file system object or an error occurs
+  /// then [io.FileSystemEntityType.notFound] is returned.
+  io.FileSystemEntityType typeSync(String path, {bool followLinks = true});
+
+  /// Checks if [`type(path)`](type) returns [io.FileSystemEntityType.FILE].
+  Future<bool> isFile(String path) async =>
+      await type(path) == io.FileSystemEntityType.file;
+
+  /// Synchronously checks if [`type(path)`](type) returns
+  /// [io.FileSystemEntityType.FILE].
+  bool isFileSync(String path) =>
+      typeSync(path) == io.FileSystemEntityType.file;
+
+  /// Checks if [`type(path)`](type) returns [io.FileSystemEntityType.DIRECTORY].
+  Future<bool> isDirectory(String path) async =>
+      await type(path) == io.FileSystemEntityType.directory;
+
+  /// Synchronously checks if [`type(path)`](type) returns
+  /// [io.FileSystemEntityType.DIRECTORY].
+  bool isDirectorySync(String path) =>
+      typeSync(path) == io.FileSystemEntityType.directory;
+
+  /// Checks if [`type(path)`](type) returns [io.FileSystemEntityType.LINK].
+  Future<bool> isLink(String path) async =>
+      await type(path, followLinks: false) == io.FileSystemEntityType.link;
+
+  /// Synchronously checks if [`type(path)`](type) returns
+  /// [io.FileSystemEntityType.LINK].
+  bool isLinkSync(String path) =>
+      typeSync(path, followLinks: false) == io.FileSystemEntityType.link;
+
+  /// Gets the string path represented by the specified generic [path].
+  ///
+  /// [path] may be a [io.FileSystemEntity], a [String], or a [Uri].
+  @protected
+  String getPath(dynamic path) {
+    if (path is io.FileSystemEntity) {
+      return path.path;
+    } else if (path is String) {
+      return path;
+    } else if (path is Uri) {
+      return this.path.fromUri(path);
+    } else {
+      throw ArgumentError('Invalid type for "path": ${path?.runtimeType}');
+    }
+  }
+}
diff --git a/pkgs/file/lib/src/interface/file_system_entity.dart b/pkgs/file/lib/src/interface/file_system_entity.dart
new file mode 100644
index 0000000..a377397
--- /dev/null
+++ b/pkgs/file/lib/src/interface/file_system_entity.dart
@@ -0,0 +1,42 @@
+// Copyright (c) 2017, 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.
+
+import '../io.dart' as io;
+
+import 'directory.dart';
+import 'file_system.dart';
+
+/// The common super class for [io.File], [io.Directory], and [io.Link] objects.
+abstract class FileSystemEntity implements io.FileSystemEntity {
+  /// Returns the file system responsible for this entity.
+  FileSystem get fileSystem;
+
+  /// Gets the part of this entity's path after the last separator.
+  ///
+  ///     context.basename('path/to/foo.dart'); // -> 'foo.dart'
+  ///     context.basename('path/to');          // -> 'to'
+  ///
+  /// Trailing separators are ignored.
+  ///
+  ///     context.basename('path/to/'); // -> 'to'
+  String get basename;
+
+  /// Gets the part of this entity's path before the last separator.
+  ///
+  ///     context.dirname('path/to/foo.dart'); // -> 'path/to'
+  ///     context.dirname('path/to');          // -> 'path'
+  ///     context.dirname('foo.dart');         // -> '.'
+  ///
+  /// Trailing separators are ignored.
+  ///
+  ///     context.dirname('path/to/'); // -> 'path'
+  String get dirname;
+
+  // Override method definitions to codify the return type covariance.
+  @override
+  Future<FileSystemEntity> delete({bool recursive = false});
+
+  @override
+  Directory get parent;
+}
diff --git a/pkgs/file/lib/src/interface/link.dart b/pkgs/file/lib/src/interface/link.dart
new file mode 100644
index 0000000..27874b3
--- /dev/null
+++ b/pkgs/file/lib/src/interface/link.dart
@@ -0,0 +1,26 @@
+// Copyright (c) 2017, 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.
+
+import '../io.dart' as io;
+
+import 'file_system_entity.dart';
+
+/// A reference to a symbolic link on the file system.
+abstract class Link implements FileSystemEntity, io.Link {
+  // Override method definitions to codify the return type covariance.
+  @override
+  Future<Link> create(String target, {bool recursive = false});
+
+  @override
+  Future<Link> update(String target);
+
+  @override
+  Future<Link> rename(String newPath);
+
+  @override
+  Link renameSync(String newPath);
+
+  @override
+  Link get absolute;
+}
diff --git a/pkgs/file/lib/src/io.dart b/pkgs/file/lib/src/io.dart
new file mode 100644
index 0000000..9d57e78
--- /dev/null
+++ b/pkgs/file/lib/src/io.dart
@@ -0,0 +1,26 @@
+// Copyright (c) 2017, 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.
+
+/// For internal use only!
+///
+/// This exposes the subset of the `dart:io` interfaces that are required by
+/// the `file` package. The `file` package re-exports these interfaces (or in
+/// some cases, implementations of these interfaces by the same name), so this
+/// file need not be exposes publicly and exists for internal use only.
+export 'dart:io'
+    show
+        Directory,
+        File,
+        FileLock,
+        FileMode,
+        FileStat,
+        FileSystemEntity,
+        FileSystemEntityType,
+        FileSystemEvent,
+        FileSystemException,
+        IOException,
+        IOSink,
+        Link,
+        OSError,
+        RandomAccessFile;
diff --git a/pkgs/file/pubspec.yaml b/pkgs/file/pubspec.yaml
new file mode 100644
index 0000000..b4195f7
--- /dev/null
+++ b/pkgs/file/pubspec.yaml
@@ -0,0 +1,19 @@
+name: file
+version: 7.0.1
+description:
+  A pluggable, mockable file system abstraction for Dart. Supports local file
+  system access, as well as in-memory file systems, record-replay file systems,
+  and chroot file systems.
+repository: https://github.com/dart-lang/tools/tree/main/pkgs/file
+
+environment:
+  sdk: ^3.0.0
+
+dependencies:
+  meta: ^1.9.1
+  path: ^1.8.3
+
+dev_dependencies:
+  file_testing: ^3.0.0
+  lints: ^2.0.1
+  test: ^1.23.1
diff --git a/pkgs/file/test/chroot_test.dart b/pkgs/file/test/chroot_test.dart
new file mode 100644
index 0000000..6c34ff2
--- /dev/null
+++ b/pkgs/file/test/chroot_test.dart
@@ -0,0 +1,177 @@
+// Copyright (c) 2017, 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.
+
+@TestOn('vm')
+import 'dart:io' as io;
+
+import 'package:file/chroot.dart';
+import 'package:file/file.dart';
+import 'package:file/local.dart';
+import 'package:file/memory.dart';
+import 'package:file_testing/file_testing.dart';
+import 'package:test/test.dart';
+
+import 'common_tests.dart';
+
+void main() {
+  group('ChrootFileSystem', () {
+    ChrootFileSystem createMemoryBackedChrootFileSystem() {
+      MemoryFileSystem fs = MemoryFileSystem();
+      fs.directory('/tmp').createSync();
+      return ChrootFileSystem(fs, '/tmp');
+    }
+
+    // TODO(jamesderlin): Make ChrootFile.openSync return a delegating
+    // RandomAccessFile that uses the chroot'd path.
+    List<String> skipCommon = <String>[
+      'File > open > .* > RandomAccessFile > read > openReadHandleDoesNotChange',
+      'File > open > .* > RandomAccessFile > openWriteHandleDoesNotChange',
+    ];
+
+    group('memoryBacked', () {
+      runCommonTests(createMemoryBackedChrootFileSystem, skip: skipCommon);
+    });
+
+    group('localBacked', () {
+      late ChrootFileSystem fs;
+      late io.Directory tmp;
+
+      setUp(() {
+        tmp = io.Directory.systemTemp.createTempSync('file_test_');
+        tmp = io.Directory(tmp.resolveSymbolicLinksSync());
+        fs = ChrootFileSystem(const LocalFileSystem(), tmp.path);
+      });
+
+      tearDown(() {
+        tmp.deleteSync(recursive: true);
+      });
+
+      runCommonTests(
+        () => fs,
+        skip: <String>[
+          // https://github.com/dart-lang/sdk/issues/28275
+          'Link > rename > throwsIfDestinationExistsAsDirectory',
+
+          // https://github.com/dart-lang/sdk/issues/28277
+          'Link > rename > throwsIfDestinationExistsAsFile',
+
+          ...skipCommon,
+        ],
+      );
+    }, skip: io.Platform.isWindows);
+
+    group('chrootSpecific', () {
+      late ChrootFileSystem fs;
+      late MemoryFileSystem mem;
+
+      setUp(() {
+        fs = createMemoryBackedChrootFileSystem();
+        mem = fs.delegate as MemoryFileSystem;
+      });
+
+      group('FileSystem', () {
+        group('currentDirectory', () {
+          test('staysInJailIfSetToParentOfRoot', () {
+            fs.currentDirectory = '../../../..';
+            fs.file('foo').createSync();
+            expect(mem.file('/tmp/foo'), exists);
+          });
+
+          test('throwsIfSetToSymlinkToDirectoryOutsideJail', () {
+            mem.directory('/bar').createSync();
+            mem.link('/tmp/foo').createSync('/bar');
+            expectFileSystemException(ErrorCodes.ENOENT, () {
+              fs.currentDirectory = '/foo';
+            });
+          });
+        });
+
+        group('stat', () {
+          test('isNotFoundForJailbreakPath', () {
+            mem.file('/foo').createSync();
+            expect(fs.statSync('../foo').type, FileSystemEntityType.notFound);
+          });
+
+          test('isNotFoundForSymlinkWithJailbreakTarget', () {
+            mem.file('/foo').createSync();
+            mem.link('/tmp/bar').createSync('/foo');
+            expect(mem.statSync('/tmp/bar').type, FileSystemEntityType.file);
+            expect(fs.statSync('/bar').type, FileSystemEntityType.notFound);
+          });
+
+          test('isNotFoundForSymlinkToOutsideAndBackInsideJail', () {
+            mem.file('/tmp/bar').createSync();
+            mem.link('/foo').createSync('/tmp/bar');
+            mem.link('/tmp/baz').createSync('/foo');
+            expect(mem.statSync('/tmp/baz').type, FileSystemEntityType.file);
+            expect(fs.statSync('/baz').type, FileSystemEntityType.notFound);
+          });
+        });
+
+        group('type', () {
+          test('isNotFoundForJailbreakPath', () {
+            mem.file('/foo').createSync();
+            expect(fs.typeSync('../foo'), FileSystemEntityType.notFound);
+          });
+
+          test('isNotFoundForSymlinkWithJailbreakTarget', () {
+            mem.file('/foo').createSync();
+            mem.link('/tmp/bar').createSync('/foo');
+            expect(mem.typeSync('/tmp/bar'), FileSystemEntityType.file);
+            expect(fs.typeSync('/bar'), FileSystemEntityType.notFound);
+          });
+
+          test('isNotFoundForSymlinkToOutsideAndBackInsideJail', () {
+            mem.file('/tmp/bar').createSync();
+            mem.link('/foo').createSync('/tmp/bar');
+            mem.link('/tmp/baz').createSync('/foo');
+            expect(mem.typeSync('/tmp/baz'), FileSystemEntityType.file);
+            expect(fs.typeSync('/baz'), FileSystemEntityType.notFound);
+          });
+        });
+      });
+
+      group('File', () {
+        group('delegate', () {
+          test('referencesRootEntityForJailbreakPath', () {
+            mem.file('/foo').createSync();
+            dynamic f = fs.file('../foo');
+            expect(f.delegate.path, '/tmp/foo');
+          });
+        });
+
+        group('create', () {
+          test('createsAtRootIfPathReferencesJailbreakFile', () {
+            fs.file('../foo').createSync();
+            expect(mem.file('/foo'), isNot(exists));
+            expect(mem.file('/tmp/foo'), exists);
+          });
+        });
+
+        group('copy', () {
+          test('copiesToRootDirectoryIfDestinationIsJailbreakPath', () {
+            File f = fs.file('/foo')..createSync();
+            f.copySync('../bar');
+            expect(mem.file('/bar'), isNot(exists));
+            expect(mem.file('/tmp/bar'), exists);
+          });
+        });
+      });
+
+      group('Link', () {
+        group('target', () {
+          test('chrootAndDelegateFileSystemsReturnSameValue', () {
+            mem.file('/foo').createSync();
+            mem.link('/tmp/bar').createSync('/foo');
+            mem.link('/tmp/baz').createSync('../foo');
+            expect(mem.link('/tmp/bar').targetSync(), '/foo');
+            expect(fs.link('/bar').targetSync(), '/foo');
+            expect(mem.link('/tmp/baz').targetSync(), '../foo');
+            expect(fs.link('/baz').targetSync(), '../foo');
+          });
+        });
+      });
+    });
+  });
+}
diff --git a/pkgs/file/test/common_tests.dart b/pkgs/file/test/common_tests.dart
new file mode 100644
index 0000000..6028c77
--- /dev/null
+++ b/pkgs/file/test/common_tests.dart
@@ -0,0 +1,3517 @@
+// Copyright (c) 2017, 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.
+
+@TestOn('vm')
+import 'dart:async';
+import 'dart:convert';
+import 'dart:io' as io;
+
+import 'package:file/file.dart';
+import 'package:file_testing/file_testing.dart';
+import 'package:path/path.dart' as p;
+import 'package:test/test.dart';
+import 'package:test/test.dart' as testpkg show group, setUp, tearDown, test;
+
+import 'utils.dart';
+
+/// Callback used in [runCommonTests] to produce the root folder in which all
+/// file system entities will be created.
+typedef RootPathGenerator = String Function();
+
+/// Callback used in [runCommonTests] to create the file system under test.
+/// It must return either a [FileSystem] or a [Future] that completes with a
+/// [FileSystem].
+typedef FileSystemGenerator = dynamic Function();
+
+/// A function to run before tests (passed to [setUp]) or after tests
+/// (passed to [tearDown]).
+typedef SetUpTearDown = dynamic Function();
+
+/// Runs a suite of tests common to all file system implementations. All file
+/// system implementations should run *at least* these tests to ensure
+/// compliance with file system API.
+///
+/// If [root] is specified, its return value will be used as the root folder
+/// in which all file system entities will be created. If not specified, the
+/// tests will attempt to create entities in the file system root.
+///
+/// [skip] may be used to skip certain tests (or entire groups of tests) in
+/// this suite (to be used, for instance, if a file system implementation is
+/// not yet fully complete). The format of each entry in the list is:
+/// `$group1Description > $group2Description > ... > $testDescription`.
+/// Entries may use regular expression syntax.
+///
+/// If [replay] is specified, each test (and its setup callbacks) will run
+/// twice - once as a "setup" pass with the file system returned by
+/// [createFileSystem], and again as the "test" pass with the file system
+/// returned by [replay]. This is intended for use with `ReplayFileSystem`,
+/// where in order for the file system to behave as expected, a recording of
+/// the invocation(s) must first be made.
+void runCommonTests(
+  FileSystemGenerator createFileSystem, {
+  RootPathGenerator? root,
+  List<String> skip = const <String>[],
+  FileSystemGenerator? replay,
+}) {
+  RootPathGenerator? rootfn = root;
+
+  group('common', () {
+    late FileSystemGenerator createFs;
+    late List<SetUpTearDown> setUps;
+    late List<SetUpTearDown> tearDowns;
+    late FileSystem fs;
+    late String root;
+    List<String> stack = <String>[];
+
+    void skipIfNecessary(String description, void Function() callback) {
+      stack.add(description);
+      bool matchesCurrentFrame(String input) =>
+          RegExp('^$input\$').hasMatch(stack.join(' > '));
+      if (skip.where(matchesCurrentFrame).isEmpty) {
+        callback();
+      }
+      stack.removeLast();
+    }
+
+    testpkg.setUp(() async {
+      createFs = createFileSystem;
+      setUps = <SetUpTearDown>[];
+      tearDowns = <SetUpTearDown>[];
+    });
+
+    void setUp(FutureOr<void> Function() callback) {
+      testpkg.setUp(replay == null ? callback : () => setUps.add(callback));
+    }
+
+    void tearDown(FutureOr<void> Function() callback) {
+      if (replay == null) {
+        testpkg.tearDown(callback);
+      } else {
+        testpkg.setUp(() => tearDowns.insert(0, callback));
+      }
+    }
+
+    void group(String description, void Function() body) =>
+        skipIfNecessary(description, () => testpkg.group(description, body));
+
+    void test(String description, FutureOr<void> Function() body,
+            {dynamic skip}) =>
+        skipIfNecessary(description, () {
+          if (replay == null) {
+            testpkg.test(description, body, skip: skip);
+          } else {
+            group('rerun', () {
+              testpkg.setUp(() async {
+                await Future.forEach(setUps, (SetUpTearDown setUp) => setUp());
+                await body();
+                for (SetUpTearDown tearDown in tearDowns) {
+                  await tearDown();
+                }
+                createFs = replay;
+                await Future.forEach(setUps, (SetUpTearDown setUp) => setUp());
+              });
+
+              testpkg.test(description, body, skip: skip);
+
+              testpkg.tearDown(() async {
+                for (SetUpTearDown tearDown in tearDowns) {
+                  await tearDown();
+                }
+              });
+            });
+          }
+        });
+
+    /// Returns [path] prefixed by the [root] namespace.
+    /// This is only intended for absolute paths.
+    String ns(String path) {
+      p.Context posix = p.Context(style: p.Style.posix);
+      List<String> parts = posix.split(path);
+      parts[0] = root;
+      path = fs.path.joinAll(parts);
+      String rootPrefix = fs.path.rootPrefix(path);
+      assert(rootPrefix.isNotEmpty);
+      String result = root == rootPrefix
+          ? path
+          : (path == rootPrefix
+              ? root
+              : fs.path.join(root, fs.path.joinAll(parts.sublist(1))));
+      return result;
+    }
+
+    setUp(() async {
+      root = rootfn != null ? rootfn() : '/';
+      fs = await createFs() as FileSystem;
+      assert(fs.path.isAbsolute(root));
+      assert(!root.endsWith(fs.path.separator) ||
+          fs.path.rootPrefix(root) == root);
+    });
+
+    group('FileSystem', () {
+      group('directory', () {
+        test('allowsStringArgument', () {
+          expect(fs.directory(ns('/foo')), isDirectory);
+        });
+
+        test('allowsUriArgument', () {
+          expect(fs.directory(Uri.parse('file:///')), isDirectory);
+        });
+
+        test('succeedsWithUriArgument', () {
+          fs.directory(ns('/foo')).createSync();
+          Uri uri = fs.path.toUri(ns('/foo'));
+          expect(fs.directory(uri), exists);
+        });
+
+        test('allowsDirectoryArgument', () {
+          expect(fs.directory(io.Directory(ns('/foo'))), isDirectory);
+        });
+
+        test('disallowsOtherArgumentType', () {
+          expect(() => fs.directory(123), throwsArgumentError);
+        });
+
+        // Fails due to
+        // https://github.com/google/file.dart/issues/112
+        test('considersBothSlashesEquivalent', () {
+          fs.directory(r'foo\bar_dir').createSync(recursive: true);
+          expect(fs.directory(r'foo/bar_dir'), exists);
+        }, skip: 'Fails due to https://github.com/google/file.dart/issues/112');
+      });
+
+      group('file', () {
+        test('allowsStringArgument', () {
+          expect(fs.file(ns('/foo')), isFile);
+        });
+
+        test('allowsUriArgument', () {
+          expect(fs.file(Uri.parse('file:///')), isFile);
+        });
+
+        test('succeedsWithUriArgument', () {
+          fs.file(ns('/foo')).createSync();
+          Uri uri = fs.path.toUri(ns('/foo'));
+          expect(fs.file(uri), exists);
+        });
+
+        test('allowsDirectoryArgument', () {
+          expect(fs.file(io.File(ns('/foo'))), isFile);
+        });
+
+        test('disallowsOtherArgumentType', () {
+          expect(() => fs.file(123), throwsArgumentError);
+        });
+
+        // Fails due to
+        // https://github.com/google/file.dart/issues/112
+        test('considersBothSlashesEquivalent', () {
+          fs.file(r'foo\bar_file').createSync(recursive: true);
+          expect(fs.file(r'foo/bar_file'), exists);
+        }, skip: 'Fails due to https://github.com/google/file.dart/issues/112');
+      });
+
+      group('link', () {
+        test('allowsStringArgument', () {
+          expect(fs.link(ns('/foo')), isLink);
+        });
+
+        test('allowsUriArgument', () {
+          expect(fs.link(Uri.parse('file:///')), isLink);
+        });
+
+        test('succeedsWithUriArgument', () {
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          Uri uri = fs.path.toUri(ns('/bar'));
+          expect(fs.link(uri), exists);
+        });
+
+        test('allowsDirectoryArgument', () {
+          expect(fs.link(io.File(ns('/foo'))), isLink);
+        });
+
+        test('disallowsOtherArgumentType', () {
+          expect(() => fs.link(123), throwsArgumentError);
+        });
+      });
+
+      group('path', () {
+        test('hasCorrectCurrentWorkingDirectory', () {
+          expect(fs.path.current, fs.currentDirectory.path);
+        });
+
+        test('separatorIsAmongExpectedValues', () {
+          expect(fs.path.separator, anyOf('/', r'\'));
+        });
+      });
+
+      group('systemTempDirectory', () {
+        test('existsAsDirectory', () {
+          Directory tmp = fs.systemTempDirectory;
+          expect(tmp, isDirectory);
+          expect(tmp, exists);
+        });
+      });
+
+      group('currentDirectory', () {
+        test('defaultsToRoot', () {
+          expect(fs.currentDirectory.path, root);
+        });
+
+        test('throwsIfSetToNonExistentPath', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.currentDirectory = ns('/foo');
+          });
+        });
+
+        test('throwsIfHasNonExistentPathInComplexChain', () {
+          fs.directory(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.currentDirectory = ns('/bar/../foo');
+          });
+        });
+
+        test('succeedsIfSetToValidStringPath', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.currentDirectory = ns('/foo');
+          expect(fs.currentDirectory.path, ns('/foo'));
+        });
+
+        test('succeedsIfSetToValidDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.currentDirectory = io.Directory(ns('/foo'));
+          expect(fs.currentDirectory.path, ns('/foo'));
+        });
+
+        test('throwsIfArgumentIsNotStringOrDirectory', () {
+          expect(() {
+            fs.currentDirectory = 123;
+          }, throwsArgumentError);
+        });
+
+        test('succeedsIfSetToRelativePath', () {
+          fs.directory(ns('/foo/bar')).createSync(recursive: true);
+          fs.currentDirectory = 'foo';
+          expect(fs.currentDirectory.path, ns('/foo'));
+          fs.currentDirectory = 'bar';
+          expect(fs.currentDirectory.path, ns('/foo/bar'));
+        });
+
+        test('succeedsIfSetToAbsolutePathWhenCwdIsNotRoot', () {
+          fs.directory(ns('/foo/bar')).createSync(recursive: true);
+          fs.directory(ns('/baz/qux')).createSync(recursive: true);
+          fs.currentDirectory = ns('/foo/bar');
+          expect(fs.currentDirectory.path, ns('/foo/bar'));
+          fs.currentDirectory = fs.directory(ns('/baz/qux'));
+          expect(fs.currentDirectory.path, ns('/baz/qux'));
+        });
+
+        test('succeedsIfSetToParentDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.currentDirectory = 'foo';
+          expect(fs.currentDirectory.path, ns('/foo'));
+          fs.currentDirectory = '..';
+          expect(fs.currentDirectory.path, ns('/'));
+        });
+
+        test('staysAtRootIfSetToParentOfRoot', () {
+          fs.currentDirectory =
+              List<String>.filled(20, '..').join(fs.path.separator);
+          String cwd = fs.currentDirectory.path;
+          expect(cwd, fs.path.rootPrefix(cwd));
+        });
+
+        test('removesTrailingSlashIfSet', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.currentDirectory = ns('/foo/');
+          expect(fs.currentDirectory.path, ns('/foo'));
+        });
+
+        test('throwsIfSetToFilePathSegmentAtTail', () {
+          fs.file(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.ENOTDIR, () {
+            fs.currentDirectory = ns('/foo');
+          });
+        });
+
+        test('throwsIfSetToFilePathSegmentViaTraversal', () {
+          fs.file(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.ENOTDIR, () {
+            fs.currentDirectory = ns('/foo/bar/baz');
+          });
+        });
+
+        test('resolvesLinksIfEncountered', () {
+          fs.link(ns('/foo/bar/baz')).createSync(ns('/qux'), recursive: true);
+          fs.directory(ns('/qux')).createSync();
+          fs.directory(ns('/quux')).createSync();
+          fs.currentDirectory = ns('/foo/bar/baz/../quux/');
+          expect(fs.currentDirectory.path, ns('/quux'));
+        });
+
+        test('succeedsIfSetToDirectoryLinkAtTail', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          fs.currentDirectory = ns('/bar');
+          expect(fs.currentDirectory.path, ns('/foo'));
+        });
+
+        test('throwsIfSetToLinkLoop', () {
+          fs.link(ns('/foo')).createSync(ns('/bar'));
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expectFileSystemException(
+            anyOf(ErrorCodes.EMLINK, ErrorCodes.ELOOP),
+            () {
+              fs.currentDirectory = ns('/foo');
+            },
+          );
+        });
+      });
+
+      group('stat', () {
+        test('isNotFoundForEmptyPath', () {
+          FileStat stat = fs.statSync('');
+          expect(stat.type, FileSystemEntityType.notFound);
+        });
+
+        test('isNotFoundForPathToNonExistentEntityAtTail', () {
+          FileStat stat = fs.statSync(ns('/foo'));
+          expect(stat.type, FileSystemEntityType.notFound);
+        });
+
+        test('isNotFoundForPathToNonExistentEntityInTraversal', () {
+          FileStat stat = fs.statSync(ns('/foo/bar'));
+          expect(stat.type, FileSystemEntityType.notFound);
+        });
+
+        test('isDirectoryForDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          FileStat stat = fs.statSync(ns('/foo'));
+          expect(stat.type, FileSystemEntityType.directory);
+        });
+
+        test('isFileForFile', () {
+          fs.file(ns('/foo')).createSync();
+          FileStat stat = fs.statSync(ns('/foo'));
+          expect(stat.type, FileSystemEntityType.file);
+        });
+
+        test('isFileForLinkToFile', () {
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          FileStat stat = fs.statSync(ns('/bar'));
+          expect(stat.type, FileSystemEntityType.file);
+        });
+
+        test('isNotFoundForLinkWithCircularReference', () {
+          fs.link(ns('/foo')).createSync(ns('/bar'));
+          fs.link(ns('/bar')).createSync(ns('/baz'));
+          fs.link(ns('/baz')).createSync(ns('/foo'));
+          FileStat stat = fs.statSync(ns('/foo'));
+          expect(stat.type, FileSystemEntityType.notFound);
+        });
+      });
+
+      group('identical', () {
+        test('isTrueForIdenticalPathsToExistentFile', () {
+          fs.file(ns('/foo')).createSync();
+          expect(fs.identicalSync(ns('/foo'), ns('/foo')), true);
+        });
+
+        test('isFalseForDifferentPathsToDifferentFiles', () {
+          fs.file(ns('/foo')).createSync();
+          fs.file(ns('/bar')).createSync();
+          expect(fs.identicalSync(ns('/foo'), ns('/bar')), false);
+        });
+
+        test('isTrueForDifferentPathsToSameFileViaLinkInTraversal', () {
+          fs.file(ns('/foo/file')).createSync(recursive: true);
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expect(fs.identicalSync(ns('/foo/file'), ns('/bar/file')), true);
+        });
+
+        test('isFalseForDifferentPathsToSameFileViaLinkAtTail', () {
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expect(fs.identicalSync(ns('/foo'), ns('/bar')), false);
+        });
+
+        test('throwsForDifferentPathsToNonExistentEntities', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.identicalSync(ns('/foo'), ns('/bar'));
+          });
+        });
+
+        test('throwsForDifferentPathsToOneFileOneNonExistentEntity', () {
+          fs.file(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.identicalSync(ns('/foo'), ns('/bar'));
+          });
+        });
+      });
+
+      group('type', () {
+        test('isFileForFile', () {
+          fs.file(ns('/foo')).createSync();
+          FileSystemEntityType type = fs.typeSync(ns('/foo'));
+          expect(type, FileSystemEntityType.file);
+        });
+
+        test('isDirectoryForDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          FileSystemEntityType type = fs.typeSync(ns('/foo'));
+          expect(type, FileSystemEntityType.directory);
+        });
+
+        test('isDirectoryForAncestorOfRoot', () {
+          FileSystemEntityType type = fs
+              .typeSync(List<String>.filled(20, '..').join(fs.path.separator));
+          expect(type, FileSystemEntityType.directory);
+        });
+
+        test('isFileForLinkToFileAndFollowLinksTrue', () {
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          FileSystemEntityType type = fs.typeSync(ns('/bar'));
+          expect(type, FileSystemEntityType.file);
+        });
+
+        test('isLinkForLinkToFileAndFollowLinksFalse', () {
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          FileSystemEntityType type =
+              fs.typeSync(ns('/bar'), followLinks: false);
+          expect(type, FileSystemEntityType.link);
+        });
+
+        test('isNotFoundForLinkWithCircularReferenceAndFollowLinksTrue', () {
+          fs.link(ns('/foo')).createSync(ns('/bar'));
+          fs.link(ns('/bar')).createSync(ns('/baz'));
+          fs.link(ns('/baz')).createSync(ns('/foo'));
+          FileSystemEntityType type = fs.typeSync(ns('/foo'));
+          expect(type, FileSystemEntityType.notFound);
+        });
+
+        test('isNotFoundForNoEntityAtTail', () {
+          FileSystemEntityType type = fs.typeSync(ns('/foo'));
+          expect(type, FileSystemEntityType.notFound);
+        });
+
+        test('isNotFoundForNoDirectoryInTraversal', () {
+          FileSystemEntityType type = fs.typeSync(ns('/foo/bar/baz'));
+          expect(type, FileSystemEntityType.notFound);
+        });
+      });
+
+      group('isFile/isDirectory/isLink', () {
+        late String filePath;
+        late String directoryPath;
+        late String fileLinkPath;
+        late String directoryLinkPath;
+
+        setUp(() {
+          filePath = ns('/file');
+          directoryPath = ns('/directory');
+          fileLinkPath = ns('/file-link');
+          directoryLinkPath = ns('/directory-link');
+
+          fs.file(filePath).createSync();
+          fs.directory(directoryPath).createSync();
+          fs.link(fileLinkPath).createSync(filePath);
+          fs.link(directoryLinkPath).createSync(directoryPath);
+        });
+
+        test('isFile', () {
+          expect(fs.isFileSync(filePath), true);
+          expect(fs.isFileSync(directoryPath), false);
+          expect(fs.isFileSync(fileLinkPath), true);
+          expect(fs.isFileSync(directoryLinkPath), false);
+        });
+
+        test('isDirectory', () {
+          expect(fs.isDirectorySync(filePath), false);
+          expect(fs.isDirectorySync(directoryPath), true);
+          expect(fs.isDirectorySync(fileLinkPath), false);
+          expect(fs.isDirectorySync(directoryLinkPath), true);
+        });
+
+        test('isLink', () {
+          expect(fs.isLinkSync(filePath), false);
+          expect(fs.isLinkSync(directoryPath), false);
+          expect(fs.isLinkSync(fileLinkPath), true);
+          expect(fs.isLinkSync(directoryLinkPath), true);
+        });
+      });
+    });
+
+    group('Directory', () {
+      test('uri', () {
+        expect(fs.directory(ns('/foo')).uri, fs.path.toUri('${ns('/foo')}/'));
+        expect(fs.directory('foo').uri.toString(), 'foo/');
+      });
+
+      group('exists', () {
+        test('falseIfNotExists', () {
+          expect(fs.directory(ns('/foo')), isNot(exists));
+          expect(fs.directory('foo'), isNot(exists));
+          expect(fs.directory(ns('/foo/bar')), isNot(exists));
+        });
+
+        test('trueIfExistsAsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expect(fs.directory(ns('/foo')), exists);
+          expect(fs.directory('foo'), exists);
+        });
+
+        test('falseIfExistsAsFile', () {
+          fs.file(ns('/foo')).createSync();
+          expect(fs.directory(ns('/foo')), isNot(exists));
+          expect(fs.directory('foo'), isNot(exists));
+        });
+
+        test('trueIfExistsAsLinkToDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expect(fs.directory(ns('/bar')), exists);
+          expect(fs.directory('bar'), exists);
+        });
+
+        test('falseIfExistsAsLinkToFile', () {
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expect(fs.directory(ns('/bar')), isNot(exists));
+          expect(fs.directory('bar'), isNot(exists));
+        });
+
+        test('falseIfNotFoundSegmentExistsThenIsBackedOut', () {
+          fs.directory(ns('/foo')).createSync();
+          expect(fs.directory(ns('/bar/../foo')), isNot(exists));
+        });
+      });
+
+      group('create', () {
+        test('returnsCovariantType', () async {
+          expect(await fs.directory(ns('/foo')).create(), isDirectory);
+        });
+
+        test('succeedsIfAlreadyExistsAsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.directory(ns('/foo')).createSync();
+        });
+
+        test('throwsIfAlreadyExistsAsFile', () {
+          fs.file(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.ENOTDIR, () {
+            fs.directory(ns('/foo')).createSync();
+          });
+        });
+
+        test('succeedsIfAlreadyExistsAsLinkToDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          fs.directory(ns('/bar')).createSync();
+        });
+
+        test('throwsIfAlreadyExistsAsLinkToFile', () {
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          // TODO(tvolkert): Change this to just be 'Not a directory'
+          // once Dart 1.22 is stable.
+          expectFileSystemException(
+            anyOf(ErrorCodes.EEXIST, ErrorCodes.ENOTDIR),
+            () {
+              fs.directory(ns('/bar')).createSync();
+            },
+          );
+        });
+
+        test('throwsIfAlreadyExistsAsLinkToNotFoundAtTail', () {
+          fs.link(ns('/foo')).createSync(ns('/bar'));
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.directory(ns('/foo')).createSync();
+          });
+        });
+
+        test('throwsIfAlreadyExistsAsLinkToNotFoundViaTraversal', () {
+          fs.link(ns('/foo')).createSync(ns('/bar/baz'));
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.directory(ns('/foo')).createSync();
+          });
+        });
+
+        test('throwsIfAlreadyExistsAsLinkToNotFoundInDifferentDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.directory(ns('/bar')).createSync();
+          fs.link(ns('/bar/baz')).createSync(ns('/foo/qux'));
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.directory(ns('/bar/baz')).createSync();
+          });
+        });
+
+        test('succeedsIfTailDoesntExist', () {
+          expect(fs.directory(ns('/')), exists);
+          fs.directory(ns('/foo')).createSync();
+          expect(fs.directory(ns('/foo')), exists);
+        });
+
+        test('throwsIfAncestorDoesntExistRecursiveFalse', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.directory(ns('/foo/bar')).createSync();
+          });
+        });
+
+        test('succeedsIfAncestorDoesntExistRecursiveTrue', () {
+          fs.directory(ns('/foo/bar')).createSync(recursive: true);
+          expect(fs.directory(ns('/foo')), exists);
+          expect(fs.directory(ns('/foo/bar')), exists);
+        });
+      });
+
+      group('rename', () {
+        test('returnsCovariantType', () async {
+          Directory src() => fs.directory(ns('/foo'))..createSync();
+          expect(src().renameSync(ns('/bar')), isDirectory);
+          expect(await src().rename(ns('/baz')), isDirectory);
+        });
+
+        test('succeedsIfDestinationDoesntExist', () {
+          Directory src = fs.directory(ns('/foo'))..createSync();
+          Directory dest = src.renameSync(ns('/bar'));
+          expect(dest.path, ns('/bar'));
+          expect(dest, exists);
+        });
+
+        test(
+          'succeedsIfDestinationIsEmptyDirectory',
+          () {
+            fs.directory(ns('/bar')).createSync();
+            Directory src = fs.directory(ns('/foo'))..createSync();
+            Directory dest = src.renameSync(ns('/bar'));
+            expect(src, isNot(exists));
+            expect(dest, exists);
+          },
+          // See https://github.com/google/file.dart/issues/197.
+          skip: io.Platform.isWindows,
+        );
+
+        test('throwsIfDestinationIsFile', () {
+          fs.file(ns('/bar')).createSync();
+          Directory src = fs.directory(ns('/foo'))..createSync();
+          expectFileSystemException(ErrorCodes.ENOTDIR, () {
+            src.renameSync(ns('/bar'));
+          });
+        });
+
+        test('throwsIfDestinationParentFolderDoesntExist', () {
+          Directory src = fs.directory(ns('/foo'))..createSync();
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            src.renameSync(ns('/bar/baz'));
+          });
+        });
+
+        test('throwsIfDestinationIsNonEmptyDirectory', () {
+          fs.file(ns('/bar/baz')).createSync(recursive: true);
+          Directory src = fs.directory(ns('/foo'))..createSync();
+          // The error will be 'Directory not empty' on OS X, but it will be
+          // 'File exists' on Linux.
+          expectFileSystemException(
+            anyOf(ErrorCodes.ENOTEMPTY, ErrorCodes.EEXIST),
+            () {
+              src.renameSync(ns('/bar'));
+            },
+          );
+        });
+
+        test('throwsIfSourceDoesntExist', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.directory(ns('/foo')).renameSync(ns('/bar'));
+          });
+        });
+
+        test('throwsIfSourceIsFile', () {
+          fs.file(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.ENOTDIR, () {
+            fs.directory(ns('/foo')).renameSync(ns('/bar'));
+          });
+        });
+
+        test('succeedsIfSourceIsLinkToDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          fs.directory(ns('/bar')).renameSync(ns('/baz'));
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.directory);
+          expect(fs.typeSync(ns('/bar')), FileSystemEntityType.notFound);
+          expect(fs.typeSync(ns('/baz'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(fs.link(ns('/baz')).targetSync(), ns('/foo'));
+        });
+
+        test('throwsIfDestinationIsLinkToNotFound', () {
+          Directory src = fs.directory(ns('/foo'))..createSync();
+          fs.link(ns('/bar')).createSync(ns('/baz'));
+          expectFileSystemException(ErrorCodes.ENOTDIR, () {
+            src.renameSync(ns('/bar'));
+          });
+        });
+
+        test('throwsIfDestinationIsLinkToEmptyDirectory', () {
+          Directory src = fs.directory(ns('/foo'))..createSync();
+          fs.directory(ns('/bar')).createSync();
+          fs.link(ns('/baz')).createSync(ns('/bar'));
+          expectFileSystemException(ErrorCodes.ENOTDIR, () {
+            src.renameSync(ns('/baz'));
+          });
+        });
+
+        test('succeedsIfDestinationIsInDifferentDirectory', () {
+          Directory src = fs.directory(ns('/foo'))..createSync();
+          fs.directory(ns('/bar')).createSync();
+          src.renameSync(ns('/bar/baz'));
+          expect(fs.typeSync(ns('/foo')), FileSystemEntityType.notFound);
+          expect(fs.typeSync(ns('/bar/baz')), FileSystemEntityType.directory);
+        });
+
+        test('succeedsIfSourceIsLinkToDifferentDirectory', () {
+          fs.directory(ns('/foo/subfoo')).createSync(recursive: true);
+          fs.directory(ns('/bar/subbar')).createSync(recursive: true);
+          fs.directory(ns('/baz/subbaz')).createSync(recursive: true);
+          fs.link(ns('/foo/subfoo/lnk')).createSync(ns('/bar/subbar'));
+          fs.directory(ns('/foo/subfoo/lnk')).renameSync(ns('/baz/subbaz/dst'));
+          expect(fs.typeSync(ns('/foo/subfoo/lnk')),
+              FileSystemEntityType.notFound);
+          expect(fs.typeSync(ns('/baz/subbaz/dst'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(fs.typeSync(ns('/baz/subbaz/dst'), followLinks: true),
+              FileSystemEntityType.directory);
+        });
+      });
+
+      group('delete', () {
+        test('returnsCovariantType', () async {
+          Directory dir = fs.directory(ns('/foo'))..createSync();
+          expect(await dir.delete(), isDirectory);
+        });
+
+        test('succeedsIfEmptyDirectoryExistsAndRecursiveFalse', () {
+          Directory dir = fs.directory(ns('/foo'))..createSync();
+          dir.deleteSync();
+          expect(dir, isNot(exists));
+        });
+
+        test('succeedsIfEmptyDirectoryExistsAndRecursiveTrue', () {
+          Directory dir = fs.directory(ns('/foo'))..createSync();
+          dir.deleteSync(recursive: true);
+          expect(dir, isNot(exists));
+        });
+
+        test('throwsIfNonEmptyDirectoryExistsAndRecursiveFalse', () {
+          Directory dir = fs.directory(ns('/foo'))..createSync();
+          fs.file(ns('/foo/bar')).createSync();
+          expectFileSystemException(ErrorCodes.ENOTEMPTY, () {
+            dir.deleteSync();
+          });
+        });
+
+        test('succeedsIfNonEmptyDirectoryExistsAndRecursiveTrue', () {
+          Directory dir = fs.directory(ns('/foo'))..createSync();
+          fs.file(ns('/foo/bar')).createSync();
+          dir.deleteSync(recursive: true);
+          expect(fs.directory(ns('/foo')), isNot(exists));
+          expect(fs.file(ns('/foo/bar')), isNot(exists));
+        });
+
+        test('throwsIfDirectoryDoesntExistAndRecursiveFalse', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.directory(ns('/foo')).deleteSync();
+          });
+        });
+
+        test('throwsIfDirectoryDoesntExistAndRecursiveTrue', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.directory(ns('/foo')).deleteSync(recursive: true);
+          });
+        });
+
+        test('succeedsIfPathReferencesFileAndRecursiveTrue', () {
+          fs.file(ns('/foo')).createSync();
+          fs.directory(ns('/foo')).deleteSync(recursive: true);
+          expect(fs.typeSync(ns('/foo')), FileSystemEntityType.notFound);
+        });
+
+        test('throwsIfPathReferencesFileAndRecursiveFalse', () {
+          fs.file(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.ENOTDIR, () {
+            fs.directory(ns('/foo')).deleteSync();
+          });
+        });
+
+        test('succeedsIfPathReferencesLinkToDirectoryAndRecursiveTrue', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          fs.directory(ns('/bar')).deleteSync(recursive: true);
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.directory);
+          expect(fs.typeSync(ns('/bar'), followLinks: false),
+              FileSystemEntityType.notFound);
+        });
+
+        test('succeedsIfPathReferencesLinkToDirectoryAndRecursiveFalse', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          fs.directory(ns('/bar')).deleteSync();
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.directory);
+          expect(fs.typeSync(ns('/bar'), followLinks: false),
+              FileSystemEntityType.notFound);
+        });
+
+        test('succeedsIfExistsAsLinkToDirectoryInDifferentDirectory', () {
+          fs.directory(ns('/foo/bar')).createSync(recursive: true);
+          fs.link(ns('/baz/qux')).createSync(ns('/foo/bar'), recursive: true);
+          fs.directory(ns('/baz/qux')).deleteSync();
+          expect(fs.typeSync(ns('/foo/bar'), followLinks: false),
+              FileSystemEntityType.directory);
+          expect(fs.typeSync(ns('/baz/qux'), followLinks: false),
+              FileSystemEntityType.notFound);
+        });
+
+        test('succeedsIfPathReferencesLinkToFileAndRecursiveTrue', () {
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          fs.directory(ns('/bar')).deleteSync(recursive: true);
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.file);
+          expect(fs.typeSync(ns('/bar'), followLinks: false),
+              FileSystemEntityType.notFound);
+        });
+
+        test('throwsIfPathReferencesLinkToFileAndRecursiveFalse', () {
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expectFileSystemException(ErrorCodes.ENOTDIR, () {
+            fs.directory(ns('/bar')).deleteSync();
+          });
+        });
+
+        test('throwsIfPathReferencesLinkToNotFoundAndRecursiveFalse', () {
+          fs.link(ns('/foo')).createSync(ns('/bar'));
+          expectFileSystemException(ErrorCodes.ENOTDIR, () {
+            fs.directory(ns('/foo')).deleteSync();
+          });
+        });
+      });
+
+      group('resolveSymbolicLinks', () {
+        test('succeedsForRootDirectory', () {
+          expect(fs.directory(ns('/')).resolveSymbolicLinksSync(), ns('/'));
+        });
+
+        test('throwsIfPathIsEmpty', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.directory('').resolveSymbolicLinksSync();
+          });
+        });
+
+        test('throwsIfLoopInLinkChain', () {
+          fs.link(ns('/foo')).createSync(ns('/bar'));
+          fs.link(ns('/bar')).createSync(ns('/baz'));
+          fs.link(ns('/baz')).createSync(ns('/foo'));
+          expectFileSystemException(
+            anyOf(ErrorCodes.EMLINK, ErrorCodes.ELOOP),
+            () {
+              fs.directory(ns('/foo')).resolveSymbolicLinksSync();
+            },
+          );
+        });
+
+        test('throwsIfPathNotFoundInTraversal', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.directory(ns('/foo/bar')).resolveSymbolicLinksSync();
+          });
+        });
+
+        test('throwsIfPathNotFoundAtTail', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.directory(ns('/foo')).resolveSymbolicLinksSync();
+          });
+        });
+
+        test('throwsIfPathNotFoundInMiddleThenBackedOut', () {
+          fs.directory(ns('/foo/bar')).createSync(recursive: true);
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.directory(ns('/foo/baz/../bar')).resolveSymbolicLinksSync();
+          });
+        });
+
+        test('resolvesRelativePathToCurrentDirectory', () {
+          fs.directory(ns('/foo/bar')).createSync(recursive: true);
+          fs.link(ns('/foo/baz')).createSync(ns('/foo/bar'));
+          fs.currentDirectory = ns('/foo');
+          expect(
+              fs.directory('baz').resolveSymbolicLinksSync(), ns('/foo/bar'));
+        });
+
+        test('resolvesAbsolutePathsAbsolutely', () {
+          fs.directory(ns('/foo/bar')).createSync(recursive: true);
+          fs.currentDirectory = ns('/foo');
+          expect(fs.directory(ns('/foo/bar')).resolveSymbolicLinksSync(),
+              ns('/foo/bar'));
+        });
+
+        test('handlesRelativeLinks', () {
+          fs.directory(ns('/foo/bar/baz')).createSync(recursive: true);
+          fs.link(ns('/foo/qux')).createSync(fs.path.join('bar', 'baz'));
+          expect(
+            fs.directory(ns('/foo/qux')).resolveSymbolicLinksSync(),
+            ns('/foo/bar/baz'),
+          );
+          expect(
+            fs.directory(fs.path.join('foo', 'qux')).resolveSymbolicLinksSync(),
+            ns('/foo/bar/baz'),
+          );
+        });
+
+        test('handlesAbsoluteLinks', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.directory(ns('/bar/baz/qux')).createSync(recursive: true);
+          fs.link(ns('/foo/quux')).createSync(ns('/bar/baz/qux'));
+          expect(fs.directory(ns('/foo/quux')).resolveSymbolicLinksSync(),
+              ns('/bar/baz/qux'));
+        });
+
+        test('handlesLinksWhoseTargetsHaveNestedLinks', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.link(ns('/foo/quuz')).createSync(ns('/bar'));
+          fs.link(ns('/foo/grault')).createSync(ns('/baz/quux'));
+          fs.directory(ns('/bar')).createSync();
+          fs.link(ns('/bar/qux')).createSync(ns('/baz'));
+          fs.link(ns('/bar/garply')).createSync(ns('/foo'));
+          fs.directory(ns('/baz')).createSync();
+          fs.link(ns('/baz/quux')).createSync(ns('/bar/garply/quuz'));
+          expect(fs.directory(ns('/foo/grault/qux')).resolveSymbolicLinksSync(),
+              ns('/baz'));
+        });
+
+        test('handlesParentAndThisFolderReferences', () {
+          fs.directory(ns('/foo/bar/baz')).createSync(recursive: true);
+          fs.link(ns('/foo/bar/baz/qux')).createSync(fs.path.join('..', '..'));
+          String resolved = fs
+              .directory(ns('/foo/./bar/baz/../baz/qux/bar'))
+              .resolveSymbolicLinksSync();
+          expect(resolved, ns('/foo/bar'));
+        });
+
+        test('handlesBackToBackSlashesInPath', () {
+          fs.directory(ns('/foo/bar/baz')).createSync(recursive: true);
+          expect(fs.directory(ns('//foo/bar///baz')).resolveSymbolicLinksSync(),
+              ns('/foo/bar/baz'));
+        });
+
+        test('handlesComplexPathWithMultipleLinks', () {
+          fs
+              .link(ns('/foo/bar/baz'))
+              .createSync(fs.path.join('..', '..', 'qux'), recursive: true);
+          fs.link(ns('/qux')).createSync('quux');
+          fs.link(ns('/quux/quuz')).createSync(ns('/foo'), recursive: true);
+          String resolved = fs
+              .directory(ns('/foo//bar/./baz/quuz/bar/..///bar/baz/'))
+              .resolveSymbolicLinksSync();
+          expect(resolved, ns('/quux'));
+        });
+      });
+
+      group('absolute', () {
+        test('returnsCovariantType', () {
+          expect(fs.directory('foo').absolute, isDirectory);
+        });
+
+        test('returnsSamePathIfAlreadyAbsolute', () {
+          expect(fs.directory(ns('/foo')).absolute.path, ns('/foo'));
+        });
+
+        test('succeedsForRelativePaths', () {
+          expect(fs.directory('foo').absolute.path, ns('/foo'));
+        });
+      });
+
+      group('parent', () {
+        late String root;
+
+        setUp(() {
+          root = fs.path.style.name == 'windows' ? r'C:\' : '/';
+        });
+
+        test('returnsCovariantType', () {
+          expect(fs.directory(root).parent, isDirectory);
+        });
+
+        test('returnsRootForRoot', () {
+          expect(fs.directory(root).parent.path, root);
+        });
+
+        test('succeedsForNonRoot', () {
+          expect(fs.directory(ns('/foo/bar')).parent.path, ns('/foo'));
+        });
+      });
+
+      group('createTemp', () {
+        test('returnsCovariantType', () {
+          expect(fs.directory(ns('/')).createTempSync(), isDirectory);
+        });
+
+        test('throwsIfDirectoryDoesntExist', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.directory(ns('/foo')).createTempSync();
+          });
+        });
+
+        test('resolvesNameCollisions', () {
+          fs.directory(ns('/foo/bar')).createSync(recursive: true);
+          Directory tmp = fs.directory(ns('/foo')).createTempSync('bar');
+          expect(tmp.path,
+              allOf(isNot(ns('/foo/bar')), startsWith(ns('/foo/bar'))));
+        });
+
+        test('succeedsWithoutPrefix', () {
+          Directory dir = fs.directory(ns('/foo'))..createSync();
+          expect(dir.createTempSync().path, startsWith(ns('/foo/')));
+        });
+
+        test('succeedsWithPrefix', () {
+          Directory dir = fs.directory(ns('/foo'))..createSync();
+          expect(dir.createTempSync('bar').path, startsWith(ns('/foo/bar')));
+        });
+
+        test('succeedsWithNestedPathPrefixThatExists', () {
+          fs.directory(ns('/foo/bar')).createSync(recursive: true);
+          Directory tmp = fs.directory(ns('/foo')).createTempSync('bar/baz');
+          expect(tmp.path, startsWith(ns('/foo/bar/baz')));
+        });
+
+        test('throwsWithNestedPathPrefixThatDoesntExist', () {
+          Directory dir = fs.directory(ns('/foo'))..createSync();
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            dir.createTempSync('bar/baz');
+          });
+        });
+      });
+
+      group('list', () {
+        late Directory dir;
+
+        setUp(() {
+          dir = fs.currentDirectory = fs.directory(ns('/foo'))..createSync();
+          fs.file('bar').createSync();
+          fs.file(fs.path.join('baz', 'qux')).createSync(recursive: true);
+          fs.link('quux').createSync(fs.path.join('baz', 'qux'));
+          fs
+              .link(fs.path.join('baz', 'quuz'))
+              .createSync(fs.path.join('..', 'quux'));
+          fs.link(fs.path.join('baz', 'grault')).createSync('.');
+          fs.currentDirectory = ns('/');
+        });
+
+        test('returnsCovariantType', () async {
+          void expectIsFileSystemEntity(dynamic entity) {
+            expect(entity, isFileSystemEntity);
+          }
+
+          dir.listSync().forEach(expectIsFileSystemEntity);
+          (await dir.list().toList()).forEach(expectIsFileSystemEntity);
+        });
+
+        test('returnsEmptyListForEmptyDirectory', () {
+          Directory empty = fs.directory(ns('/bar'))..createSync();
+          expect(empty.listSync(), isEmpty);
+        });
+
+        test('throwsIfDirectoryDoesntExist', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.directory(ns('/bar')).listSync();
+          });
+        });
+
+        test('returnsLinkObjectsIfFollowLinksFalse', () {
+          List<FileSystemEntity> list = dir.listSync(followLinks: false);
+          expect(list, hasLength(3));
+          expect(list, contains(allOf(isFile, hasPath(ns('/foo/bar')))));
+          expect(list, contains(allOf(isDirectory, hasPath(ns('/foo/baz')))));
+          expect(list, contains(allOf(isLink, hasPath(ns('/foo/quux')))));
+        });
+
+        test('followsLinksIfFollowLinksTrue', () {
+          List<FileSystemEntity> list = dir.listSync();
+          expect(list, hasLength(3));
+          expect(list, contains(allOf(isFile, hasPath(ns('/foo/bar')))));
+          expect(list, contains(allOf(isDirectory, hasPath(ns('/foo/baz')))));
+          expect(list, contains(allOf(isFile, hasPath(ns('/foo/quux')))));
+        });
+
+        test('returnsLinkObjectsForRecursiveLinkIfFollowLinksTrue', () {
+          expect(
+            dir.listSync(recursive: true),
+            allOf(
+              hasLength(9),
+              allOf(
+                contains(allOf(isFile, hasPath(ns('/foo/bar')))),
+                contains(allOf(isFile, hasPath(ns('/foo/quux')))),
+                contains(allOf(isFile, hasPath(ns('/foo/baz/qux')))),
+                contains(allOf(isFile, hasPath(ns('/foo/baz/quuz')))),
+                contains(allOf(isFile, hasPath(ns('/foo/baz/grault/qux')))),
+                contains(allOf(isFile, hasPath(ns('/foo/baz/grault/quuz')))),
+              ),
+              allOf(
+                contains(allOf(isDirectory, hasPath(ns('/foo/baz')))),
+                contains(allOf(isDirectory, hasPath(ns('/foo/baz/grault')))),
+              ),
+              contains(allOf(isLink, hasPath(ns('/foo/baz/grault/grault')))),
+            ),
+          );
+        });
+
+        test('recurseIntoDirectoriesIfRecursiveTrueFollowLinksFalse', () {
+          expect(
+            dir.listSync(recursive: true, followLinks: false),
+            allOf(
+              hasLength(6),
+              contains(allOf(isFile, hasPath(ns('/foo/bar')))),
+              contains(allOf(isFile, hasPath(ns('/foo/baz/qux')))),
+              contains(allOf(isLink, hasPath(ns('/foo/quux')))),
+              contains(allOf(isLink, hasPath(ns('/foo/baz/quuz')))),
+              contains(allOf(isLink, hasPath(ns('/foo/baz/grault')))),
+              contains(allOf(isDirectory, hasPath(ns('/foo/baz')))),
+            ),
+          );
+        });
+
+        test('childEntriesNotNormalized', () {
+          dir = fs.directory(ns('/bar/baz'))..createSync(recursive: true);
+          fs.file(ns('/bar/baz/qux')).createSync();
+          List<FileSystemEntity> list =
+              fs.directory(ns('/bar//../bar/./baz')).listSync();
+          expect(list, hasLength(1));
+          expect(list[0], allOf(isFile, hasPath(ns('/bar//../bar/./baz/qux'))));
+        });
+
+        test('symlinksToNotFoundAlwaysReturnedAsLinks', () {
+          dir = fs.directory(ns('/bar'))..createSync();
+          fs.link(ns('/bar/baz')).createSync('qux');
+          for (bool followLinks in const <bool>[true, false]) {
+            List<FileSystemEntity> list =
+                dir.listSync(followLinks: followLinks);
+            expect(list, hasLength(1));
+            expect(list[0], allOf(isLink, hasPath(ns('/bar/baz'))));
+          }
+        });
+      });
+
+      test('childEntities', () {
+        Directory dir = fs.directory(ns('/foo'))..createSync();
+        dir.childDirectory('bar').createSync();
+        dir.childFile('baz').createSync();
+        dir.childLink('qux').createSync('bar');
+        expect(fs.directory(ns('/foo/bar')), exists);
+        expect(fs.file(ns('/foo/baz')), exists);
+        expect(fs.link(ns('/foo/qux')), exists);
+      });
+    });
+
+    group('File', () {
+      test('uri', () {
+        expect(fs.file(ns('/foo')).uri, fs.path.toUri(ns('/foo')));
+        expect(fs.file('foo').uri.toString(), 'foo');
+      });
+
+      group('create', () {
+        test('returnsCovariantType', () async {
+          expect(await fs.file(ns('/foo')).create(), isFile);
+        });
+
+        test('succeedsIfTailDoesntAlreadyExist', () {
+          fs.file(ns('/foo')).createSync();
+          expect(fs.file(ns('/foo')), exists);
+        });
+
+        test('succeedsIfAlreadyExistsAsFile', () {
+          fs.file(ns('/foo')).createSync();
+          fs.file(ns('/foo')).createSync();
+          expect(fs.file(ns('/foo')), exists);
+        });
+
+        test('throwsIfAncestorDoesntExistRecursiveFalse', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.file(ns('/foo/bar')).createSync();
+          });
+        });
+
+        test('succeedsIfAncestorDoesntExistRecursiveTrue', () {
+          fs.file(ns('/foo/bar')).createSync(recursive: true);
+          expect(fs.file(ns('/foo/bar')), exists);
+        });
+
+        test('throwsIfAlreadyExistsAsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/foo')).createSync();
+          });
+        });
+
+        test('throwsIfAlreadyExistsAsLinkToDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/bar')).createSync();
+          });
+        });
+
+        test('succeedsIfAlreadyExistsAsLinkToFile', () {
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          fs.file(ns('/bar')).createSync();
+          expect(fs.file(ns('/bar')), exists);
+        });
+
+        test('succeedsIfAlreadyExistsAsLinkToNotFoundAtTail', () {
+          fs.link(ns('/foo')).createSync(ns('/bar'));
+          fs.file(ns('/foo')).createSync();
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(fs.typeSync(ns('/bar'), followLinks: false),
+              FileSystemEntityType.file);
+        });
+
+        test('throwsIfAlreadyExistsAsLinkToNotFoundViaTraversal', () {
+          fs.link(ns('/foo')).createSync(ns('/bar/baz'));
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.file(ns('/foo')).createSync();
+          });
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.file(ns('/foo')).createSync(recursive: true);
+          });
+        });
+
+        /*
+        test('throwsIfPathSegmentIsLinkToNotFoundAndRecursiveTrue', () {
+          fs.link(ns('/foo')).createSync(ns('/bar'));
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.file(ns('/foo/baz')).createSync(recursive: true);
+          });
+        });
+        */
+
+        test('succeedsIfAlreadyExistsAsLinkToNotFoundInDifferentDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.directory(ns('/bar')).createSync();
+          fs.link(ns('/bar/baz')).createSync(ns('/foo/qux'));
+          fs.file(ns('/bar/baz')).createSync();
+          expect(fs.typeSync(ns('/bar/baz'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(fs.typeSync(ns('/foo/qux'), followLinks: false),
+              FileSystemEntityType.file);
+        });
+      });
+
+      group('rename', () {
+        test('returnsCovariantType', () async {
+          File f() => fs.file(ns('/foo'))..createSync();
+          expect(await f().rename(ns('/bar')), isFile);
+          expect(f().renameSync(ns('/baz')), isFile);
+        });
+
+        test('succeedsIfDestinationDoesntExistAtTail', () {
+          File src = fs.file(ns('/foo'))..createSync();
+          File dest = src.renameSync(ns('/bar'));
+          expect(fs.file(ns('/foo')), isNot(exists));
+          expect(fs.file(ns('/bar')), exists);
+          expect(dest.path, ns('/bar'));
+        });
+
+        test('throwsIfDestinationDoesntExistViaTraversal', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            f.renameSync(ns('/bar/baz'));
+          });
+        });
+
+        test('succeedsIfDestinationExistsAsFile', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          fs.file(ns('/bar')).createSync();
+          f.renameSync(ns('/bar'));
+          expect(fs.file(ns('/foo')), isNot(exists));
+          expect(fs.file(ns('/bar')), exists);
+        });
+
+        test('throwsIfDestinationExistsAsDirectory', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          fs.directory(ns('/bar')).createSync();
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            f.renameSync(ns('/bar'));
+          });
+        });
+
+        test('succeedsIfDestinationExistsAsLinkToFile', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          fs.file(ns('/bar')).createSync();
+          fs.link(ns('/baz')).createSync(ns('/bar'));
+          f.renameSync(ns('/baz'));
+          expect(fs.typeSync(ns('/foo')), FileSystemEntityType.notFound);
+          expect(fs.typeSync(ns('/bar'), followLinks: false),
+              FileSystemEntityType.file);
+          expect(fs.typeSync(ns('/baz'), followLinks: false),
+              FileSystemEntityType.file);
+        });
+
+        test('throwsIfDestinationExistsAsLinkToDirectory', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          fs.directory(ns('/bar')).createSync();
+          fs.link(ns('/baz')).createSync(ns('/bar'));
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            f.renameSync(ns('/baz'));
+          });
+        });
+
+        test('succeedsIfDestinationExistsAsLinkToNotFound', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          fs.link(ns('/bar')).createSync(ns('/baz'));
+          f.renameSync(ns('/bar'));
+          expect(fs.typeSync(ns('/foo')), FileSystemEntityType.notFound);
+          expect(fs.typeSync(ns('/bar'), followLinks: false),
+              FileSystemEntityType.file);
+        });
+
+        test('throwsIfSourceDoesntExist', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.file(ns('/foo')).renameSync(ns('/bar'));
+          });
+        });
+
+        test('throwsIfSourceExistsAsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/foo')).renameSync(ns('/bar'));
+          });
+        });
+
+        test('succeedsIfSourceExistsAsLinkToFile', () {
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          fs.file(ns('/bar')).renameSync(ns('/baz'));
+          expect(fs.typeSync(ns('/bar')), FileSystemEntityType.notFound);
+          expect(fs.typeSync(ns('/baz'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(fs.typeSync(ns('/baz'), followLinks: true),
+              FileSystemEntityType.file);
+        });
+
+        test('throwsIfSourceExistsAsLinkToDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/bar')).renameSync(ns('/baz'));
+          });
+        });
+
+        test('throwsIfSourceExistsAsLinkToNotFound', () {
+          fs.link(ns('/foo')).createSync(ns('/bar'));
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.file(ns('/foo')).renameSync(ns('/baz'));
+          });
+        });
+      });
+
+      group('copy', () {
+        test('returnsCovariantType', () async {
+          File f() => fs.file(ns('/foo'))..createSync();
+          expect(await f().copy(ns('/bar')), isFile);
+          expect(f().copySync(ns('/baz')), isFile);
+        });
+
+        test('succeedsIfDestinationDoesntExistAtTail', () {
+          File f = fs.file(ns('/foo'))
+            ..createSync()
+            ..writeAsStringSync('foo');
+          f.copySync(ns('/bar'));
+          expect(fs.file(ns('/foo')), exists);
+          expect(fs.file(ns('/bar')), exists);
+          expect(fs.file(ns('/foo')).readAsStringSync(), 'foo');
+        });
+
+        test('throwsIfDestinationDoesntExistViaTraversal', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            f.copySync(ns('/bar/baz'));
+          });
+        });
+
+        test('succeedsIfDestinationExistsAsFile', () {
+          File f = fs.file(ns('/foo'))
+            ..createSync()
+            ..writeAsStringSync('foo');
+          fs.file(ns('/bar'))
+            ..createSync()
+            ..writeAsStringSync('bar');
+          f.copySync(ns('/bar'));
+          expect(fs.file(ns('/foo')), exists);
+          expect(fs.file(ns('/bar')), exists);
+          expect(fs.file(ns('/foo')).readAsStringSync(), 'foo');
+          expect(fs.file(ns('/bar')).readAsStringSync(), 'foo');
+        });
+
+        test('throwsIfDestinationExistsAsDirectory', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          fs.directory(ns('/bar')).createSync();
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            f.copySync(ns('/bar'));
+          });
+        });
+
+        test('succeedsIfDestinationExistsAsLinkToFile', () {
+          File f = fs.file(ns('/foo'))
+            ..createSync()
+            ..writeAsStringSync('foo');
+          fs.file(ns('/bar'))
+            ..createSync()
+            ..writeAsStringSync('bar');
+          fs.link(ns('/baz')).createSync(ns('/bar'));
+          f.copySync(ns('/baz'));
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.file);
+          expect(fs.typeSync(ns('/bar'), followLinks: false),
+              FileSystemEntityType.file);
+          expect(fs.typeSync(ns('/baz'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(fs.file(ns('/foo')).readAsStringSync(), 'foo');
+          expect(fs.file(ns('/bar')).readAsStringSync(), 'foo');
+        }, skip: io.Platform.isWindows /* No links on Windows */);
+
+        test('throwsIfDestinationExistsAsLinkToDirectory', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          fs.directory(ns('/bar')).createSync();
+          fs.link(ns('/baz')).createSync(ns('/bar'));
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            f.copySync(ns('/baz'));
+          });
+        });
+
+        test('throwsIfSourceDoesntExist', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.file(ns('/foo')).copySync(ns('/bar'));
+          });
+        });
+
+        test('throwsIfSourceExistsAsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/foo')).copySync(ns('/bar'));
+          });
+        });
+
+        test('succeedsIfSourceExistsAsLinkToFile', () {
+          fs.file(ns('/foo'))
+            ..createSync()
+            ..writeAsStringSync('foo');
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          fs.file(ns('/bar')).copySync(ns('/baz'));
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.file);
+          expect(fs.typeSync(ns('/bar'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(fs.typeSync(ns('/baz'), followLinks: false),
+              FileSystemEntityType.file);
+          expect(fs.file(ns('/foo')).readAsStringSync(), 'foo');
+          expect(fs.file(ns('/baz')).readAsStringSync(), 'foo');
+        });
+
+        test('succeedsIfDestinationIsInDifferentDirectoryThanSource', () {
+          File f = fs.file(ns('/foo/bar'))
+            ..createSync(recursive: true)
+            ..writeAsStringSync('foo');
+          fs.directory(ns('/baz')).createSync();
+          f.copySync(ns('/baz/qux'));
+          expect(fs.file(ns('/foo/bar')), exists);
+          expect(fs.file(ns('/baz/qux')), exists);
+          expect(fs.file(ns('/foo/bar')).readAsStringSync(), 'foo');
+          expect(fs.file(ns('/baz/qux')).readAsStringSync(), 'foo');
+        });
+
+        test('succeedsIfSourceIsLinkToFileInDifferentDirectory', () {
+          fs.file(ns('/foo/bar'))
+            ..createSync(recursive: true)
+            ..writeAsStringSync('foo');
+          fs.link(ns('/baz/qux')).createSync(ns('/foo/bar'), recursive: true);
+          fs.file(ns('/baz/qux')).copySync(ns('/baz/quux'));
+          expect(fs.typeSync(ns('/foo/bar'), followLinks: false),
+              FileSystemEntityType.file);
+          expect(fs.typeSync(ns('/baz/qux'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(fs.typeSync(ns('/baz/quux'), followLinks: false),
+              FileSystemEntityType.file);
+          expect(fs.file(ns('/foo/bar')).readAsStringSync(), 'foo');
+          expect(fs.file(ns('/baz/quux')).readAsStringSync(), 'foo');
+        });
+
+        test('succeedsIfDestinationIsLinkToFileInDifferentDirectory', () {
+          fs.file(ns('/foo/bar'))
+            ..createSync(recursive: true)
+            ..writeAsStringSync('bar');
+          fs.file(ns('/baz/qux'))
+            ..createSync(recursive: true)
+            ..writeAsStringSync('qux');
+          fs.link(ns('/baz/quux')).createSync(ns('/foo/bar'));
+          fs.file(ns('/baz/qux')).copySync(ns('/baz/quux'));
+          expect(fs.typeSync(ns('/foo/bar'), followLinks: false),
+              FileSystemEntityType.file);
+          expect(fs.typeSync(ns('/baz/qux'), followLinks: false),
+              FileSystemEntityType.file);
+          expect(fs.typeSync(ns('/baz/quux'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(fs.file(ns('/foo/bar')).readAsStringSync(), 'qux');
+          expect(fs.file(ns('/baz/qux')).readAsStringSync(), 'qux');
+        }, skip: io.Platform.isWindows /* No links on Windows */);
+      });
+
+      group('length', () {
+        test('throwsIfDoesntExist', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.file(ns('/foo')).lengthSync();
+          });
+        });
+
+        test('throwsIfExistsAsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/foo')).lengthSync();
+          });
+        });
+
+        test('returnsZeroForNewlyCreatedFile', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          expect(f.lengthSync(), 0);
+        });
+
+        test('writeNBytesReturnsLengthN', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          f.writeAsBytesSync(<int>[1, 2, 3, 4], flush: true);
+          expect(f.lengthSync(), 4);
+        });
+
+        test('succeedsIfExistsAsLinkToFile', () {
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expect(fs.file(ns('/bar')).lengthSync(), 0);
+        });
+      });
+
+      group('absolute', () {
+        test('returnsSamePathIfAlreadyAbsolute', () {
+          expect(fs.file(ns('/foo')).absolute.path, ns('/foo'));
+        });
+
+        test('succeedsForRelativePaths', () {
+          expect(fs.file('foo').absolute.path, ns('/foo'));
+        });
+      });
+
+      group('lastAccessed', () {
+        test('isNowForNewlyCreatedFile', () {
+          DateTime before = downstairs();
+          File f = fs.file(ns('/foo'))..createSync();
+          DateTime after = ceil();
+          DateTime accessed = f.lastAccessedSync();
+          expect(accessed, isSameOrAfter(before));
+          expect(accessed, isSameOrBefore(after));
+        });
+
+        test('throwsIfDoesntExist', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.file(ns('/foo')).lastAccessedSync();
+          });
+        });
+
+        test('throwsIfExistsAsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/foo')).lastAccessedSync();
+          });
+        });
+
+        test('succeedsIfExistsAsLinkToFile', () {
+          DateTime before = downstairs();
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          DateTime after = ceil();
+          DateTime accessed = fs.file(ns('/bar')).lastAccessedSync();
+          expect(accessed, isSameOrAfter(before));
+          expect(accessed, isSameOrBefore(after));
+        });
+      });
+
+      group('setLastAccessed', () {
+        final DateTime time = DateTime(1999);
+
+        test('throwsIfDoesntExist', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.file(ns('/foo')).setLastAccessedSync(time);
+          });
+        });
+
+        test('throwsIfExistsAsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/foo')).setLastAccessedSync(time);
+          });
+        });
+
+        test('succeedsIfExistsAsFile', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          f.setLastAccessedSync(time);
+          expect(fs.file(ns('/foo')).lastAccessedSync(), time);
+        });
+
+        test('succeedsIfExistsAsLinkToFile', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          f.setLastAccessedSync(time);
+          expect(fs.file(ns('/bar')).lastAccessedSync(), time);
+        });
+      });
+
+      group('lastModified', () {
+        test('isNowForNewlyCreatedFile', () {
+          DateTime before = downstairs();
+          File f = fs.file(ns('/foo'))..createSync();
+          DateTime after = ceil();
+          DateTime modified = f.lastModifiedSync();
+          expect(modified, isSameOrAfter(before));
+          expect(modified, isSameOrBefore(after));
+        });
+
+        test('throwsIfDoesntExist', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.file(ns('/foo')).lastModifiedSync();
+          });
+        });
+
+        test('throwsIfExistsAsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/foo')).lastModifiedSync();
+          });
+        });
+
+        test('succeedsIfExistsAsLinkToFile', () {
+          DateTime before = downstairs();
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          DateTime after = ceil();
+          DateTime modified = fs.file(ns('/bar')).lastModifiedSync();
+          expect(modified, isSameOrAfter(before));
+          expect(modified, isSameOrBefore(after));
+        });
+      });
+
+      group('setLastModified', () {
+        final DateTime time = DateTime(1999);
+
+        test('throwsIfDoesntExist', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.file(ns('/foo')).setLastModifiedSync(time);
+          });
+        });
+
+        test('throwsIfExistsAsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/foo')).setLastModifiedSync(time);
+          });
+        });
+
+        test('succeedsIfExistsAsFile', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          f.setLastModifiedSync(time);
+          expect(fs.file(ns('/foo')).lastModifiedSync(), time);
+        });
+
+        test('succeedsIfExistsAsLinkToFile', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          f.setLastModifiedSync(time);
+          expect(fs.file(ns('/bar')).lastModifiedSync(), time);
+        });
+      });
+
+      group('open', () {
+        void testIfDoesntExistAtTail(FileMode mode) {
+          if (mode == FileMode.read) {
+            test('throwsIfDoesntExistAtTail', () {
+              expectFileSystemException(ErrorCodes.ENOENT, () {
+                fs.file(ns('/bar')).openSync(mode: mode);
+              });
+            });
+          } else {
+            test('createsFileIfDoesntExistAtTail', () {
+              RandomAccessFile raf = fs.file(ns('/bar')).openSync(mode: mode);
+              raf.closeSync();
+              expect(fs.file(ns('/bar')), exists);
+            });
+          }
+        }
+
+        void testThrowsIfDoesntExistViaTraversal(FileMode mode) {
+          test('throwsIfDoesntExistViaTraversal', () {
+            expectFileSystemException(ErrorCodes.ENOENT, () {
+              fs.file(ns('/bar/baz')).openSync(mode: mode);
+            });
+          });
+        }
+
+        void testRandomAccessFileOperations(FileMode mode) {
+          group('RandomAccessFile', () {
+            late File f;
+            late RandomAccessFile raf;
+
+            setUp(() {
+              f = fs.file(ns('/foo'))..createSync();
+              f.writeAsStringSync('pre-existing content\n', flush: true);
+              raf = f.openSync(mode: mode);
+            });
+
+            tearDown(() {
+              try {
+                raf.closeSync();
+              } on FileSystemException {
+                // Ignore; a test may have already closed it.
+              }
+            });
+
+            test('succeedsIfClosedAfterClosed', () {
+              raf.closeSync();
+              expectFileSystemException(null, () {
+                raf.closeSync();
+              });
+            });
+
+            test('throwsIfReadAfterClose', () {
+              raf.closeSync();
+              expectFileSystemException(null, () {
+                raf.readByteSync();
+              });
+            });
+
+            test('throwsIfWriteAfterClose', () {
+              raf.closeSync();
+              expectFileSystemException(null, () {
+                raf.writeByteSync(0xBAD);
+              });
+            });
+
+            test('throwsIfTruncateAfterClose', () {
+              raf.closeSync();
+              expectFileSystemException(null, () {
+                raf.truncateSync(0);
+              });
+            });
+
+            if (mode == FileMode.write || mode == FileMode.writeOnly) {
+              test('lengthIsResetToZeroIfOpened', () {
+                expect(raf.lengthSync(), equals(0));
+              });
+
+              test('throwsIfAsyncUnawaited', () async {
+                try {
+                  final Future<void> future = raf.flush();
+                  expectFileSystemException(null, () => raf.flush());
+                  expectFileSystemException(null, () => raf.flushSync());
+                  await expectLater(future, completes);
+                  raf.flushSync();
+                } finally {
+                  raf.closeSync();
+                }
+              });
+            } else {
+              test('lengthIsNotModifiedIfOpened', () {
+                expect(raf.lengthSync(), isNot(equals(0)));
+              });
+            }
+
+            if (mode == FileMode.writeOnly ||
+                mode == FileMode.writeOnlyAppend) {
+              test('throwsIfReadByte', () {
+                expectFileSystemException(ErrorCodes.EBADF, () {
+                  raf.readByteSync();
+                });
+              });
+
+              test('throwsIfRead', () {
+                expectFileSystemException(ErrorCodes.EBADF, () {
+                  raf.readSync(2);
+                });
+              });
+
+              test('throwsIfReadInto', () {
+                expectFileSystemException(ErrorCodes.EBADF, () {
+                  raf.readIntoSync(List<int>.filled(5, 0));
+                });
+              });
+            } else {
+              group('read', () {
+                setUp(() {
+                  if (mode == FileMode.write) {
+                    // Write data back that we truncated when opening the file.
+                    raf.writeStringSync('pre-existing content\n');
+                  }
+                  // Reset the position to zero so we can read the content.
+                  raf.setPositionSync(0);
+                });
+
+                test('readByte', () {
+                  expect(utf8.decode(<int>[raf.readByteSync()]), 'p');
+                });
+
+                test('read', () {
+                  List<int> bytes = raf.readSync(1024);
+                  expect(bytes.length, 21);
+                  expect(utf8.decode(bytes), 'pre-existing content\n');
+                });
+
+                test('readIntoWithBufferLargerThanContent', () {
+                  List<int> buffer = List<int>.filled(1024, 0);
+                  int numRead = raf.readIntoSync(buffer);
+                  expect(numRead, 21);
+                  expect(utf8.decode(buffer.sublist(0, 21)),
+                      'pre-existing content\n');
+                });
+
+                test('readIntoWithBufferSmallerThanContent', () {
+                  List<int> buffer = List<int>.filled(10, 0);
+                  int numRead = raf.readIntoSync(buffer);
+                  expect(numRead, 10);
+                  expect(utf8.decode(buffer), 'pre-existi');
+                });
+
+                test('readIntoWithStart', () {
+                  List<int> buffer = List<int>.filled(10, 0);
+                  int numRead = raf.readIntoSync(buffer, 2);
+                  expect(numRead, 8);
+                  expect(utf8.decode(buffer.sublist(2)), 'pre-exis');
+                });
+
+                test('readIntoWithStartAndEnd', () {
+                  List<int> buffer = List<int>.filled(10, 0);
+                  int numRead = raf.readIntoSync(buffer, 2, 5);
+                  expect(numRead, 3);
+                  expect(utf8.decode(buffer.sublist(2, 5)), 'pre');
+                });
+
+                test('openReadHandleDoesNotChange', () {
+                  final String initial = utf8.decode(raf.readSync(4));
+                  expect(initial, 'pre-');
+                  final File newFile = f.renameSync(ns('/bar'));
+                  String rest = utf8.decode(raf.readSync(1024));
+                  expect(rest, 'existing content\n');
+
+                  assert(newFile.path != f.path);
+                  expect(f, isNot(exists));
+                  expect(newFile, exists);
+
+                  // [RandomAccessFile.path] always returns the original path.
+                  expect(raf.path, f.path);
+                });
+              });
+            }
+
+            if (mode == FileMode.read) {
+              test('throwsIfWriteByte', () {
+                expectFileSystemException(ErrorCodes.EBADF, () {
+                  raf.writeByteSync(0xBAD);
+                });
+              });
+
+              test('throwsIfWriteFrom', () {
+                expectFileSystemException(ErrorCodes.EBADF, () {
+                  raf.writeFromSync(<int>[1, 2, 3, 4]);
+                });
+              });
+
+              test('throwsIfWriteString', () {
+                expectFileSystemException(ErrorCodes.EBADF, () {
+                  raf.writeStringSync('This should throw.');
+                });
+              });
+            } else {
+              test('lengthGrowsAsDataIsWritten', () {
+                int lengthBefore = f.lengthSync();
+                raf.writeByteSync(0xFACE);
+                expect(raf.lengthSync(), lengthBefore + 1);
+              });
+
+              test('flush', () {
+                int lengthBefore = f.lengthSync();
+                raf.writeByteSync(0xFACE);
+                raf.flushSync();
+                expect(f.lengthSync(), lengthBefore + 1);
+              });
+
+              test('writeByte', () {
+                raf.writeByteSync(utf8.encode('A').first);
+                raf.flushSync();
+                if (mode == FileMode.write || mode == FileMode.writeOnly) {
+                  expect(f.readAsStringSync(), 'A');
+                } else {
+                  expect(f.readAsStringSync(), 'pre-existing content\nA');
+                }
+              });
+
+              test('writeFrom', () {
+                raf.writeFromSync(utf8.encode('Hello world'));
+                raf.flushSync();
+                if (mode == FileMode.write || mode == FileMode.writeOnly) {
+                  expect(f.readAsStringSync(), 'Hello world');
+                } else {
+                  expect(f.readAsStringSync(),
+                      'pre-existing content\nHello world');
+                }
+              });
+
+              test('writeFromWithStart', () {
+                raf.writeFromSync(utf8.encode('Hello world'), 2);
+                raf.flushSync();
+                if (mode == FileMode.write || mode == FileMode.writeOnly) {
+                  expect(f.readAsStringSync(), 'llo world');
+                } else {
+                  expect(
+                      f.readAsStringSync(), 'pre-existing content\nllo world');
+                }
+              });
+
+              test('writeFromWithStartAndEnd', () {
+                raf.writeFromSync(utf8.encode('Hello world'), 2, 5);
+                raf.flushSync();
+                if (mode == FileMode.write || mode == FileMode.writeOnly) {
+                  expect(f.readAsStringSync(), 'llo');
+                } else {
+                  expect(f.readAsStringSync(), 'pre-existing content\nllo');
+                }
+              });
+
+              test('writeString', () {
+                raf.writeStringSync('Hello world');
+                raf.flushSync();
+                if (mode == FileMode.write || mode == FileMode.writeOnly) {
+                  expect(f.readAsStringSync(), 'Hello world');
+                } else {
+                  expect(f.readAsStringSync(),
+                      'pre-existing content\nHello world');
+                }
+              });
+
+              test('openWriteHandleDoesNotChange', () {
+                raf.writeStringSync('Hello ');
+                final File newFile = f.renameSync(ns('/bar'));
+                raf.writeStringSync('world');
+
+                final String contents = newFile.readAsStringSync();
+                if (mode == FileMode.write || mode == FileMode.writeOnly) {
+                  expect(contents, 'Hello world');
+                } else {
+                  expect(contents, 'pre-existing content\nHello world');
+                }
+
+                assert(newFile.path != f.path);
+                expect(f, isNot(exists));
+                expect(newFile, exists);
+
+                // [RandomAccessFile.path] always returns the original path.
+                expect(raf.path, f.path);
+              });
+            }
+
+            if (mode == FileMode.append || mode == FileMode.writeOnlyAppend) {
+              test('positionInitializedToEndOfFile', () {
+                expect(raf.positionSync(), 21);
+              });
+            } else {
+              test('positionInitializedToZero', () {
+                expect(raf.positionSync(), 0);
+              });
+            }
+
+            group('position', () {
+              setUp(() {
+                if (mode == FileMode.write || mode == FileMode.writeOnly) {
+                  // Write data back that we truncated when opening the file.
+                  raf.writeStringSync('pre-existing content\n');
+                }
+              });
+
+              if (mode != FileMode.writeOnly &&
+                  mode != FileMode.writeOnlyAppend) {
+                test('growsAfterRead', () {
+                  raf.setPositionSync(0);
+                  raf.readSync(10);
+                  expect(raf.positionSync(), 10);
+                });
+
+                test('affectsRead', () {
+                  raf.setPositionSync(5);
+                  expect(utf8.decode(raf.readSync(5)), 'xisti');
+                });
+              }
+
+              if (mode == FileMode.read) {
+                test('succeedsIfSetPastEndOfFile', () {
+                  raf.setPositionSync(32);
+                  expect(raf.positionSync(), 32);
+                });
+              } else {
+                test('growsAfterWrite', () {
+                  int positionBefore = raf.positionSync();
+                  raf.writeStringSync('Hello world');
+                  expect(raf.positionSync(), positionBefore + 11);
+                });
+
+                test('affectsWrite', () {
+                  raf.setPositionSync(5);
+                  raf.writeStringSync('-yo-');
+                  raf.flushSync();
+                  expect(f.readAsStringSync(), 'pre-e-yo-ing content\n');
+                });
+
+                test('succeedsIfSetAndWrittenPastEndOfFile', () {
+                  raf.setPositionSync(32);
+                  expect(raf.positionSync(), 32);
+                  raf.writeStringSync('here');
+                  raf.flushSync();
+                  List<int> bytes = f.readAsBytesSync();
+                  expect(bytes.length, 36);
+                  expect(utf8.decode(bytes.sublist(0, 21)),
+                      'pre-existing content\n');
+                  expect(utf8.decode(bytes.sublist(32, 36)), 'here');
+                  expect(bytes.sublist(21, 32), everyElement(0));
+                });
+              }
+
+              test('throwsIfSetToNegativeNumber', () {
+                expectFileSystemException(ErrorCodes.EINVAL, () {
+                  raf.setPositionSync(-12);
+                });
+              });
+            });
+
+            if (mode == FileMode.read) {
+              test('throwsIfTruncate', () {
+                expectFileSystemException(ErrorCodes.EINVAL, () {
+                  raf.truncateSync(5);
+                });
+              });
+            } else {
+              group('truncate', () {
+                setUp(() {
+                  if (mode == FileMode.write || mode == FileMode.writeOnly) {
+                    // Write data back that we truncated when opening the file.
+                    raf.writeStringSync('pre-existing content\n');
+                  }
+                });
+
+                test('succeedsIfSetWithinRangeOfContent', () {
+                  raf.truncateSync(5);
+                  raf.flushSync();
+                  expect(f.lengthSync(), 5);
+                  expect(f.readAsStringSync(), 'pre-e');
+                });
+
+                test('succeedsIfSetToZero', () {
+                  raf.truncateSync(0);
+                  raf.flushSync();
+                  expect(f.lengthSync(), 0);
+                  expect(f.readAsStringSync(), isEmpty);
+                });
+
+                test('throwsIfSetToNegativeNumber', () {
+                  expectFileSystemException(ErrorCodes.EINVAL, () {
+                    raf.truncateSync(-2);
+                  });
+                });
+
+                test('extendsFileIfSetPastEndOfFile', () {
+                  raf.truncateSync(32);
+                  raf.flushSync();
+                  List<int> bytes = f.readAsBytesSync();
+                  expect(bytes.length, 32);
+                  expect(utf8.decode(bytes.sublist(0, 21)),
+                      'pre-existing content\n');
+                  expect(bytes.sublist(21, 32), everyElement(0));
+                });
+              });
+            }
+          });
+        }
+
+        void testOpenWithMode(FileMode mode) {
+          testIfDoesntExistAtTail(mode);
+          testThrowsIfDoesntExistViaTraversal(mode);
+          testRandomAccessFileOperations(mode);
+        }
+
+        group('READ', () => testOpenWithMode(FileMode.read));
+        group('WRITE', () => testOpenWithMode(FileMode.write));
+        group('APPEND', () => testOpenWithMode(FileMode.append));
+        group('WRITE_ONLY', () => testOpenWithMode(FileMode.writeOnly));
+        group('WRITE_ONLY_APPEND',
+            () => testOpenWithMode(FileMode.writeOnlyAppend));
+      });
+
+      group('openRead', () {
+        test('throwsIfDoesntExist', () {
+          Stream<List<int>> stream = fs.file(ns('/foo')).openRead();
+          expect(stream.drain<void>(),
+              throwsFileSystemException(ErrorCodes.ENOENT));
+        });
+
+        test('succeedsIfExistsAsFile', () async {
+          File f = fs.file(ns('/foo'))..createSync();
+          f.writeAsStringSync('Hello world', flush: true);
+          Stream<List<int>> stream = f.openRead();
+          List<List<int>> data = await stream.toList();
+          expect(data, hasLength(1));
+          expect(utf8.decode(data[0]), 'Hello world');
+        });
+
+        test('throwsIfExistsAsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          Stream<List<int>> stream = fs.file(ns('/foo')).openRead();
+          expect(stream.drain<void>(),
+              throwsFileSystemException(ErrorCodes.EISDIR));
+        });
+
+        test('succeedsIfExistsAsLinkToFile', () async {
+          File f = fs.file(ns('/foo'))..createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          f.writeAsStringSync('Hello world', flush: true);
+          Stream<List<int>> stream = fs.file(ns('/bar')).openRead();
+          List<List<int>> data = await stream.toList();
+          expect(data, hasLength(1));
+          expect(utf8.decode(data[0]), 'Hello world');
+        });
+
+        test('respectsStartAndEndParameters', () async {
+          File f = fs.file(ns('/foo'))..createSync();
+          f.writeAsStringSync('Hello world', flush: true);
+          Stream<List<int>> stream = f.openRead(2);
+          List<List<int>> data = await stream.toList();
+          expect(data, hasLength(1));
+          expect(utf8.decode(data[0]), 'llo world');
+          stream = f.openRead(2, 5);
+          data = await stream.toList();
+          expect(data, hasLength(1));
+          expect(utf8.decode(data[0]), 'llo');
+        });
+
+        test('throwsIfStartParameterIsNegative', () async {
+          File f = fs.file(ns('/foo'))..createSync();
+          Stream<List<int>> stream = f.openRead(-2);
+          expect(stream.drain<void>(), throwsRangeError);
+        });
+
+        test('stopsAtEndOfFileIfEndParameterIsPastEndOfFile', () async {
+          File f = fs.file(ns('/foo'))..createSync();
+          f.writeAsStringSync('Hello world', flush: true);
+          Stream<List<int>> stream = f.openRead(2, 1024);
+          List<List<int>> data = await stream.toList();
+          expect(data, hasLength(1));
+          expect(utf8.decode(data[0]), 'llo world');
+        });
+
+        test('providesSingleSubscriptionStream', () async {
+          File f = fs.file(ns('/foo'))..createSync();
+          f.writeAsStringSync('Hello world', flush: true);
+          Stream<List<int>> stream = f.openRead();
+          expect(stream.isBroadcast, isFalse);
+          await stream.drain<void>();
+        });
+
+        test('openReadHandleDoesNotChange', () async {
+          // Ideally, `data` should be large enough so that its contents are
+          // split across multiple chunks in the [Stream].  However, there
+          // doesn't seem to be a good way to determine the chunk size used by
+          // [io.File].
+          final List<int> data = List<int>.generate(
+            1024 * 256,
+            (int index) => index & 0xFF,
+            growable: false,
+          );
+
+          final File f = fs.file(ns('/foo'))..createSync();
+
+          f.writeAsBytesSync(data, flush: true);
+          final Stream<List<int>> stream = f.openRead();
+
+          File? newFile;
+          List<int>? initialChunk;
+          final List<int> remainingChunks = <int>[];
+
+          await for (List<int> chunk in stream) {
+            if (initialChunk == null) {
+              initialChunk = chunk;
+              assert(initialChunk.isNotEmpty);
+              expect(initialChunk, data.getRange(0, initialChunk.length));
+
+              newFile = f.renameSync(ns('/bar'));
+            } else {
+              remainingChunks.addAll(chunk);
+            }
+          }
+
+          expect(
+            remainingChunks,
+            data.getRange(initialChunk!.length, data.length),
+          );
+
+          assert(newFile?.path != f.path);
+          expect(f, isNot(exists));
+          expect(newFile, exists);
+        });
+
+        test('openReadCompatibleWithUtf8Decoder', () async {
+          const content = 'Hello world!';
+          File file = fs.file(ns('/foo'))
+            ..createSync()
+            ..writeAsStringSync(content);
+          expect(
+            await file
+                .openRead()
+                .transform(utf8.decoder)
+                .transform(const LineSplitter())
+                .first,
+            content,
+          );
+        });
+      });
+
+      group('openWrite', () {
+        test('createsFileIfDoesntExist', () async {
+          await fs.file(ns('/foo')).openWrite().close();
+          expect(fs.file(ns('/foo')), exists);
+        });
+
+        test('throwsIfExistsAsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expect(fs.file(ns('/foo')).openWrite().close(),
+              throwsFileSystemException(ErrorCodes.EISDIR));
+        });
+
+        test('throwsIfExistsAsLinkToDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expect(fs.file(ns('/bar')).openWrite().close(),
+              throwsFileSystemException(ErrorCodes.EISDIR));
+        });
+
+        test('throwsIfModeIsRead', () {
+          expect(() => fs.file(ns('/foo')).openWrite(mode: FileMode.read),
+              throwsArgumentError);
+        });
+
+        test('succeedsIfExistsAsEmptyFile', () async {
+          File f = fs.file(ns('/foo'))..createSync();
+          IOSink sink = f.openWrite();
+          sink.write('Hello world');
+          await sink.flush();
+          await sink.close();
+          expect(f.readAsStringSync(), 'Hello world');
+        });
+
+        test('succeedsIfExistsAsLinkToFile', () async {
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          IOSink sink = fs.file(ns('/bar')).openWrite();
+          sink.write('Hello world');
+          await sink.flush();
+          await sink.close();
+          expect(fs.file(ns('/foo')).readAsStringSync(), 'Hello world');
+        });
+
+        test('overwritesContentInWriteMode', () async {
+          File f = fs.file(ns('/foo'))..createSync();
+          f.writeAsStringSync('Hello');
+          IOSink sink = f.openWrite();
+          sink.write('Goodbye');
+          await sink.flush();
+          await sink.close();
+          expect(fs.file(ns('/foo')).readAsStringSync(), 'Goodbye');
+        });
+
+        test('appendsContentInAppendMode', () async {
+          File f = fs.file(ns('/foo'))..createSync();
+          f.writeAsStringSync('Hello');
+          IOSink sink = f.openWrite(mode: FileMode.append);
+          sink.write('Goodbye');
+          await sink.flush();
+          await sink.close();
+          expect(fs.file(ns('/foo')).readAsStringSync(), 'HelloGoodbye');
+        });
+
+        test('openWriteHandleDoesNotChange', () async {
+          File f = fs.file(ns('/foo'))..createSync();
+          IOSink sink = f.openWrite();
+          sink.write('Hello');
+          await sink.flush();
+
+          final File newFile = f.renameSync(ns('/bar'));
+          sink.write('Goodbye');
+          await sink.flush();
+          await sink.close();
+
+          expect(newFile.readAsStringSync(), 'HelloGoodbye');
+
+          assert(newFile.path != f.path);
+          expect(f, isNot(exists));
+          expect(newFile, exists);
+        });
+
+        group('ioSink', () {
+          late File f;
+          late IOSink sink;
+          late bool isSinkClosed;
+
+          Future<dynamic> closeSink() {
+            Future<dynamic> future = sink.close();
+            isSinkClosed = true;
+            return future;
+          }
+
+          setUp(() {
+            f = fs.file(ns('/foo'));
+            sink = f.openWrite();
+            isSinkClosed = false;
+          });
+
+          tearDown(() async {
+            if (!isSinkClosed) {
+              await closeSink();
+            }
+          });
+
+          test('throwsIfAddError', () async {
+            sink.addError(ArgumentError());
+            expect(sink.done, throwsArgumentError);
+            isSinkClosed = true;
+          });
+
+          test('allowsChangingEncoding', () async {
+            sink.encoding = latin1;
+            sink.write('ÿ');
+            sink.encoding = utf8;
+            sink.write('ÿ');
+            await sink.flush();
+            expect(await f.readAsBytes(), <int>[255, 195, 191]);
+          });
+
+          test('succeedsIfAddRawData', () async {
+            sink.add(<int>[1, 2, 3, 4]);
+            await sink.flush();
+            expect(await f.readAsBytes(), <int>[1, 2, 3, 4]);
+          });
+
+          test('succeedsIfWrite', () async {
+            sink.write('Hello world');
+            await sink.flush();
+            expect(await f.readAsString(), 'Hello world');
+          });
+
+          test('succeedsIfWriteAll', () async {
+            sink.writeAll(<String>['foo', 'bar', 'baz'], ' ');
+            await sink.flush();
+            expect(await f.readAsString(), 'foo bar baz');
+          });
+
+          test('succeedsIfWriteCharCode', () async {
+            sink.writeCharCode(35);
+            await sink.flush();
+            expect(await f.readAsString(), '#');
+          });
+
+          test('succeedsIfWriteln', () async {
+            sink.writeln('Hello world');
+            await sink.flush();
+            expect(await f.readAsString(), 'Hello world\n');
+          });
+
+          test('ignoresDataWrittenAfterClose', () async {
+            sink.write('Before close');
+            await closeSink();
+            expect(() => sink.write('After close'), throwsStateError);
+            expect(await f.readAsString(), 'Before close');
+          });
+
+          test('ignoresCloseAfterAlreadyClosed', () async {
+            sink.write('Hello world');
+            Future<dynamic> f1 = closeSink();
+            Future<dynamic> f2 = closeSink();
+            await Future.wait<dynamic>(<Future<dynamic>>[f1, f2]);
+          });
+
+          test('returnsAccurateDoneFuture', () async {
+            bool done = false;
+            // ignore: unawaited_futures
+            sink.done.then((dynamic _) => done = true);
+            expect(done, isFalse);
+            sink.write('foo');
+            expect(done, isFalse);
+            await sink.close();
+            expect(done, isTrue);
+          });
+
+          group('addStream', () {
+            late StreamController<List<int>> controller;
+            late bool isControllerClosed;
+
+            Future<dynamic> closeController() {
+              Future<dynamic> future = controller.close();
+              isControllerClosed = true;
+              return future;
+            }
+
+            setUp(() {
+              controller = StreamController<List<int>>();
+              isControllerClosed = false;
+              sink.addStream(controller.stream);
+            });
+
+            tearDown(() async {
+              if (!isControllerClosed) {
+                await closeController();
+              }
+            });
+
+            test('succeedsIfStreamProducesData', () async {
+              controller.add(<int>[1, 2, 3, 4, 5]);
+              await closeController();
+              await sink.flush();
+              expect(await f.readAsBytes(), <int>[1, 2, 3, 4, 5]);
+            });
+
+            test('blocksCallToAddWhileStreamIsActive', () {
+              expect(() => sink.add(<int>[1, 2, 3]), throwsStateError);
+            });
+
+            test('blocksCallToWriteWhileStreamIsActive', () {
+              expect(() => sink.write('foo'), throwsStateError);
+            });
+
+            test('blocksCallToWriteAllWhileStreamIsActive', () {
+              expect(() => sink.writeAll(<String>['a', 'b']), throwsStateError);
+            });
+
+            test('blocksCallToWriteCharCodeWhileStreamIsActive', () {
+              expect(() => sink.writeCharCode(35), throwsStateError);
+            });
+
+            test('blocksCallToWritelnWhileStreamIsActive', () {
+              expect(() => sink.writeln('foo'), throwsStateError);
+            });
+
+            test('blocksCallToFlushWhileStreamIsActive', () {
+              expect(() => sink.flush(), throwsStateError);
+            });
+          });
+        });
+      });
+
+      group('readAsBytes', () {
+        test('throwsIfDoesntExist', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.file(ns('/foo')).readAsBytesSync();
+          });
+        });
+
+        test('throwsIfExistsAsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/foo')).readAsBytesSync();
+          });
+        });
+
+        test('throwsIfExistsAsLinkToDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/bar')).readAsBytesSync();
+          });
+        });
+
+        test('succeedsIfExistsAsFile', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          f.writeAsBytesSync(<int>[1, 2, 3, 4]);
+          expect(f.readAsBytesSync(), <int>[1, 2, 3, 4]);
+        });
+
+        test('succeedsIfExistsAsLinkToFile', () {
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          fs.file(ns('/foo')).writeAsBytesSync(<int>[1, 2, 3, 4]);
+          expect(fs.file(ns('/bar')).readAsBytesSync(), <int>[1, 2, 3, 4]);
+        });
+
+        test('returnsEmptyListForZeroByteFile', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          expect(f.readAsBytesSync(), isEmpty);
+        });
+
+        test('returns a copy, not a view, of the file content', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          f.writeAsBytesSync(<int>[1, 2, 3, 4]);
+          List<int> result = f.readAsBytesSync();
+          expect(result, <int>[1, 2, 3, 4]);
+          result[0] = 10;
+          expect(f.readAsBytesSync(), <int>[1, 2, 3, 4]);
+        });
+      });
+
+      group('readAsString', () {
+        test('throwsIfDoesntExist', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.file(ns('/foo')).readAsStringSync();
+          });
+        });
+
+        test('throwsIfExistsAsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/foo')).readAsStringSync();
+          });
+        });
+
+        test('throwsIfExistsAsLinkToDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/bar')).readAsStringSync();
+          });
+        });
+
+        test('succeedsIfExistsAsFile', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          f.writeAsStringSync('Hello world');
+          expect(f.readAsStringSync(), 'Hello world');
+        });
+
+        test('succeedsIfExistsAsLinkToFile', () {
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          fs.file(ns('/foo')).writeAsStringSync('Hello world');
+          expect(fs.file(ns('/bar')).readAsStringSync(), 'Hello world');
+        });
+
+        test('returnsEmptyStringForZeroByteFile', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          expect(f.readAsStringSync(), isEmpty);
+        });
+      });
+
+      group('readAsLines', () {
+        const String testString = 'Hello world\nHow are you?\nI am fine';
+        final List<String> expectedLines = <String>[
+          'Hello world',
+          'How are you?',
+          'I am fine',
+        ];
+
+        test('throwsIfDoesntExist', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.file(ns('/foo')).readAsLinesSync();
+          });
+        });
+
+        test('throwsIfExistsAsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/foo')).readAsLinesSync();
+          });
+        });
+
+        test('throwsIfExistsAsLinkToDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/bar')).readAsLinesSync();
+          });
+        });
+
+        test('succeedsIfExistsAsFile', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          f.writeAsStringSync(testString);
+          expect(f.readAsLinesSync(), expectedLines);
+        });
+
+        test('succeedsIfExistsAsLinkToFile', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          f.writeAsStringSync(testString);
+          expect(f.readAsLinesSync(), expectedLines);
+        });
+
+        test('returnsEmptyListForZeroByteFile', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          expect(f.readAsLinesSync(), isEmpty);
+        });
+
+        test('isTrailingNewlineAgnostic', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          f.writeAsStringSync('$testString\n');
+          expect(f.readAsLinesSync(), expectedLines);
+
+          f.writeAsStringSync('\n');
+          expect(f.readAsLinesSync(), <String>['']);
+
+          f.writeAsStringSync('\n\n');
+          expect(f.readAsLinesSync(), <String>['', '']);
+        });
+      });
+
+      group('writeAsBytes', () {
+        test('returnsCovariantType', () async {
+          expect(await fs.file(ns('/foo')).writeAsBytes(<int>[]), isFile);
+        });
+
+        test('createsFileIfDoesntExist', () {
+          File f = fs.file(ns('/foo'));
+          expect(f, isNot(exists));
+          f.writeAsBytesSync(<int>[1, 2, 3, 4]);
+          expect(f, exists);
+        });
+
+        test('throwsIfExistsAsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/foo')).writeAsBytesSync(<int>[1, 2, 3, 4]);
+          });
+        });
+
+        test('throwsIfExistsAsLinkToDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/foo')).writeAsBytesSync(<int>[1, 2, 3, 4]);
+          });
+        });
+
+        test('succeedsIfExistsAsLinkToFile', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          fs.file(ns('/bar')).writeAsBytesSync(<int>[1, 2, 3, 4]);
+          expect(f.readAsBytesSync(), <int>[1, 2, 3, 4]);
+        });
+
+        test('throwsIfFileModeRead', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          expectFileSystemException(ErrorCodes.EBADF, () {
+            f.writeAsBytesSync(<int>[1], mode: FileMode.read);
+          });
+        });
+
+        test('overwritesContentIfFileModeWrite', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          f.writeAsBytesSync(<int>[1, 2]);
+          expect(f.readAsBytesSync(), <int>[1, 2]);
+          f.writeAsBytesSync(<int>[3, 4]);
+          expect(f.readAsBytesSync(), <int>[3, 4]);
+        });
+
+        test('appendsContentIfFileModeAppend', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          f.writeAsBytesSync(<int>[1, 2], mode: FileMode.append);
+          expect(f.readAsBytesSync(), <int>[1, 2]);
+          f.writeAsBytesSync(<int>[3, 4], mode: FileMode.append);
+          expect(f.readAsBytesSync(), <int>[1, 2, 3, 4]);
+        });
+
+        test('acceptsEmptyBytesList', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          f.writeAsBytesSync(<int>[]);
+          expect(f.readAsBytesSync(), <int>[]);
+        });
+
+        test('updatesLastModifiedTime', () async {
+          File f = fs.file(ns('/foo'))..createSync();
+          DateTime before = f.statSync().modified;
+          await Future<void>.delayed(const Duration(seconds: 2));
+          f.writeAsBytesSync(<int>[1, 2, 3]);
+          DateTime after = f.statSync().modified;
+          expect(after, isAfter(before));
+        });
+      });
+
+      group('writeAsString', () {
+        test('returnsCovariantType', () async {
+          expect(await fs.file(ns('/foo')).writeAsString('foo'), isFile);
+        });
+
+        test('createsFileIfDoesntExist', () {
+          File f = fs.file(ns('/foo'));
+          expect(f, isNot(exists));
+          f.writeAsStringSync('Hello world');
+          expect(f, exists);
+        });
+
+        test('throwsIfExistsAsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/foo')).writeAsStringSync('Hello world');
+          });
+        });
+
+        test('throwsIfExistsAsLinkToDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/foo')).writeAsStringSync('Hello world');
+          });
+        });
+
+        test('succeedsIfExistsAsLinkToFile', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          fs.file(ns('/bar')).writeAsStringSync('Hello world');
+          expect(f.readAsStringSync(), 'Hello world');
+        });
+
+        test('throwsIfFileModeRead', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          expectFileSystemException(ErrorCodes.EBADF, () {
+            f.writeAsStringSync('Hello world', mode: FileMode.read);
+          });
+        });
+
+        test('overwritesContentIfFileModeWrite', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          f.writeAsStringSync('Hello world');
+          expect(f.readAsStringSync(), 'Hello world');
+          f.writeAsStringSync('Goodbye cruel world');
+          expect(f.readAsStringSync(), 'Goodbye cruel world');
+        });
+
+        test('appendsContentIfFileModeAppend', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          f.writeAsStringSync('Hello', mode: FileMode.append);
+          expect(f.readAsStringSync(), 'Hello');
+          f.writeAsStringSync('Goodbye', mode: FileMode.append);
+          expect(f.readAsStringSync(), 'HelloGoodbye');
+        });
+
+        test('acceptsEmptyString', () {
+          File f = fs.file(ns('/foo'))..createSync();
+          f.writeAsStringSync('');
+          expect(f.readAsStringSync(), isEmpty);
+        });
+      });
+
+      group('exists', () {
+        test('trueIfExists', () {
+          fs.file(ns('/foo')).createSync();
+          expect(fs.file(ns('/foo')), exists);
+        });
+
+        test('falseIfDoesntExistAtTail', () {
+          expect(fs.file(ns('/foo')), isNot(exists));
+        });
+
+        test('falseIfDoesntExistViaTraversal', () {
+          expect(fs.file(ns('/foo/bar')), isNot(exists));
+        });
+
+        test('falseIfExistsAsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expect(fs.file(ns('/foo')), isNot(exists));
+        });
+
+        test('falseIfExistsAsLinkToDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expect(fs.file(ns('/bar')), isNot(exists));
+        });
+
+        test('trueIfExistsAsLinkToFile', () {
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expect(fs.file(ns('/bar')), exists);
+        });
+
+        test('falseIfNotFoundSegmentExistsThenIsBackedOut', () {
+          fs.file(ns('/foo/bar')).createSync(recursive: true);
+          expect(fs.directory(ns('/baz/../foo/bar')), isNot(exists));
+        });
+      });
+
+      group('stat', () {
+        test('isNotFoundIfDoesntExistAtTail', () {
+          FileStat stat = fs.file(ns('/foo')).statSync();
+          expect(stat.type, FileSystemEntityType.notFound);
+        });
+
+        test('isNotFoundIfDoesntExistViaTraversal', () {
+          FileStat stat = fs.file(ns('/foo/bar')).statSync();
+          expect(stat.type, FileSystemEntityType.notFound);
+        });
+
+        test('isDirectoryIfExistsAsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          FileStat stat = fs.file(ns('/foo')).statSync();
+          expect(stat.type, FileSystemEntityType.directory);
+        });
+
+        test('isFileIfExistsAsFile', () {
+          fs.file(ns('/foo')).createSync();
+          FileStat stat = fs.file(ns('/foo')).statSync();
+          expect(stat.type, FileSystemEntityType.file);
+        });
+
+        test('isFileIfExistsAsLinkToFile', () {
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          FileStat stat = fs.file(ns('/bar')).statSync();
+          expect(stat.type, FileSystemEntityType.file);
+        });
+      });
+
+      group('delete', () {
+        test('returnsCovariantType', () async {
+          File f = fs.file(ns('/foo'))..createSync();
+          expect(await f.delete(), isFile);
+        });
+
+        test('succeedsIfExistsAsFile', () {
+          fs.file(ns('/foo')).createSync();
+          expect(fs.file(ns('/foo')), exists);
+          fs.file(ns('/foo')).deleteSync();
+          expect(fs.file(ns('/foo')), isNot(exists));
+        });
+
+        test('throwsIfDoesntExistAndRecursiveFalse', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.file(ns('/foo')).deleteSync();
+          });
+        });
+
+        test('throwsIfDoesntExistAndRecursiveTrue', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.file(ns('/foo')).deleteSync(recursive: true);
+          });
+        });
+
+        test('succeedsIfExistsAsDirectoryAndRecursiveTrue', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.file(ns('/foo')).deleteSync(recursive: true);
+          expect(fs.typeSync(ns('/foo')), FileSystemEntityType.notFound);
+        });
+
+        test('throwsIfExistsAsDirectoryAndRecursiveFalse', () {
+          fs.directory(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/foo')).deleteSync();
+          });
+        });
+
+        test('succeedsIfExistsAsLinkToFileAndRecursiveTrue', () {
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expect(fs.file(ns('/bar')), exists);
+          fs.file(ns('/bar')).deleteSync(recursive: true);
+          expect(fs.file(ns('/bar')), isNot(exists));
+        });
+
+        test('succeedsIfExistsAsLinkToFileAndRecursiveFalse', () {
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expect(fs.file(ns('/bar')), exists);
+          fs.file(ns('/bar')).deleteSync();
+          expect(fs.file(ns('/bar')), isNot(exists));
+        });
+
+        test('succeedsIfExistsAsLinkToDirectoryAndRecursiveTrue', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expect(fs.typeSync(ns('/bar')), FileSystemEntityType.directory);
+          fs.file(ns('/bar')).deleteSync(recursive: true);
+          expect(fs.typeSync(ns('/foo')), FileSystemEntityType.directory);
+          expect(fs.typeSync(ns('/bar')), FileSystemEntityType.notFound);
+        });
+
+        test('throwsIfExistsAsLinkToDirectoryAndRecursiveFalse', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.file(ns('/bar')).deleteSync();
+          });
+        });
+      });
+    });
+
+    group('Link', () {
+      group('uri', () {
+        test('whenTargetIsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          Link l = fs.link(ns('/bar'))..createSync(ns('/foo'));
+          expect(l.uri, fs.path.toUri(ns('/bar')));
+          expect(fs.link('bar').uri.toString(), 'bar');
+        });
+
+        test('whenTargetIsFile', () {
+          fs.file(ns('/foo')).createSync();
+          Link l = fs.link(ns('/bar'))..createSync(ns('/foo'));
+          expect(l.uri, fs.path.toUri(ns('/bar')));
+          expect(fs.link('bar').uri.toString(), 'bar');
+        });
+
+        test('whenLinkDoesntExist', () {
+          expect(fs.link(ns('/foo')).uri, fs.path.toUri(ns('/foo')));
+          expect(fs.link('foo').uri.toString(), 'foo');
+        });
+      });
+
+      group('exists', () {
+        test('isFalseIfLinkDoesntExistAtTail', () {
+          expect(fs.link(ns('/foo')), isNot(exists));
+        });
+
+        test('isFalseIfLinkDoesntExistViaTraversal', () {
+          expect(fs.link(ns('/foo/bar')), isNot(exists));
+        });
+
+        test('isFalseIfPathReferencesFile', () {
+          fs.file(ns('/foo')).createSync();
+          expect(fs.link(ns('/foo')), isNot(exists));
+        });
+
+        test('isFalseIfPathReferencesDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expect(fs.link(ns('/foo')), isNot(exists));
+        });
+
+        test('isTrueIfTargetIsNotFound', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          expect(l, exists);
+        });
+
+        test('isTrueIfTargetIsFile', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.file(ns('/bar')).createSync();
+          expect(l, exists);
+        });
+
+        test('isTrueIfTargetIsDirectory', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.directory(ns('/bar')).createSync();
+          expect(l, exists);
+        });
+
+        test('isTrueIfTargetIsLinkLoop', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expect(l, exists);
+        });
+      });
+
+      group('stat', () {
+        test('isNotFoundIfLinkDoesntExistAtTail', () {
+          expect(fs.link(ns('/foo')).statSync().type,
+              FileSystemEntityType.notFound);
+        });
+
+        test('isNotFoundIfLinkDoesntExistViaTraversal', () {
+          expect(fs.link(ns('/foo/bar')).statSync().type,
+              FileSystemEntityType.notFound);
+        });
+
+        test('isFileIfPathReferencesFile', () {
+          fs.file(ns('/foo')).createSync();
+          expect(
+              fs.link(ns('/foo')).statSync().type, FileSystemEntityType.file);
+        });
+
+        test('isDirectoryIfPathReferencesDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expect(fs.link(ns('/foo')).statSync().type,
+              FileSystemEntityType.directory);
+        });
+
+        test('isNotFoundIfTargetNotFoundAtTail', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          expect(l.statSync().type, FileSystemEntityType.notFound);
+        });
+
+        test('isNotFoundIfTargetNotFoundViaTraversal', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar/baz'));
+          expect(l.statSync().type, FileSystemEntityType.notFound);
+        });
+
+        test('isNotFoundIfTargetIsLinkLoop', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expect(l.statSync().type, FileSystemEntityType.notFound);
+        });
+
+        test('isFileIfTargetIsFile', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.file(ns('/bar')).createSync();
+          expect(l.statSync().type, FileSystemEntityType.file);
+        });
+
+        test('isDirectoryIfTargetIsDirectory', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.directory(ns('/bar')).createSync();
+          expect(l.statSync().type, FileSystemEntityType.directory);
+        });
+      });
+
+      group('delete', () {
+        test('returnsCovariantType', () async {
+          Link link = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          expect(await link.delete(), isLink);
+        });
+
+        test('throwsIfLinkDoesntExistAtTail', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.link(ns('/foo')).deleteSync();
+          });
+        });
+
+        test('throwsIfLinkDoesntExistViaTraversal', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.link(ns('/foo/bar')).deleteSync();
+          });
+        });
+
+        test('throwsIfPathReferencesFileAndRecursiveFalse', () {
+          fs.file(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.EINVAL, () {
+            fs.link(ns('/foo')).deleteSync();
+          });
+        });
+
+        test('succeedsIfPathReferencesFileAndRecursiveTrue', () {
+          fs.file(ns('/foo')).createSync();
+          fs.link(ns('/foo')).deleteSync(recursive: true);
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.notFound);
+        });
+
+        test('throwsIfPathReferencesDirectoryAndRecursiveFalse', () {
+          fs.directory(ns('/foo')).createSync();
+          // TODO(tvolkert): Change this to just be 'Is a directory'
+          // once Dart 1.22 is stable.
+          expectFileSystemException(
+            anyOf(ErrorCodes.EINVAL, ErrorCodes.EISDIR),
+            () {
+              fs.link(ns('/foo')).deleteSync();
+            },
+          );
+        });
+
+        test('succeedsIfPathReferencesDirectoryAndRecursiveTrue', () {
+          fs.directory(ns('/foo')).createSync();
+          fs.link(ns('/foo')).deleteSync(recursive: true);
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.notFound);
+        });
+
+        test('unlinksIfTargetIsFileAndRecursiveFalse', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.file(ns('/bar')).createSync();
+          l.deleteSync();
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.notFound);
+          expect(fs.typeSync(ns('/bar'), followLinks: false),
+              FileSystemEntityType.file);
+        });
+
+        test('unlinksIfTargetIsFileAndRecursiveTrue', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.file(ns('/bar')).createSync();
+          l.deleteSync(recursive: true);
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.notFound);
+          expect(fs.typeSync(ns('/bar'), followLinks: false),
+              FileSystemEntityType.file);
+        });
+
+        test('unlinksIfTargetIsDirectoryAndRecursiveFalse', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.directory(ns('/bar')).createSync();
+          l.deleteSync();
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.notFound);
+          expect(fs.typeSync(ns('/bar'), followLinks: false),
+              FileSystemEntityType.directory);
+        });
+
+        test('unlinksIfTargetIsDirectoryAndRecursiveTrue', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.directory(ns('/bar')).createSync();
+          l.deleteSync(recursive: true);
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.notFound);
+          expect(fs.typeSync(ns('/bar'), followLinks: false),
+              FileSystemEntityType.directory);
+        });
+
+        test('unlinksIfTargetIsLinkLoop', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          l.deleteSync();
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.notFound);
+          expect(fs.typeSync(ns('/bar'), followLinks: false),
+              FileSystemEntityType.link);
+        });
+      });
+
+      group('parent', () {
+        test('returnsCovariantType', () {
+          expect(fs.link(ns('/foo')).parent, isDirectory);
+        });
+
+        test('succeedsIfLinkDoesntExist', () {
+          expect(fs.link(ns('/foo')).parent.path, ns('/'));
+        });
+
+        test('ignoresLinkTarget', () {
+          Link l = fs.link(ns('/foo/bar'))
+            ..createSync(ns('/baz/qux'), recursive: true);
+          expect(l.parent.path, ns('/foo'));
+        });
+      });
+
+      group('create', () {
+        test('returnsCovariantType', () async {
+          expect(await fs.link(ns('/foo')).create(ns('/bar')), isLink);
+        });
+
+        test('succeedsIfLinkDoesntExistAtTail', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(l.targetSync(), ns('/bar'));
+        });
+
+        test('throwsIfLinkDoesntExistViaTraversalAndRecursiveFalse', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.link(ns('/foo/bar')).createSync('baz');
+          });
+        });
+
+        test('succeedsIfLinkDoesntExistViaTraversalAndRecursiveTrue', () {
+          Link l = fs.link(ns('/foo/bar'))..createSync('baz', recursive: true);
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.directory);
+          expect(fs.typeSync(ns('/foo/bar'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(l.targetSync(), 'baz');
+        });
+
+        test('throwsIfAlreadyExistsAsFile', () {
+          fs.file(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.EEXIST, () {
+            fs.link(ns('/foo')).createSync(ns('/bar'));
+          });
+        });
+
+        test('throwsIfAlreadyExistsAsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.EEXIST, () {
+            fs.link(ns('/foo')).createSync(ns('/bar'));
+          });
+        });
+
+        test('throwsIfAlreadyExistsWithSameTarget', () {
+          fs.link(ns('/foo')).createSync(ns('/bar'));
+          expectFileSystemException(ErrorCodes.EEXIST, () {
+            fs.link(ns('/foo')).createSync(ns('/bar'));
+          });
+        });
+
+        test('throwsIfAlreadyExistsWithDifferentTarget', () {
+          fs.link(ns('/foo')).createSync(ns('/bar'));
+          expectFileSystemException(ErrorCodes.EEXIST, () {
+            fs.link(ns('/foo')).createSync(ns('/baz'));
+          });
+        });
+      });
+
+      group('update', () {
+        test('returnsCovariantType', () async {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          expect(await l.update(ns('/baz')), isLink);
+        });
+
+        test('throwsIfLinkDoesntExistAtTail', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.link(ns('/foo')).updateSync(ns('/bar'));
+          });
+        });
+
+        test('throwsIfLinkDoesntExistViaTraversal', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.link(ns('/foo/bar')).updateSync(ns('/baz'));
+          });
+        });
+
+        test('throwsIfPathReferencesFile', () {
+          fs.file(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.EINVAL, () {
+            fs.link(ns('/foo')).updateSync(ns('/bar'));
+          });
+        });
+
+        test('throwsIfPathReferencesDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          // TODO(tvolkert): Change this to just be 'Is a directory'
+          // once Dart 1.22 is stable.
+          expectFileSystemException(
+            anyOf(ErrorCodes.EINVAL, ErrorCodes.EISDIR),
+            () {
+              fs.link(ns('/foo')).updateSync(ns('/bar'));
+            },
+          );
+        });
+
+        test('succeedsIfNewTargetSameAsOldTarget', () {
+          fs.link(ns('/foo')).createSync(ns('/bar'));
+          fs.link(ns('/foo')).updateSync(ns('/bar'));
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(fs.link(ns('/foo')).targetSync(), ns('/bar'));
+        });
+
+        test('succeedsIfNewTargetDifferentFromOldTarget', () {
+          fs.link(ns('/foo')).createSync(ns('/bar'));
+          fs.link(ns('/foo')).updateSync(ns('/baz'));
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(fs.link(ns('/foo')).targetSync(), ns('/baz'));
+        });
+      });
+
+      group('absolute', () {
+        test('returnsCovariantType', () {
+          expect(fs.link('foo').absolute, isLink);
+        });
+
+        test('returnsSamePathIfAlreadyAbsolute', () {
+          expect(fs.link(ns('/foo')).absolute.path, ns('/foo'));
+        });
+
+        test('succeedsForRelativePaths', () {
+          expect(fs.link('foo').absolute.path, ns('/foo'));
+        });
+      });
+
+      group('target', () {
+        test('throwsIfLinkDoesntExistAtTail', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.link(ns('/foo')).targetSync();
+          });
+        });
+
+        test('throwsIfLinkDoesntExistViaTraversal', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.link(ns('/foo/bar')).targetSync();
+          });
+        });
+
+        test('throwsIfPathReferencesFile', () {
+          fs.file(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.link(ns('/foo')).targetSync();
+          });
+        });
+
+        test('throwsIfPathReferencesDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.link(ns('/foo')).targetSync();
+          });
+        });
+
+        test('succeedsIfTargetIsNotFound', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          expect(l.targetSync(), ns('/bar'));
+        });
+
+        test('succeedsIfTargetIsFile', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.file(ns('/bar')).createSync();
+          expect(l.targetSync(), ns('/bar'));
+        });
+
+        test('succeedsIfTargetIsDirectory', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.directory(ns('/bar')).createSync();
+          expect(l.targetSync(), ns('/bar'));
+        });
+
+        test('succeedsIfTargetIsLinkLoop', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          expect(l.targetSync(), ns('/bar'));
+        });
+      });
+
+      group('rename', () {
+        test('returnsCovariantType', () async {
+          Link l() => fs.link(ns('/foo'))..createSync(ns('/bar'));
+          expect(l().renameSync(ns('/bar')), isLink);
+          expect(await l().rename(ns('/bar')), isLink);
+        });
+
+        test('throwsIfSourceDoesntExistAtTail', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.link(ns('/foo')).renameSync(ns('/bar'));
+          });
+        });
+
+        test('throwsIfSourceDoesntExistViaTraversal', () {
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            fs.link(ns('/foo/bar')).renameSync(ns('/bar'));
+          });
+        });
+
+        test('throwsIfSourceIsFile', () {
+          fs.file(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.EINVAL, () {
+            fs.link(ns('/foo')).renameSync(ns('/bar'));
+          });
+        });
+
+        test('throwsIfSourceIsDirectory', () {
+          fs.directory(ns('/foo')).createSync();
+          expectFileSystemException(ErrorCodes.EISDIR, () {
+            fs.link(ns('/foo')).renameSync(ns('/bar'));
+          });
+        });
+
+        test('succeedsIfSourceIsLinkToFile', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.file(ns('/bar')).createSync();
+          Link renamed = l.renameSync(ns('/baz'));
+          expect(renamed.path, ns('/baz'));
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.notFound);
+          expect(fs.typeSync(ns('/bar'), followLinks: false),
+              FileSystemEntityType.file);
+          expect(fs.typeSync(ns('/baz'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(fs.link(ns('/baz')).targetSync(), ns('/bar'));
+        });
+
+        test('succeedsIfSourceIsLinkToNotFound', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          Link renamed = l.renameSync(ns('/baz'));
+          expect(renamed.path, ns('/baz'));
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.notFound);
+          expect(fs.typeSync(ns('/baz'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(fs.link(ns('/baz')).targetSync(), ns('/bar'));
+        });
+
+        test('succeedsIfSourceIsLinkToDirectory', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.directory(ns('/bar')).createSync();
+          Link renamed = l.renameSync(ns('/baz'));
+          expect(renamed.path, ns('/baz'));
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.notFound);
+          expect(fs.typeSync(ns('/bar'), followLinks: false),
+              FileSystemEntityType.directory);
+          expect(fs.typeSync(ns('/baz'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(fs.link(ns('/baz')).targetSync(), ns('/bar'));
+        });
+
+        test('succeedsIfSourceIsLinkLoop', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.link(ns('/bar')).createSync(ns('/foo'));
+          Link renamed = l.renameSync(ns('/baz'));
+          expect(renamed.path, ns('/baz'));
+          expect(fs.typeSync(ns('/foo'), followLinks: false),
+              FileSystemEntityType.notFound);
+          expect(fs.typeSync(ns('/bar'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(fs.typeSync(ns('/baz'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(fs.link(ns('/baz')).targetSync(), ns('/bar'));
+        });
+
+        test('succeedsIfDestinationDoesntExistAtTail', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          Link renamed = l.renameSync(ns('/baz'));
+          expect(renamed.path, ns('/baz'));
+          expect(fs.link(ns('/foo')), isNot(exists));
+          expect(fs.link(ns('/baz')), exists);
+        });
+
+        test('throwsIfDestinationDoesntExistViaTraversal', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          expectFileSystemException(ErrorCodes.ENOENT, () {
+            l.renameSync(ns('/baz/qux'));
+          });
+        });
+
+        test('throwsIfDestinationExistsAsFile', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.file(ns('/baz')).createSync();
+          expectFileSystemException(ErrorCodes.EINVAL, () {
+            l.renameSync(ns('/baz'));
+          });
+        });
+
+        test('throwsIfDestinationExistsAsDirectory', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.directory(ns('/baz')).createSync();
+          expectFileSystemException(ErrorCodes.EINVAL, () {
+            l.renameSync(ns('/baz'));
+          });
+        });
+
+        test('succeedsIfDestinationExistsAsLinkToFile', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.file(ns('/baz')).createSync();
+          fs.link(ns('/qux')).createSync(ns('/baz'));
+          l.renameSync(ns('/qux'));
+          expect(fs.typeSync(ns('/foo')), FileSystemEntityType.notFound);
+          expect(fs.typeSync(ns('/baz'), followLinks: false),
+              FileSystemEntityType.file);
+          expect(fs.typeSync(ns('/qux'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(fs.link(ns('/qux')).targetSync(), ns('/bar'));
+        });
+
+        test('throwsIfDestinationExistsAsLinkToDirectory', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.directory(ns('/baz')).createSync();
+          fs.link(ns('/qux')).createSync(ns('/baz'));
+          l.renameSync(ns('/qux'));
+          expect(fs.typeSync(ns('/foo')), FileSystemEntityType.notFound);
+          expect(fs.typeSync(ns('/baz'), followLinks: false),
+              FileSystemEntityType.directory);
+          expect(fs.typeSync(ns('/qux'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(fs.link(ns('/qux')).targetSync(), ns('/bar'));
+        });
+
+        test('succeedsIfDestinationExistsAsLinkToNotFound', () {
+          Link l = fs.link(ns('/foo'))..createSync(ns('/bar'));
+          fs.link(ns('/baz')).createSync(ns('/qux'));
+          l.renameSync(ns('/baz'));
+          expect(fs.typeSync(ns('/foo')), FileSystemEntityType.notFound);
+          expect(fs.typeSync(ns('/baz'), followLinks: false),
+              FileSystemEntityType.link);
+          expect(fs.link(ns('/baz')).targetSync(), ns('/bar'));
+        });
+      });
+    });
+  });
+}
diff --git a/pkgs/file/test/local_test.dart b/pkgs/file/test/local_test.dart
new file mode 100644
index 0000000..e1618d2
--- /dev/null
+++ b/pkgs/file/test/local_test.dart
@@ -0,0 +1,132 @@
+// Copyright (c) 2017, 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.
+
+@TestOn('vm')
+import 'dart:io' as io;
+
+import 'package:file/local.dart';
+import 'package:file_testing/src/testing/internal.dart';
+import 'package:test/test.dart';
+
+import 'common_tests.dart';
+
+void main() {
+  group('LocalFileSystem', () {
+    late LocalFileSystem fs;
+    late io.Directory tmp;
+    late String cwd;
+
+    setUp(() {
+      fs = const LocalFileSystem();
+      tmp = io.Directory.systemTemp.createTempSync('file_test_');
+      tmp = io.Directory(tmp.resolveSymbolicLinksSync());
+      cwd = io.Directory.current.path;
+      io.Directory.current = tmp;
+    });
+
+    tearDown(() {
+      io.Directory.current = cwd;
+      tmp.deleteSync(recursive: true);
+    });
+
+    setUpAll(() {
+      if (io.Platform.isWindows) {
+        // TODO(tvolkert): Remove once all more serious test failures are fixed
+        // https://github.com/google/file.dart/issues/56
+        ignoreOsErrorCodes = true;
+      }
+    });
+
+    tearDownAll(() {
+      ignoreOsErrorCodes = false;
+    });
+
+    Map<String, List<String>> skipOnPlatform = <String, List<String>>{
+      'windows': <String>[
+        'FileSystem > currentDirectory > throwsIfHasNonExistentPathInComplexChain',
+        'FileSystem > currentDirectory > resolvesLinksIfEncountered',
+        'FileSystem > currentDirectory > succeedsIfSetToDirectoryLinkAtTail',
+        'FileSystem > stat > isFileForLinkToFile',
+        'FileSystem > type > isFileForLinkToFileAndFollowLinksTrue',
+        'FileSystem > type > isNotFoundForLinkWithCircularReferenceAndFollowLinksTrue',
+        'Directory > exists > falseIfNotFoundSegmentExistsThenIsBackedOut',
+        'Directory > rename > throwsIfDestinationIsNonEmptyDirectory',
+        'Directory > rename > throwsIfDestinationIsLinkToEmptyDirectory',
+        'Directory > resolveSymbolicLinks > throwsIfPathNotFoundInMiddleThenBackedOut',
+        'Directory > resolveSymbolicLinks > handlesRelativeLinks',
+        'Directory > resolveSymbolicLinks > handlesLinksWhoseTargetsHaveNestedLinks',
+        'Directory > resolveSymbolicLinks > handlesComplexPathWithMultipleLinks',
+        'Directory > createTemp > succeedsWithNestedPathPrefixThatExists',
+        'Directory > list > followsLinksIfFollowLinksTrue',
+        'Directory > list > returnsCovariantType',
+        'Directory > list > returnsLinkObjectsForRecursiveLinkIfFollowLinksTrue',
+        'Directory > delete > succeedsIfPathReferencesLinkToFileAndRecursiveTrue',
+        'File > rename > succeedsIfSourceExistsAsLinkToFile',
+        'File > copy > succeedsIfSourceExistsAsLinkToFile',
+        'File > copy > succeedsIfSourceIsLinkToFileInDifferentDirectory',
+        'File > delete > succeedsIfExistsAsLinkToFileAndRecursiveTrue',
+        'File > openWrite > ioSink > throwsIfEncodingIsNullAndWriteObject',
+        'File > openWrite > ioSink > allowsChangingEncoding',
+        'File > openWrite > ioSink > succeedsIfAddRawData',
+        'File > openWrite > ioSink > succeedsIfWrite',
+        'File > openWrite > ioSink > succeedsIfWriteAll',
+        'File > openWrite > ioSink > succeedsIfWriteCharCode',
+        'File > openWrite > ioSink > succeedsIfWriteln',
+        'File > openWrite > ioSink > addStream > succeedsIfStreamProducesData',
+        'File > openWrite > ioSink > addStream > blocksCallToAddWhileStreamIsActive',
+        'File > openWrite > ioSink > addStream > blocksCallToWriteWhileStreamIsActive',
+        'File > openWrite > ioSink > addStream > blocksCallToWriteAllWhileStreamIsActive',
+        'File > openWrite > ioSink > addStream > blocksCallToWriteCharCodeWhileStreamIsActive',
+        'File > openWrite > ioSink > addStream > blocksCallToWritelnWhileStreamIsActive',
+        'File > openWrite > ioSink > addStream > blocksCallToFlushWhileStreamIsActive',
+        'File > stat > isFileIfExistsAsLinkToFile',
+        'Link > stat > isFileIfTargetIsFile',
+        'Link > stat > isDirectoryIfTargetIsDirectory',
+        'Link > delete > unlinksIfTargetIsDirectoryAndRecursiveTrue',
+        'Link > delete > unlinksIfTargetIsFileAndRecursiveTrue',
+
+        // Fixed in SDK 1.23 (https://github.com/dart-lang/sdk/issues/28852)
+        'File > open > WRITE > RandomAccessFile > truncate > throwsIfSetToNegativeNumber',
+        'File > open > APPEND > RandomAccessFile > truncate > throwsIfSetToNegativeNumber',
+        'File > open > WRITE_ONLY > RandomAccessFile > truncate > throwsIfSetToNegativeNumber',
+        'File > open > WRITE_ONLY_APPEND > RandomAccessFile > truncate > throwsIfSetToNegativeNumber',
+
+        // Windows does not allow removing or renaming open files.
+        '.* > openReadHandleDoesNotChange',
+        '.* > openWriteHandleDoesNotChange',
+      ],
+    };
+
+    runCommonTests(
+      () => fs,
+      root: () => tmp.path,
+      skip: <String>[
+        // https://github.com/dart-lang/sdk/issues/28171
+        'File > rename > throwsIfDestinationExistsAsLinkToDirectory',
+
+        // https://github.com/dart-lang/sdk/issues/28275
+        'Link > rename > throwsIfDestinationExistsAsDirectory',
+
+        // https://github.com/dart-lang/sdk/issues/28277
+        'Link > rename > throwsIfDestinationExistsAsFile',
+
+        ...skipOnPlatform[io.Platform.operatingSystem] ?? <String>[],
+      ],
+    );
+
+    group('toString', () {
+      test('File', () {
+        expect(fs.file('/foo').toString(), "LocalFile: '/foo'");
+      });
+
+      test('Directory', () {
+        expect(fs.directory('/foo').toString(), "LocalDirectory: '/foo'");
+      });
+
+      test('Link', () {
+        expect(fs.link('/foo').toString(), "LocalLink: '/foo'");
+      });
+    });
+  });
+}
diff --git a/pkgs/file/test/memory_operations_test.dart b/pkgs/file/test/memory_operations_test.dart
new file mode 100644
index 0000000..5e27843
--- /dev/null
+++ b/pkgs/file/test/memory_operations_test.dart
@@ -0,0 +1,231 @@
+// Copyright (c) 2017, 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.
+
+import 'package:file/file.dart';
+import 'package:file/memory.dart';
+import 'package:test/test.dart';
+
+void main() {
+  test('Read operations invoke opHandle', () async {
+    List<String> contexts = <String>[];
+    List<FileSystemOp> operations = <FileSystemOp>[];
+    MemoryFileSystem fs = MemoryFileSystem.test(
+        opHandle: (String context, FileSystemOp operation) {
+      if (operation == FileSystemOp.read) {
+        contexts.add(context);
+        operations.add(operation);
+      }
+    });
+    final File file = fs.file('test')..createSync();
+
+    await file.readAsBytes();
+    file.readAsBytesSync();
+    await file.readAsString();
+    file.readAsStringSync();
+
+    expect(contexts, <String>['test', 'test', 'test', 'test']);
+    expect(operations, <FileSystemOp>[
+      FileSystemOp.read,
+      FileSystemOp.read,
+      FileSystemOp.read,
+      FileSystemOp.read
+    ]);
+  });
+
+  test('Write operations invoke opHandle', () async {
+    List<String> contexts = <String>[];
+    List<FileSystemOp> operations = <FileSystemOp>[];
+    MemoryFileSystem fs = MemoryFileSystem.test(
+        opHandle: (String context, FileSystemOp operation) {
+      if (operation == FileSystemOp.write) {
+        contexts.add(context);
+        operations.add(operation);
+      }
+    });
+    final File file = fs.file('test')..createSync();
+
+    await file.writeAsBytes(<int>[]);
+    file.writeAsBytesSync(<int>[]);
+    await file.writeAsString('');
+    file.writeAsStringSync('');
+
+    expect(contexts, <String>['test', 'test', 'test', 'test']);
+    expect(operations, <FileSystemOp>[
+      FileSystemOp.write,
+      FileSystemOp.write,
+      FileSystemOp.write,
+      FileSystemOp.write
+    ]);
+  });
+
+  test('Delete operations invoke opHandle', () async {
+    List<String> contexts = <String>[];
+    List<FileSystemOp> operations = <FileSystemOp>[];
+    MemoryFileSystem fs = MemoryFileSystem.test(
+        opHandle: (String context, FileSystemOp operation) {
+      if (operation == FileSystemOp.delete) {
+        contexts.add(context);
+        operations.add(operation);
+      }
+    });
+    final File file = fs.file('test')..createSync();
+    final Directory directory = fs.directory('testDir')..createSync();
+    final Link link = fs.link('testLink')..createSync('foo');
+
+    await file.delete();
+    file.createSync();
+    file.deleteSync();
+
+    await directory.delete();
+    directory.createSync();
+    directory.deleteSync();
+
+    await link.delete();
+    link.createSync('foo');
+    link.deleteSync();
+
+    expect(contexts,
+        <String>['test', 'test', 'testDir', 'testDir', 'testLink', 'testLink']);
+    expect(operations, <FileSystemOp>[
+      FileSystemOp.delete,
+      FileSystemOp.delete,
+      FileSystemOp.delete,
+      FileSystemOp.delete,
+      FileSystemOp.delete,
+      FileSystemOp.delete,
+    ]);
+  });
+
+  test('Create operations invoke opHandle', () async {
+    List<String> contexts = <String>[];
+    List<FileSystemOp> operations = <FileSystemOp>[];
+    MemoryFileSystem fs = MemoryFileSystem.test(
+        opHandle: (String context, FileSystemOp operation) {
+      if (operation == FileSystemOp.create) {
+        contexts.add(context);
+        operations.add(operation);
+      }
+    });
+    fs.file('testA').createSync();
+    await fs.file('testB').create();
+    fs.directory('testDirA').createSync();
+    await fs.directory('testDirB').create();
+    fs.link('testLinkA').createSync('foo');
+    await fs.link('testLinkB').create('foo');
+    fs.currentDirectory.createTempSync('tmp.bar');
+    await fs.currentDirectory.createTemp('tmp.bar');
+
+    expect(contexts, <dynamic>[
+      'testA',
+      'testB',
+      'testDirA',
+      'testDirB',
+      'testLinkA',
+      'testLinkB',
+      startsWith('/tmp.bar'),
+      startsWith('/tmp.bar'),
+    ]);
+    expect(operations, <FileSystemOp>[
+      FileSystemOp.create,
+      FileSystemOp.create,
+      FileSystemOp.create,
+      FileSystemOp.create,
+      FileSystemOp.create,
+      FileSystemOp.create,
+      FileSystemOp.create,
+      FileSystemOp.create,
+    ]);
+  });
+
+  test('Open operations invoke opHandle', () async {
+    List<String> contexts = <String>[];
+    List<FileSystemOp> operations = <FileSystemOp>[];
+    MemoryFileSystem fs = MemoryFileSystem.test(
+        opHandle: (String context, FileSystemOp operation) {
+      if (operation == FileSystemOp.open) {
+        contexts.add(context);
+        operations.add(operation);
+      }
+    });
+    final File file = fs.file('test')..createSync();
+
+    await file.open();
+    file.openSync();
+    file.openRead();
+    file.openWrite();
+
+    expect(contexts, <String>['test', 'test', 'test', 'test']);
+    expect(operations, <FileSystemOp>[
+      FileSystemOp.open,
+      FileSystemOp.open,
+      FileSystemOp.open,
+      FileSystemOp.open,
+    ]);
+  });
+
+  test('Copy operations invoke opHandle', () async {
+    List<String> contexts = <String>[];
+    List<FileSystemOp> operations = <FileSystemOp>[];
+    MemoryFileSystem fs = MemoryFileSystem.test(
+        opHandle: (String context, FileSystemOp operation) {
+      if (operation == FileSystemOp.copy) {
+        contexts.add(context);
+        operations.add(operation);
+      }
+    });
+    final File file = fs.file('test')..createSync();
+
+    await file.copy('A');
+    file.copySync('B');
+
+    expect(contexts, <String>['test', 'test']);
+    expect(operations, <FileSystemOp>[
+      FileSystemOp.copy,
+      FileSystemOp.copy,
+    ]);
+  });
+
+  test('Exists operations invoke opHandle', () async {
+    List<String> contexts = <String>[];
+    List<FileSystemOp> operations = <FileSystemOp>[];
+    MemoryFileSystem fs = MemoryFileSystem.test(
+        opHandle: (String context, FileSystemOp operation) {
+      if (operation == FileSystemOp.exists) {
+        contexts.add(context);
+        operations.add(operation);
+      }
+    });
+    fs.file('testA').existsSync();
+    await fs.file('testB').exists();
+    fs.directory('testDirA').existsSync();
+    await fs.directory('testDirB').exists();
+    fs.link('testLinkA').existsSync();
+    await fs.link('testLinkB').exists();
+
+    expect(contexts, <dynamic>[
+      'testA',
+      'testB',
+      'testDirA',
+      'testDirB',
+      'testLinkA',
+      'testLinkB',
+    ]);
+    expect(operations, <FileSystemOp>[
+      FileSystemOp.exists,
+      FileSystemOp.exists,
+      FileSystemOp.exists,
+      FileSystemOp.exists,
+      FileSystemOp.exists,
+      FileSystemOp.exists,
+    ]);
+  });
+
+  test('FileSystemOp toString', () {
+    expect(FileSystemOp.create.toString(), 'FileSystemOp.create');
+    expect(FileSystemOp.delete.toString(), 'FileSystemOp.delete');
+    expect(FileSystemOp.read.toString(), 'FileSystemOp.read');
+    expect(FileSystemOp.write.toString(), 'FileSystemOp.write');
+    expect(FileSystemOp.exists.toString(), 'FileSystemOp.exists');
+  });
+}
diff --git a/pkgs/file/test/memory_test.dart b/pkgs/file/test/memory_test.dart
new file mode 100644
index 0000000..f3b324e
--- /dev/null
+++ b/pkgs/file/test/memory_test.dart
@@ -0,0 +1,173 @@
+// Copyright (c) 2017, 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.
+
+import 'dart:async';
+import 'dart:io' as io;
+
+import 'package:file/file.dart';
+import 'package:file/memory.dart';
+import 'package:file/src/backends/memory/memory_random_access_file.dart';
+import 'package:test/test.dart';
+
+import 'common_tests.dart';
+
+void main() {
+  group('MemoryFileSystem unix style', () {
+    late MemoryFileSystem fs;
+
+    setUp(() {
+      fs = MemoryFileSystem();
+    });
+
+    runCommonTests(() => fs);
+
+    group('toString', () {
+      test('File', () {
+        expect(fs.file('/foo').toString(), "MemoryFile: '/foo'");
+      });
+
+      test('Directory', () {
+        expect(fs.directory('/foo').toString(), "MemoryDirectory: '/foo'");
+      });
+
+      test('Link', () {
+        expect(fs.link('/foo').toString(), "MemoryLink: '/foo'");
+      });
+    });
+  });
+
+  group('MemoryFileSystem windows style', () {
+    late MemoryFileSystem fs;
+
+    setUp(() {
+      fs = MemoryFileSystem(style: FileSystemStyle.windows);
+    });
+
+    runCommonTests(
+      () => fs,
+      root: () => fs.style.root,
+    );
+
+    group('toString', () {
+      test('File', () {
+        expect(fs.file('C:\\foo').toString(), "MemoryFile: 'C:\\foo'");
+      });
+
+      test('Directory', () {
+        expect(
+            fs.directory('C:\\foo').toString(), "MemoryDirectory: 'C:\\foo'");
+      });
+
+      test('Link', () {
+        expect(fs.link('C:\\foo').toString(), "MemoryLink: 'C:\\foo'");
+      });
+    });
+  });
+
+  test('MemoryFileSystem.test', () {
+    final MemoryFileSystem fs =
+        MemoryFileSystem.test(); // creates root directory
+    fs.file('/test1.txt').createSync(); // creates file
+    fs.file('/test2.txt').createSync(); // creates file
+    expect(fs.directory('/').statSync().modified, DateTime(2000, 1, 1, 0, 1));
+    expect(
+        fs.file('/test1.txt').statSync().modified, DateTime(2000, 1, 1, 0, 2));
+    expect(
+        fs.file('/test2.txt').statSync().modified, DateTime(2000, 1, 1, 0, 3));
+    fs.file('/test1.txt').createSync();
+    fs.file('/test2.txt').createSync();
+    expect(fs.file('/test1.txt').statSync().modified,
+        DateTime(2000, 1, 1, 0, 2)); // file already existed
+    expect(fs.file('/test2.txt').statSync().modified,
+        DateTime(2000, 1, 1, 0, 3)); // file already existed
+    fs.file('/test1.txt').writeAsStringSync('test'); // touches file
+    expect(
+        fs.file('/test1.txt').statSync().modified, DateTime(2000, 1, 1, 0, 4));
+    expect(fs.file('/test2.txt').statSync().modified,
+        DateTime(2000, 1, 1, 0, 3)); // didn't touch it
+    fs.file('/test1.txt').copySync(
+        '/test2.txt'); // creates file, then mutates file (so time changes twice)
+    expect(fs.file('/test1.txt').statSync().modified,
+        DateTime(2000, 1, 1, 0, 4)); // didn't touch it
+    expect(
+        fs.file('/test2.txt').statSync().modified, DateTime(2000, 1, 1, 0, 6));
+  });
+
+  test('MemoryFile.openSync returns a MemoryRandomAccessFile', () async {
+    final MemoryFileSystem fs = MemoryFileSystem.test();
+    final io.File file = fs.file('/test1')..createSync();
+
+    io.RandomAccessFile raf = file.openSync();
+    try {
+      expect(raf, isA<MemoryRandomAccessFile>());
+    } finally {
+      raf.closeSync();
+    }
+
+    raf = await file.open();
+    try {
+      expect(raf, isA<MemoryRandomAccessFile>());
+    } finally {
+      raf.closeSync();
+    }
+  });
+
+  test('MemoryFileSystem.systemTempDirectory test', () {
+    final MemoryFileSystem fs = MemoryFileSystem.test();
+
+    final io.Directory fooA = fs.systemTempDirectory.createTempSync('foo');
+    final io.Directory fooB = fs.systemTempDirectory.createTempSync('foo');
+
+    expect(fooA.path, '/.tmp_rand0/foorand0');
+    expect(fooB.path, '/.tmp_rand0/foorand1');
+
+    final MemoryFileSystem secondFs = MemoryFileSystem.test();
+
+    final io.Directory fooAA =
+        secondFs.systemTempDirectory.createTempSync('foo');
+    final io.Directory fooBB =
+        secondFs.systemTempDirectory.createTempSync('foo');
+
+    // Names are recycled with a new instance
+    expect(fooAA.path, '/.tmp_rand0/foorand0');
+    expect(fooBB.path, '/.tmp_rand0/foorand1');
+  });
+
+  test('Failed UTF8 decoding in MemoryFileSystem throws a FileSystemException',
+      () {
+    final MemoryFileSystem fileSystem = MemoryFileSystem.test();
+    final File file = fileSystem.file('foo')
+      ..writeAsBytesSync(<int>[0xFFFE]); // Invalid UTF8
+
+    expect(file.readAsStringSync, throwsA(isA<FileSystemException>()));
+  });
+
+  test('Creating a temporary directory actually creates the directory', () {
+    final MemoryFileSystem fileSystem = MemoryFileSystem.test();
+    final Directory tempDir = fileSystem.currentDirectory.createTempSync('foo');
+
+    expect(tempDir.existsSync(), true);
+  });
+
+  test(
+      'addStream forwards error to returned future and file can still be '
+      'closed', () async {
+    final file = MemoryFileSystem.test().file('foo').openWrite();
+    await expectLater(file.addStream(Stream.error('bar')), throwsA('bar'));
+    await file.close();
+  });
+
+  test(
+      'addStream cancels on error and does not misbehave if the stream '
+      'produces multiple errors and then closes', () async {
+    final file = MemoryFileSystem.test().file('foo').openWrite();
+    final controller = StreamController<List<int>>()
+      ..addError('bar')
+      ..addError('baz');
+    final close = controller.close();
+    await expectLater(file.addStream(controller.stream), throwsA('bar'));
+    await file.close();
+    await close;
+  });
+}
diff --git a/pkgs/file/test/utils.dart b/pkgs/file/test/utils.dart
new file mode 100644
index 0000000..231312f
--- /dev/null
+++ b/pkgs/file/test/utils.dart
@@ -0,0 +1,117 @@
+// Copyright (c) 2017, 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.
+
+import 'package:meta/meta.dart';
+import 'package:test/test.dart';
+
+const Duration _oneSecond = Duration(seconds: 1);
+
+/// Returns a [DateTime] with an exact second-precision by removing the
+/// milliseconds and microseconds from the specified [time].
+///
+/// If [time] is not specified, it will default to the current time.
+DateTime floor([DateTime? time]) {
+  time ??= DateTime.now();
+  return time.subtract(Duration(
+    milliseconds: time.millisecond,
+    microseconds: time.microsecond,
+  ));
+}
+
+/// Returns a [DateTime] with an exact second precision, rounding up to the
+/// nearest second if necessary.
+///
+/// If [time] is not specified, it will default to the current time.
+DateTime ceil([DateTime? time]) {
+  time ??= DateTime.now();
+  int microseconds = (1000 * time.millisecond) + time.microsecond;
+  return (microseconds == 0)
+      ? time
+      // Add just enough milliseconds and microseconds to reach the next second.
+      : time.add(Duration(microseconds: 1000000 - microseconds));
+}
+
+/// Returns 1 second before the [floor] of the specified [DateTime].
+// TODO(jamesderlin): Remove this and use [floor], https://github.com/dart-lang/sdk/issues/42444
+DateTime downstairs([DateTime? time]) => floor(time).subtract(_oneSecond);
+
+/// Successfully matches against a [DateTime] that is the same moment or before
+/// the specified [time].
+Matcher isSameOrBefore(DateTime time) => _IsSameOrBefore(time);
+
+/// Successfully matches against a [DateTime] that is the same moment or after
+/// the specified [time].
+Matcher isSameOrAfter(DateTime time) => _IsSameOrAfter(time);
+
+/// Successfully matches against a [DateTime] that is after the specified
+/// [time].
+Matcher isAfter(DateTime time) => _IsAfter(time);
+
+abstract class _CompareDateTime extends Matcher {
+  const _CompareDateTime(this._time, this._matcher);
+
+  final DateTime _time;
+  final Matcher _matcher;
+
+  @override
+  bool matches(dynamic item, Map<dynamic, dynamic> matchState) {
+    return item is DateTime &&
+        _matcher.matches(item.compareTo(_time), <dynamic, dynamic>{});
+  }
+
+  @protected
+  String get descriptionOperator;
+
+  @override
+  Description describe(Description description) =>
+      description.add('a DateTime $descriptionOperator $_time');
+
+  @protected
+  String get mismatchAdjective;
+
+  @override
+  Description describeMismatch(
+    dynamic item,
+    Description description,
+    Map<dynamic, dynamic> matchState,
+    bool verbose,
+  ) {
+    if (item is DateTime) {
+      Duration diff = item.difference(_time).abs();
+      return description.add('is $mismatchAdjective $_time by $diff');
+    } else {
+      return description.add('is not a DateTime');
+    }
+  }
+}
+
+class _IsSameOrBefore extends _CompareDateTime {
+  const _IsSameOrBefore(DateTime time) : super(time, isNonPositive);
+
+  @override
+  String get descriptionOperator => '<=';
+
+  @override
+  String get mismatchAdjective => 'after';
+}
+
+class _IsSameOrAfter extends _CompareDateTime {
+  const _IsSameOrAfter(DateTime time) : super(time, isNonNegative);
+
+  @override
+  String get descriptionOperator => '>=';
+
+  @override
+  String get mismatchAdjective => 'before';
+}
+
+class _IsAfter extends _CompareDateTime {
+  const _IsAfter(DateTime time) : super(time, isPositive);
+
+  @override
+  String get descriptionOperator => '>';
+
+  @override
+  String get mismatchAdjective => 'before';
+}
diff --git a/pkgs/file/test/utils_test.dart b/pkgs/file/test/utils_test.dart
new file mode 100644
index 0000000..75293bf
--- /dev/null
+++ b/pkgs/file/test/utils_test.dart
@@ -0,0 +1,43 @@
+// Copyright (c) 2017, 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.
+
+import 'package:test/test.dart';
+
+import 'utils.dart';
+
+void main() {
+  test('floorAndCeilProduceExactSecondDateTime', () {
+    DateTime time = DateTime.fromMicrosecondsSinceEpoch(1001);
+    DateTime lower = floor(time);
+    DateTime upper = ceil(time);
+    expect(lower.millisecond, 0);
+    expect(upper.millisecond, 0);
+    expect(lower.microsecond, 0);
+    expect(upper.microsecond, 0);
+  });
+
+  test('floorAndCeilWorkWithNow', () {
+    DateTime time = DateTime.now();
+    int lower = time.difference(floor(time)).inMicroseconds;
+    int upper = ceil(time).difference(time).inMicroseconds;
+    expect(lower, lessThan(1000000));
+    expect(upper, lessThanOrEqualTo(1000000));
+  });
+
+  test('floorAndCeilWorkWithExactSecondDateTime', () {
+    DateTime time = DateTime.parse('1999-12-31 23:59:59');
+    DateTime lower = floor(time);
+    DateTime upper = ceil(time);
+    expect(lower, time);
+    expect(upper, time);
+  });
+
+  test('floorAndCeilWorkWithInexactSecondDateTime', () {
+    DateTime time = DateTime.parse('1999-12-31 23:59:59.500');
+    DateTime lower = floor(time);
+    DateTime upper = ceil(time);
+    Duration difference = upper.difference(lower);
+    expect(difference.inMicroseconds, 1000000);
+  });
+}
diff --git a/pkgs/file_testing/.gitignore b/pkgs/file_testing/.gitignore
new file mode 100644
index 0000000..ddfdca1
--- /dev/null
+++ b/pkgs/file_testing/.gitignore
@@ -0,0 +1,5 @@
+.dart_tool/
+.packages
+.pub/
+build/
+pubspec.lock
diff --git a/pkgs/file_testing/CHANGELOG.md b/pkgs/file_testing/CHANGELOG.md
new file mode 100644
index 0000000..0af779d
--- /dev/null
+++ b/pkgs/file_testing/CHANGELOG.md
@@ -0,0 +1,44 @@
+## 3.0.2
+
+* Require Dart 3.1.
+
+## 3.0.1
+
+* Update the pubspec repository field to reflect the new package repository.
+* Require Dart 3.0.
+
+## 3.0.0
+
+* Migrate to null safety.
+
+## 2.2.0
+
+* Change dependency on `package:test_api` back to `package:test`.
+
+## 2.1.0
+
+* Changed dependency on `package:test` to `package:test_api`
+* Bumped Dart SDK constraint to match `package:test_api`'s requirements
+* Updated style to match latest lint rules from Flutter repo.
+
+## 2.0.3
+
+* Relaxed constraints on `package:test`
+
+## 2.0.2
+
+* Bumped dependency on `package:test` to version 1.0
+
+## 2.0.1
+
+* Bumped Dart SDK constraint to allow for Dart 2 stable
+
+## 2.0.0
+
+* Removed `record_replay_matchers.dart` from API
+
+## 1.0.0
+
+* Moved `package:file/testing.dart` library into a dedicated package so that
+  libraries don't need to take on a transitive dependency on `package:test`
+  in order to use `package:file`.
diff --git a/pkgs/file_testing/LICENSE b/pkgs/file_testing/LICENSE
new file mode 100644
index 0000000..076334f
--- /dev/null
+++ b/pkgs/file_testing/LICENSE
@@ -0,0 +1,26 @@
+Copyright 2017, the Dart project authors. All rights reserved.
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+    * Redistributions of source code must retain the above copyright
+      notice, this list of conditions and the following disclaimer.
+    * Redistributions in binary form must reproduce the above
+      copyright notice, this list of conditions and the following
+      disclaimer in the documentation and/or other materials provided
+      with the distribution.
+    * Neither the name of Google Inc. nor the names of its
+      contributors may be used to endorse or promote products derived
+      from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
\ No newline at end of file
diff --git a/pkgs/file_testing/README.md b/pkgs/file_testing/README.md
new file mode 100644
index 0000000..7dda57e
--- /dev/null
+++ b/pkgs/file_testing/README.md
@@ -0,0 +1,39 @@
+[![pub package](https://img.shields.io/pub/v/file_testing.svg)](https://pub.dev/packages/file_testing)
+[![package publisher](https://img.shields.io/pub/publisher/file_testing.svg)](https://pub.dev/packages/file_testing/publisher)
+
+Testing utilities intended to work with `package:file`.
+
+## Features
+
+This package provides a series of matchers to be used in tests that work with file
+system types.
+
+## Usage
+
+```dart
+import 'package:file/file.dart';
+import 'package:file/memory.dart';
+import 'package:file_testing/file_testing.dart';
+import 'package:test/test.dart';
+
+void main() {
+  MemoryFileSystem fs;
+
+  setUp(() {
+    fs = MemoryFileSystem();
+    fs.file('/foo').createSync();
+  });
+
+  test('some test', () {
+    expectFileSystemException(
+      ErrorCodes.ENOENT,
+      () {
+        fs.directory('').resolveSymbolicLinksSync();
+      },
+    );
+    expect(fs.file('/path/to/file'), isFile);
+    expect(fs.file('/path/to/directory'), isDirectory);
+    expect(fs.file('/foo'), exists);
+  });
+}
+```
diff --git a/pkgs/file_testing/analysis_options.yaml b/pkgs/file_testing/analysis_options.yaml
new file mode 100644
index 0000000..8fbd2e4
--- /dev/null
+++ b/pkgs/file_testing/analysis_options.yaml
@@ -0,0 +1,6 @@
+include: package:lints/recommended.yaml
+
+analyzer:
+  errors:
+    # Allow having TODOs in the code
+    todo: ignore
diff --git a/pkgs/file_testing/lib/file_testing.dart b/pkgs/file_testing/lib/file_testing.dart
new file mode 100644
index 0000000..2ac2d0a
--- /dev/null
+++ b/pkgs/file_testing/lib/file_testing.dart
@@ -0,0 +1,8 @@
+// Copyright (c) 2017, 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.
+
+/// Matchers (from `package:test`) for use in tests that deal with file systems.
+library;
+
+export 'src/testing/core_matchers.dart';
diff --git a/pkgs/file_testing/lib/src/testing/core_matchers.dart b/pkgs/file_testing/lib/src/testing/core_matchers.dart
new file mode 100644
index 0000000..f58539f
--- /dev/null
+++ b/pkgs/file_testing/lib/src/testing/core_matchers.dart
@@ -0,0 +1,155 @@
+// Copyright (c) 2017, 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.
+
+import 'dart:io';
+
+import 'package:test/test.dart';
+
+import 'internal.dart';
+
+/// Matcher that successfully matches against any instance of [Directory].
+const Matcher isDirectory = TypeMatcher<Directory>();
+
+/// Matcher that successfully matches against any instance of [File].
+const Matcher isFile = TypeMatcher<File>();
+
+/// Matcher that successfully matches against any instance of [Link].
+const Matcher isLink = TypeMatcher<Link>();
+
+/// Matcher that successfully matches against any instance of
+/// [FileSystemEntity].
+const Matcher isFileSystemEntity = TypeMatcher<FileSystemEntity>();
+
+/// Matcher that successfully matches against any instance of [FileStat].
+const Matcher isFileStat = TypeMatcher<FileStat>();
+
+/// Returns a [Matcher] that matches [path] against an entity's path.
+///
+/// [path] may be a String, a predicate function, or a [Matcher]. If it is
+/// a String, it will be wrapped in an equality matcher.
+Matcher hasPath(dynamic path) => _HasPath(path);
+
+/// Returns a [Matcher] that successfully matches against an instance of
+/// [FileSystemException].
+///
+/// If [osErrorCode] is specified, matches will be limited to exceptions whose
+/// `osError.errorCode` also match the specified matcher.
+///
+/// [osErrorCode] may be an `int`, a predicate function, or a [Matcher]. If it
+/// is an `int`, it will be wrapped in an equality matcher.
+Matcher isFileSystemException([dynamic osErrorCode]) =>
+    _FileSystemException(osErrorCode);
+
+/// Returns a matcher that successfully matches against a future or function
+/// that throws a [FileSystemException].
+///
+/// If [osErrorCode] is specified, matches will be limited to exceptions whose
+/// `osError.errorCode` also match the specified matcher.
+///
+/// [osErrorCode] may be an `int`, a predicate function, or a [Matcher]. If it
+/// is an `int`, it will be wrapped in an equality matcher.
+Matcher throwsFileSystemException([dynamic osErrorCode]) =>
+    throwsA(isFileSystemException(osErrorCode));
+
+/// Expects the specified [callback] to throw a [FileSystemException] with the
+/// specified [osErrorCode] (matched against the exception's
+/// `osError.errorCode`).
+///
+/// [osErrorCode] may be an `int`, a predicate function, or a [Matcher]. If it
+/// is an `int`, it will be wrapped in an equality matcher.
+///
+/// See also:
+///   - [ErrorCodes]
+void expectFileSystemException(dynamic osErrorCode, void Function() callback) {
+  expect(callback, throwsFileSystemException(osErrorCode));
+}
+
+/// Matcher that successfully matches against a [FileSystemEntity] that
+/// exists ([FileSystemEntity.existsSync] returns true).
+const Matcher exists = _Exists();
+
+class _FileSystemException extends Matcher {
+  _FileSystemException(dynamic osErrorCode)
+      : _matcher = _wrapMatcher(osErrorCode);
+
+  final Matcher? _matcher;
+
+  static Matcher? _wrapMatcher(dynamic osErrorCode) {
+    if (osErrorCode == null) {
+      return null;
+    }
+    return ignoreOsErrorCodes ? anything : wrapMatcher(osErrorCode);
+  }
+
+  @override
+  bool matches(dynamic item, Map<dynamic, dynamic> matchState) {
+    if (item is FileSystemException) {
+      return _matcher == null ||
+          _matcher!.matches(item.osError?.errorCode, matchState);
+    }
+    return false;
+  }
+
+  @override
+  Description describe(Description desc) {
+    if (_matcher == null) {
+      return desc.add('FileSystemException');
+    } else {
+      desc.add('FileSystemException with osError.errorCode: ');
+      return _matcher!.describe(desc);
+    }
+  }
+}
+
+class _HasPath extends Matcher {
+  _HasPath(dynamic path) : _matcher = wrapMatcher(path);
+
+  final Matcher _matcher;
+
+  @override
+  bool matches(dynamic item, Map<dynamic, dynamic> matchState) =>
+      _matcher.matches(item.path, matchState);
+
+  @override
+  Description describe(Description desc) {
+    desc.add('has path: ');
+    return _matcher.describe(desc);
+  }
+
+  @override
+  Description describeMismatch(
+    dynamic item,
+    Description desc,
+    Map<dynamic, dynamic> matchState,
+    bool verbose,
+  ) {
+    desc.add('has path: \'${item.path}\'').add('\n   Which: ');
+    final Description pathDesc = StringDescription();
+    _matcher.describeMismatch(item.path, pathDesc, matchState, verbose);
+    desc.add(pathDesc.toString());
+    return desc;
+  }
+}
+
+class _Exists extends Matcher {
+  const _Exists();
+
+  @override
+  bool matches(dynamic item, Map<dynamic, dynamic> matchState) =>
+      item is FileSystemEntity && item.existsSync();
+
+  @override
+  Description describe(Description description) =>
+      description.add('a file system entity that exists');
+
+  @override
+  Description describeMismatch(
+    dynamic item,
+    Description description,
+    Map<dynamic, dynamic> matchState,
+    bool verbose,
+  ) {
+    return description.add('does not exist');
+  }
+}
diff --git a/pkgs/file_testing/lib/src/testing/internal.dart b/pkgs/file_testing/lib/src/testing/internal.dart
new file mode 100644
index 0000000..8f53a65
--- /dev/null
+++ b/pkgs/file_testing/lib/src/testing/internal.dart
@@ -0,0 +1,6 @@
+// Copyright (c) 2017, 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.
+
+/// True if we should ignore OS error codes in our matchers.
+bool ignoreOsErrorCodes = false;
diff --git a/pkgs/file_testing/pubspec.yaml b/pkgs/file_testing/pubspec.yaml
new file mode 100644
index 0000000..1dd0396
--- /dev/null
+++ b/pkgs/file_testing/pubspec.yaml
@@ -0,0 +1,13 @@
+name: file_testing
+version: 3.0.2
+description: Testing utilities for package:file.
+repository: https://github.com/dart-lang/tools/tree/main/pkgs/file_testing
+
+environment:
+  sdk: ^3.1.0
+
+dependencies:
+  test: ^1.23.1
+
+dev_dependencies: 
+  lints: ^5.0.0
diff --git a/pkgs/graphs/.gitignore b/pkgs/graphs/.gitignore
new file mode 100644
index 0000000..ddfdca1
--- /dev/null
+++ b/pkgs/graphs/.gitignore
@@ -0,0 +1,5 @@
+.dart_tool/
+.packages
+.pub/
+build/
+pubspec.lock
diff --git a/pkgs/graphs/CHANGELOG.md b/pkgs/graphs/CHANGELOG.md
new file mode 100644
index 0000000..7213b5a
--- /dev/null
+++ b/pkgs/graphs/CHANGELOG.md
@@ -0,0 +1,77 @@
+## 2.3.3-wip
+
+- Add an example usage to the README.
+
+## 2.3.2
+
+- Require Dart 3.4
+- Update to the latest version of `package:dart_flutter_team_lints`.
+
+## 2.3.1
+
+- Update package repository after move.
+
+## 2.3.0
+
+- Add a `transitiveClosure` function.
+- Make `stronglyConnectedComponents` and `topologicalSort` iterative rather than
+  recursive to avoid stack overflows on very large graphs.
+- Require Dart 2.18
+
+## 2.2.0
+
+- Add a `secondarySort` parameter to the `topologicalSort()` function which
+  applies an additional lexical sort where that doesn't break the topological
+  sort.
+
+## 2.1.0
+
+- Add a `topologicalSort()` function.
+
+## 2.0.0
+
+- **Breaking**: `crawlAsync` will no longer ignore a node from the graph if the
+  `readNode` callback returns null.
+
+## 1.0.0
+
+- Migrate to null safety.
+- **Breaking**: Paths from `shortestPath[s]` are now returned as iterables to
+  reduce memory consumption of the algorithm to O(n).
+
+## 0.2.0
+
+- **BREAKING** `shortestPath`, `shortestPaths` and `stronglyConnectedComponents`
+  now have one generic parameter and have replaced the `key` parameter with
+  optional params: `{bool equals(T key1, T key2), int hashCode(T key)}`.
+  This follows the pattern used in `dart:collection` classes `HashMap` and 
+  `LinkedHashMap`. It improves the usability and performance of the case where
+  the source values are directly usable in a hash data structure.
+
+## 0.1.3+1
+
+- Fixed a bug with non-identity `key` in `shortestPath` and `shortestPaths`.
+
+## 0.1.3
+
+- Added `shortestPath` and `shortestPaths` functions.
+- Use `HashMap` and `HashSet` from `dart:collection` for
+  `stronglyConnectedComponents`. Improves runtime performance.
+
+## 0.1.2+1
+
+- Allow using non-dev Dart 2 SDK.
+
+## 0.1.2
+
+- `crawlAsync` surfaces exceptions while crawling through the result stream
+  rather than as uncaught asynchronous errors.
+
+## 0.1.1
+
+- `crawlAsync` will now ignore nodes that are resolved to `null`.
+
+## 0.1.0
+
+- Initial release with an implementation of `stronglyConnectedComponents` and
+  `crawlAsync`.
diff --git a/pkgs/graphs/LICENSE b/pkgs/graphs/LICENSE
new file mode 100644
index 0000000..03af64a
--- /dev/null
+++ b/pkgs/graphs/LICENSE
@@ -0,0 +1,27 @@
+Copyright 2017, the Dart project authors. 
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+    * Redistributions of source code must retain the above copyright
+      notice, this list of conditions and the following disclaimer.
+    * Redistributions in binary form must reproduce the above
+      copyright notice, this list of conditions and the following
+      disclaimer in the documentation and/or other materials provided
+      with the distribution.
+    * Neither the name of Google LLC nor the names of its
+      contributors may be used to endorse or promote products derived
+      from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
diff --git a/pkgs/graphs/README.md b/pkgs/graphs/README.md
new file mode 100644
index 0000000..09512b8
--- /dev/null
+++ b/pkgs/graphs/README.md
@@ -0,0 +1,57 @@
+[![CI](https://github.com/dart-lang/tools/actions/workflows/graphs.yml/badge.svg)](https://github.com/dart-lang/tools/actions/workflows/graphs.yml)
+[![pub package](https://img.shields.io/pub/v/graphs.svg)](https://pub.dev/packages/graphs)
+[![package publisher](https://img.shields.io/pub/publisher/graphs.svg)](https://pub.dev/packages/graphs/publisher)
+
+Graph algorithms that do not specify a particular approach for representing a
+Graph.
+
+Each algorithm is a top level function which takes callback arguments that
+provide the mechanism for traversing the graph. For example, two common
+approaches for representing a graph:
+
+```dart
+class AdjacencyListGraph<T> {
+  Map<T, List<T>> nodes;
+  // ...
+}
+```
+
+```dart
+class TreeGraph<T> {
+  Node<T> root;
+  // ...
+}
+class Node<T> {
+  List<Node<T>> edges;
+  T value;
+}
+```
+
+Any representation can be adapted to the callback arguments.
+
+- Algorithms which need to traverse the graph take an `edges` callback which
+  provides the immediate neighbors of a given node.
+- Algorithms which need to associate unique data with each node in the graph
+  allow passing `equals` and/or `hashCode` callbacks if the unique data type
+  does not correctly or efficiently implement `operator==` or `get hashCode`.
+
+
+Algorithms that support graphs which are resolved asynchronously will have
+similar callbacks which return `FutureOr`.
+
+```dart
+import 'package:graphs/graphs.dart';
+
+void sendMessage() {
+  final network = AdjacencyListGraph();
+  // ...
+  final route = shortestPath(
+      sender, receiver, (node) => network.nodes[node] ?? const []);
+}
+
+void resolveBuildOrder() {
+  final dependencies = TreeGraph();
+  // ...
+  final buildOrder = topologicalSort([dependencies.root], (node) => node.edges);
+}
+```
diff --git a/pkgs/graphs/analysis_options.yaml b/pkgs/graphs/analysis_options.yaml
new file mode 100644
index 0000000..19437b4
--- /dev/null
+++ b/pkgs/graphs/analysis_options.yaml
@@ -0,0 +1,36 @@
+# https://dart.dev/guides/language/analysis-options
+include: package:dart_flutter_team_lints/analysis_options.yaml
+
+analyzer:
+  language:
+    strict-raw-types: true
+  errors:
+    sort_pub_dependencies: ignore
+    # https://github.com/dart-lang/sdk/issues/56465
+    unintended_html_in_doc_comment: ignore
+
+linter:
+  rules:
+    - avoid_bool_literals_in_conditional_expressions
+    - avoid_classes_with_only_static_members
+    - avoid_private_typedef_functions
+    - avoid_redundant_argument_values
+    - avoid_returning_this
+    - avoid_unused_constructor_parameters
+    - avoid_void_async
+    - cancel_subscriptions
+    - join_return_with_assignment
+    - literal_only_boolean_expressions
+    - missing_whitespace_between_adjacent_strings
+    - no_adjacent_strings_in_list
+    - no_runtimeType_toString
+    - package_api_docs
+    - prefer_const_declarations
+    - prefer_expression_function_bodies
+    - prefer_final_locals
+    - require_trailing_commas
+    - unnecessary_await_in_return
+    - unnecessary_raw_strings
+    - use_if_null_to_convert_nulls_to_bools
+    - use_raw_strings
+    - use_string_buffers
diff --git a/pkgs/graphs/benchmark/connected_components_benchmark.dart b/pkgs/graphs/benchmark/connected_components_benchmark.dart
new file mode 100644
index 0000000..1f71879
--- /dev/null
+++ b/pkgs/graphs/benchmark/connected_components_benchmark.dart
@@ -0,0 +1,50 @@
+// Copyright (c) 2018, 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.
+
+import 'dart:collection';
+import 'dart:math' show Random;
+
+import 'package:graphs/graphs.dart';
+
+void main() {
+  final rnd = Random(0);
+  const size = 2000;
+  final graph = HashMap<int, List<int>>();
+
+  for (var i = 0; i < size * 3; i++) {
+    final toList = graph.putIfAbsent(rnd.nextInt(size), () => <int>[]);
+
+    final toValue = rnd.nextInt(size);
+    if (!toList.contains(toValue)) {
+      toList.add(toValue);
+    }
+  }
+
+  var maxCount = 0;
+  var maxIteration = 0;
+
+  const duration = Duration(milliseconds: 100);
+
+  for (var i = 1;; i++) {
+    var count = 0;
+    final watch = Stopwatch()..start();
+    while (watch.elapsed < duration) {
+      count++;
+      final length =
+          stronglyConnectedComponents(graph.keys, (e) => graph[e] ?? <Never>[])
+              .length;
+      assert(length == 244, '$length');
+    }
+
+    if (count > maxCount) {
+      maxCount = count;
+      maxIteration = i;
+    }
+
+    if (maxIteration == i || (i - maxIteration) % 20 == 0) {
+      print('max iterations in ${duration.inMilliseconds}ms: $maxCount\t'
+          'after $maxIteration of $i iterations');
+    }
+  }
+}
diff --git a/pkgs/graphs/benchmark/shortest_path_benchmark.dart b/pkgs/graphs/benchmark/shortest_path_benchmark.dart
new file mode 100644
index 0000000..67e7367
--- /dev/null
+++ b/pkgs/graphs/benchmark/shortest_path_benchmark.dart
@@ -0,0 +1,54 @@
+// Copyright (c) 2018, 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.
+
+import 'dart:collection';
+import 'dart:math' show Random;
+
+import 'package:graphs/graphs.dart';
+
+void main() {
+  final rnd = Random(1);
+  const size = 1000;
+  final graph = HashMap<int, List<int>>();
+
+  for (var i = 0; i < size * 5; i++) {
+    final toList = graph.putIfAbsent(rnd.nextInt(size), () => <int>[]);
+
+    final toValue = rnd.nextInt(size);
+    if (!toList.contains(toValue)) {
+      toList.add(toValue);
+    }
+  }
+
+  int? minTicks;
+  var maxIteration = 0;
+
+  final testOutput =
+      shortestPath(0, size - 1, (e) => graph[e] ?? <Never>[]).toString();
+  print(testOutput);
+  assert(testOutput == '(258, 252, 819, 999)', testOutput);
+
+  final watch = Stopwatch();
+  for (var i = 1;; i++) {
+    watch
+      ..reset()
+      ..start();
+    final result = shortestPath(0, size - 1, (e) => graph[e] ?? <Never>[])!;
+    final length = result.length;
+    final first = result.first;
+    watch.stop();
+    assert(length == 4, '$length');
+    assert(first == 258, '$first');
+
+    if (minTicks == null || watch.elapsedTicks < minTicks) {
+      minTicks = watch.elapsedTicks;
+      maxIteration = i;
+    }
+
+    if (maxIteration == i || (i - maxIteration) % 100000 == 0) {
+      print('min ticks for one run: $minTicks\t'
+          'after $maxIteration of $i iterations');
+    }
+  }
+}
diff --git a/pkgs/graphs/benchmark/shortest_path_worst_case_benchmark.dart b/pkgs/graphs/benchmark/shortest_path_worst_case_benchmark.dart
new file mode 100644
index 0000000..d3117ac
--- /dev/null
+++ b/pkgs/graphs/benchmark/shortest_path_worst_case_benchmark.dart
@@ -0,0 +1,58 @@
+// Copyright (c) 2020, 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.
+
+import 'dart:collection';
+
+import 'package:graphs/graphs.dart';
+
+void main() {
+  const size = 1000;
+  final graph = HashMap<int, List<int>>();
+
+  // We create a graph where every subsequent node has an edge to every other
+  // node before it as well as the next node. This triggers worst case behavior
+  // in many algorithms as it requires visiting all nodes and edges before
+  // finding a solution, and there are a maximum number of edges.
+  for (var i = 0; i < size; i++) {
+    final toList = graph.putIfAbsent(i, () => <int>[]);
+    for (var t = 0; t < i + 2 && i < size; t++) {
+      if (i == t) continue;
+      toList.add(t);
+    }
+  }
+
+  int? minTicks;
+  var maxIteration = 0;
+
+  final testOutput =
+      shortestPath(0, size - 1, (e) => graph[e] ?? <Never>[]).toString();
+  print(testOutput);
+  assert(
+    testOutput == Iterable.generate(size - 1, (i) => i + 1).toString(),
+    testOutput,
+  );
+
+  final watch = Stopwatch();
+  for (var i = 1;; i++) {
+    watch
+      ..reset()
+      ..start();
+    final result = shortestPath(0, size - 1, (e) => graph[e] ?? <Never>[])!;
+    final length = result.length;
+    final first = result.first;
+    watch.stop();
+    assert(length == 999, '$length');
+    assert(first == 1, '$first');
+
+    if (minTicks == null || watch.elapsedTicks < minTicks) {
+      minTicks = watch.elapsedTicks;
+      maxIteration = i;
+    }
+
+    if (maxIteration == i || (i - maxIteration) % 100000 == 0) {
+      print('min ticks for one run: $minTicks\t'
+          'after $maxIteration of $i iterations');
+    }
+  }
+}
diff --git a/pkgs/graphs/example/crawl_async_example.dart b/pkgs/graphs/example/crawl_async_example.dart
new file mode 100644
index 0000000..bd305c9
--- /dev/null
+++ b/pkgs/graphs/example/crawl_async_example.dart
@@ -0,0 +1,84 @@
+// Copyright (c) 2017, 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.
+
+import 'dart:async';
+import 'dart:isolate';
+
+import 'package:analyzer/dart/analysis/analysis_context_collection.dart';
+import 'package:analyzer/dart/analysis/results.dart';
+import 'package:analyzer/dart/ast/ast.dart';
+import 'package:graphs/graphs.dart';
+import 'package:path/path.dart' as p;
+import 'package:pool/pool.dart';
+
+/// Print a transitive set of imported URIs where libraries are read
+/// asynchronously.
+Future<void> main() async {
+  // Limits calls to [findImports].
+  final pool = Pool(10);
+  final allImports = await crawlAsync<Uri, Source>(
+    [Uri.parse('package:graphs/graphs.dart')],
+    read,
+    (from, source) => pool.withResource(() => findImports(from, source)),
+  ).toList();
+  print(allImports.map((s) => s.uri).toList());
+}
+
+AnalysisContextCollection? _analysisContextCollection;
+
+Future<AnalysisContextCollection> get analysisContextCollection async {
+  var collection = _analysisContextCollection;
+  if (collection == null) {
+    final libUri = Uri.parse('package:graphs/');
+    final libPath = await pathForUri(libUri);
+    final packagePath = p.dirname(libPath);
+
+    collection = _analysisContextCollection = AnalysisContextCollection(
+      includedPaths: [packagePath],
+    );
+  }
+
+  return collection;
+}
+
+Future<Iterable<Uri>> findImports(Uri from, Source source) async =>
+    source.unit.directives
+        .whereType<UriBasedDirective>()
+        .map((d) => d.uri.stringValue!)
+        .where((uri) => !uri.startsWith('dart:'))
+        .map((import) => resolveImport(import, from));
+
+Future<CompilationUnit> parseUri(Uri uri) async {
+  final path = await pathForUri(uri);
+  final analysisContext = (await analysisContextCollection).contexts.single;
+  final analysisSession = analysisContext.currentSession;
+  final parseResult = analysisSession.getParsedUnit(path);
+  return (parseResult as ParsedUnitResult).unit;
+}
+
+Future<String> pathForUri(Uri uri) async {
+  final fileUri = await Isolate.resolvePackageUri(uri);
+  if (fileUri == null || !fileUri.isScheme('file')) {
+    throw StateError('Expected to resolve $uri to a file URI, got $fileUri');
+  }
+  return p.fromUri(fileUri);
+}
+
+Future<Source> read(Uri uri) async => Source(uri, await parseUri(uri));
+
+Uri resolveImport(String import, Uri from) {
+  if (import.startsWith('package:')) return Uri.parse(import);
+  assert(from.scheme == 'package');
+  final package = from.pathSegments.first;
+  final fromPath = p.joinAll(from.pathSegments.skip(1));
+  final path = p.normalize(p.join(p.dirname(fromPath), import));
+  return Uri.parse('package:${p.join(package, path)}');
+}
+
+class Source {
+  final Uri uri;
+  final CompilationUnit unit;
+
+  Source(this.uri, this.unit);
+}
diff --git a/pkgs/graphs/example/example.dart b/pkgs/graphs/example/example.dart
new file mode 100644
index 0000000..c9cf6dd
--- /dev/null
+++ b/pkgs/graphs/example/example.dart
@@ -0,0 +1,49 @@
+// Copyright (c) 2017, 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.
+
+import 'package:graphs/graphs.dart';
+
+/// A representation of a directed graph.
+///
+/// Data is stored on the [Node] class.
+class Graph {
+  final Map<Node, List<Node>> nodes;
+
+  Graph(this.nodes);
+}
+
+class Node {
+  final String id;
+  final int data;
+
+  Node(this.id, this.data);
+
+  @override
+  bool operator ==(Object other) => other is Node && other.id == id;
+
+  @override
+  int get hashCode => id.hashCode;
+
+  @override
+  String toString() => '<$id -> $data>';
+}
+
+void main() {
+  final nodeA = Node('A', 1);
+  final nodeB = Node('B', 2);
+  final nodeC = Node('C', 3);
+  final nodeD = Node('D', 4);
+  final graph = Graph({
+    nodeA: [nodeB, nodeC],
+    nodeB: [nodeC, nodeD],
+    nodeC: [nodeB, nodeD],
+  });
+
+  final components = stronglyConnectedComponents<Node>(
+    graph.nodes.keys,
+    (node) => graph.nodes[node] ?? [],
+  );
+
+  print(components);
+}
diff --git a/pkgs/graphs/lib/graphs.dart b/pkgs/graphs/lib/graphs.dart
new file mode 100644
index 0000000..f10b2e4
--- /dev/null
+++ b/pkgs/graphs/lib/graphs.dart
@@ -0,0 +1,11 @@
+// Copyright (c) 2017, 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.
+
+export 'src/crawl_async.dart' show crawlAsync;
+export 'src/cycle_exception.dart' show CycleException;
+export 'src/shortest_path.dart' show shortestPath, shortestPaths;
+export 'src/strongly_connected_components.dart'
+    show stronglyConnectedComponents;
+export 'src/topological_sort.dart' show topologicalSort;
+export 'src/transitive_closure.dart' show transitiveClosure;
diff --git a/pkgs/graphs/lib/src/crawl_async.dart b/pkgs/graphs/lib/src/crawl_async.dart
new file mode 100644
index 0000000..68c0a5b
--- /dev/null
+++ b/pkgs/graphs/lib/src/crawl_async.dart
@@ -0,0 +1,85 @@
+// Copyright (c) 2017, 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.
+
+import 'dart:async';
+import 'dart:collection';
+
+final _empty = Future<void>.value();
+
+/// Finds and returns every node in a graph who's nodes and edges are
+/// asynchronously resolved.
+///
+/// Cycles are allowed. If this is an undirected graph the [edges] function
+/// may be symmetric. In this case the [roots] may be any node in each connected
+/// graph.
+///
+/// [V] is the type of values in the graph nodes. [K] must be a type suitable
+/// for using as a Map or Set key. [edges] should return the next reachable
+/// nodes.
+///
+/// There are no ordering guarantees. This is useful for ensuring some work is
+/// performed at every node in an asynchronous graph, but does not give
+/// guarantees that the work is done in topological order.
+///
+/// If either [readNode] or [edges] throws the error will be forwarded
+/// through the result stream and no further nodes will be crawled, though some
+/// work may have already been started.
+///
+/// Crawling is eager, so calls to [edges] may overlap with other calls that
+/// have not completed. If the [edges] callback needs to be limited or throttled
+/// that must be done by wrapping it before calling [crawlAsync].
+Stream<V> crawlAsync<K extends Object, V>(
+  Iterable<K> roots,
+  FutureOr<V> Function(K) readNode,
+  FutureOr<Iterable<K>> Function(K, V) edges,
+) {
+  final crawl = _CrawlAsync(roots, readNode, edges)..run();
+  return crawl.result.stream;
+}
+
+class _CrawlAsync<K, V> {
+  final result = StreamController<V>();
+
+  final FutureOr<V> Function(K) readNode;
+  final FutureOr<Iterable<K>> Function(K, V) edges;
+  final Iterable<K> roots;
+
+  final _seen = HashSet<K>();
+
+  _CrawlAsync(this.roots, this.readNode, this.edges);
+
+  /// Add all nodes in the graph to [result] and return a Future which fires
+  /// after all nodes have been seen.
+  Future<void> run() async {
+    try {
+      await Future.wait(roots.map(_visit), eagerError: true);
+      await result.close();
+    } catch (e, st) {
+      result.addError(e, st);
+      await result.close();
+    }
+  }
+
+  /// Resolve the node at [key] and output it, then start crawling all of it's
+  /// edges.
+  Future<void> _crawlFrom(K key) async {
+    final value = await readNode(key);
+    if (result.isClosed) return;
+    result.add(value);
+    final next = await edges(key, value);
+    await Future.wait(next.map(_visit), eagerError: true);
+  }
+
+  /// Synchronously record that [key] is being handled then start work on the
+  /// node for [key].
+  ///
+  /// The returned Future will complete only after the work for [key] and all
+  /// transitively reachable nodes has either been finished, or will be finished
+  /// by some other Future in [_seen].
+  Future<void> _visit(K key) {
+    if (_seen.contains(key)) return _empty;
+    _seen.add(key);
+    return _crawlFrom(key);
+  }
+}
diff --git a/pkgs/graphs/lib/src/cycle_exception.dart b/pkgs/graphs/lib/src/cycle_exception.dart
new file mode 100644
index 0000000..eb9b433
--- /dev/null
+++ b/pkgs/graphs/lib/src/cycle_exception.dart
@@ -0,0 +1,19 @@
+// Copyright (c) 2021, 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.
+
+/// An exception indicating that a cycle was detected in a graph that was
+/// expected to be acyclic.
+class CycleException<T> implements Exception {
+  /// The list of nodes comprising the cycle.
+  ///
+  /// Each node in this list has an edge to the next node. The final node has an
+  /// edge to the first node.
+  final List<T> cycle;
+
+  CycleException(Iterable<T> cycle) : cycle = List.unmodifiable(cycle);
+
+  @override
+  String toString() => 'A cycle was detected in a graph that must be acyclic:\n'
+      '${cycle.map((node) => '* $node').join('\n')}';
+}
diff --git a/pkgs/graphs/lib/src/shortest_path.dart b/pkgs/graphs/lib/src/shortest_path.dart
new file mode 100644
index 0000000..28f7e51
--- /dev/null
+++ b/pkgs/graphs/lib/src/shortest_path.dart
@@ -0,0 +1,144 @@
+// Copyright (c) 2018, 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.
+
+import 'dart:collection';
+
+/// Returns the shortest path from [start] to [target] given the directed
+/// edges of a graph provided by [edges].
+///
+/// If [start] `==` [target], an empty [List] is returned and [edges] is never
+/// called.
+///
+/// If [equals] is provided, it is used to compare nodes in the graph. If
+/// [equals] is omitted, the node's own [Object.==] is used instead.
+///
+/// Similarly, if [hashCode] is provided, it is used to produce a hash value
+/// for nodes to efficiently calculate the return value. If it is omitted, the
+/// key's own [Object.hashCode] is used.
+///
+/// If you supply one of [equals] or [hashCode], you should generally also to
+/// supply the other.
+Iterable<T>? shortestPath<T extends Object>(
+  T start,
+  T target,
+  Iterable<T> Function(T) edges, {
+  bool Function(T, T)? equals,
+  int Function(T)? hashCode,
+}) =>
+    _shortestPaths<T>(
+      start,
+      edges,
+      target: target,
+      equals: equals,
+      hashCode: hashCode,
+    )[target];
+
+/// Returns a [Map] of the shortest paths from [start] to all of the nodes in
+/// the directed graph defined by [edges].
+///
+/// All return values will contain the key [start] with an empty [List] value.
+///
+/// [start] and all values returned by [edges] must not be `null`.
+/// If asserts are enabled, an [AssertionError] is raised if these conditions
+/// are not met. If asserts are not enabled, violations result in undefined
+/// behavior.
+///
+/// If [equals] is provided, it is used to compare nodes in the graph. If
+/// [equals] is omitted, the node's own [Object.==] is used instead.
+///
+/// Similarly, if [hashCode] is provided, it is used to produce a hash value
+/// for nodes to efficiently calculate the return value. If it is omitted, the
+/// key's own [Object.hashCode] is used.
+///
+/// If you supply one of [equals] or [hashCode], you should generally also to
+/// supply the other.
+Map<T, Iterable<T>> shortestPaths<T extends Object>(
+  T start,
+  Iterable<T> Function(T) edges, {
+  bool Function(T, T)? equals,
+  int Function(T)? hashCode,
+}) =>
+    _shortestPaths<T>(
+      start,
+      edges,
+      equals: equals,
+      hashCode: hashCode,
+    );
+
+Map<T, Iterable<T>> _shortestPaths<T extends Object>(
+  T start,
+  Iterable<T> Function(T) edges, {
+  T? target,
+  bool Function(T, T)? equals,
+  int Function(T)? hashCode,
+}) {
+  final distances = HashMap<T, _Tail<T>>(equals: equals, hashCode: hashCode);
+  distances[start] = _Tail<T>();
+
+  final nonNullEquals = equals ??= _defaultEquals;
+  final isTarget =
+      target == null ? _neverTarget : (T node) => nonNullEquals(node, target);
+  if (isTarget(start)) {
+    return distances;
+  }
+
+  final toVisit = ListQueue<T>()..add(start);
+
+  while (toVisit.isNotEmpty) {
+    final current = toVisit.removeFirst();
+    final currentPath = distances[current]!;
+
+    for (var edge in edges(current)) {
+      final existingPath = distances[edge];
+
+      if (existingPath == null) {
+        distances[edge] = currentPath.append(edge);
+        if (isTarget(edge)) {
+          return distances;
+        }
+        toVisit.add(edge);
+      }
+    }
+  }
+
+  return distances;
+}
+
+bool _defaultEquals(Object a, Object b) => a == b;
+bool _neverTarget(Object _) => false;
+
+/// An immutable iterable that can efficiently return a copy with a value
+/// appended.
+///
+/// This implementation has an efficient [length] property.
+///
+/// Note that grabbing an [iterator] for the first time is O(n) in time and
+/// space because it copies all the values to a new list and uses that
+/// iterator in order to avoid stack overflows for large paths. This copy is
+/// cached for subsequent calls.
+class _Tail<T extends Object> extends Iterable<T> {
+  final T? tail;
+  final _Tail<T>? head;
+  @override
+  final int length;
+  _Tail()
+      : tail = null,
+        head = null,
+        length = 0;
+  _Tail._(this.tail, this.head, this.length);
+  _Tail<T> append(T value) => _Tail._(value, this, length + 1);
+
+  @override
+  Iterator<T> get iterator => _asIterable.iterator;
+
+  late final _asIterable = () {
+    _Tail<T>? next = this;
+    final reversed = List.generate(length, (_) {
+      final val = next!.tail;
+      next = next!.head;
+      return val as T;
+    });
+    return reversed.reversed;
+  }();
+}
diff --git a/pkgs/graphs/lib/src/strongly_connected_components.dart b/pkgs/graphs/lib/src/strongly_connected_components.dart
new file mode 100644
index 0000000..e8a775c
--- /dev/null
+++ b/pkgs/graphs/lib/src/strongly_connected_components.dart
@@ -0,0 +1,117 @@
+// Copyright (c) 2017, 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.
+
+import 'dart:collection';
+import 'dart:math' show min;
+
+/// Finds the strongly connected components of a directed graph using Tarjan's
+/// algorithm.
+///
+/// The result will be a valid reverse topological order ordering of the
+/// strongly connected components. Components further from a root will appear in
+/// the result before the components which they are connected to.
+///
+/// Nodes within a strongly connected component have no ordering guarantees,
+/// except that if the first value in [nodes] is a valid root, and is contained
+/// in a cycle, it will be the last element of that cycle.
+///
+/// [nodes] must contain at least a root of every tree in the graph if there are
+/// disjoint subgraphs but it may contain all nodes in the graph if the roots
+/// are not known.
+///
+/// If [equals] is provided, it is used to compare nodes in the graph. If
+/// [equals] is omitted, the node's own [Object.==] is used instead.
+///
+/// Similarly, if [hashCode] is provided, it is used to produce a hash value
+/// for nodes to efficiently calculate the return value. If it is omitted, the
+/// key's own [Object.hashCode] is used.
+///
+/// If you supply one of [equals] or [hashCode], you should generally also to
+/// supply the other.
+List<List<T>> stronglyConnectedComponents<T extends Object>(
+  Iterable<T> nodes,
+  Iterable<T> Function(T) edges, {
+  bool Function(T, T)? equals,
+  int Function(T)? hashCode,
+}) {
+  final result = <List<T>>[];
+  final lowLinks = HashMap<T, int>(equals: equals, hashCode: hashCode);
+  final indexes = HashMap<T, int>(equals: equals, hashCode: hashCode);
+  final onStack = HashSet<T>(equals: equals, hashCode: hashCode);
+
+  final nonNullEquals = equals ?? _defaultEquals;
+
+  var index = 0;
+  final lastVisited = Queue<T>();
+
+  final stack = [for (final node in nodes) _StackState(node)];
+  outer:
+  while (stack.isNotEmpty) {
+    final state = stack.removeLast();
+    final node = state.node;
+    var iterator = state.iterator;
+
+    int lowLink;
+    if (iterator == null) {
+      if (indexes.containsKey(node)) continue;
+      indexes[node] = index;
+      lowLink = lowLinks[node] = index;
+      index++;
+      iterator = edges(node).iterator;
+
+      // Nodes with no edges are always in their own component.
+      if (!iterator.moveNext()) {
+        result.add([node]);
+        continue;
+      }
+
+      lastVisited.addLast(node);
+      onStack.add(node);
+    } else {
+      lowLink = min(lowLinks[node]!, lowLinks[iterator.current]!);
+    }
+
+    do {
+      final next = iterator.current;
+      if (!indexes.containsKey(next)) {
+        stack.add(_StackState(node, iterator));
+        stack.add(_StackState(next));
+        continue outer;
+      } else if (onStack.contains(next)) {
+        lowLink = lowLinks[node] = min(lowLink, indexes[next]!);
+      }
+    } while (iterator.moveNext());
+
+    if (lowLink == indexes[node]) {
+      final component = <T>[];
+      T next;
+      do {
+        next = lastVisited.removeLast();
+        onStack.remove(next);
+        component.add(next);
+      } while (!nonNullEquals(next, node));
+      result.add(component);
+    }
+  }
+
+  return result;
+}
+
+/// The state of a pass on a single node in Tarjan's Algorithm.
+///
+/// This is used to perform the algorithm with an explicit stack rather than
+/// recursively, to avoid stack overflow errors for very large graphs.
+class _StackState<T> {
+  /// The node being inspected.
+  final T node;
+
+  /// The iterator traversing [node]'s edges.
+  ///
+  /// This is null if the node hasn't yet begun being traversed.
+  final Iterator<T>? iterator;
+
+  _StackState(this.node, [this.iterator]);
+}
+
+bool _defaultEquals(Object a, Object b) => a == b;
diff --git a/pkgs/graphs/lib/src/topological_sort.dart b/pkgs/graphs/lib/src/topological_sort.dart
new file mode 100644
index 0000000..948e696
--- /dev/null
+++ b/pkgs/graphs/lib/src/topological_sort.dart
@@ -0,0 +1,146 @@
+// Copyright (c) 2021, 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.
+
+import 'dart:collection';
+
+import 'package:collection/collection.dart' hide stronglyConnectedComponents;
+
+import 'cycle_exception.dart';
+
+/// Returns a topological sort of the nodes of the directed edges of a graph
+/// provided by [nodes] and [edges].
+///
+/// Each element of the returned iterable is guaranteed to appear after all
+/// nodes that have edges leading to that node. The result is not guaranteed to
+/// be unique, nor is it guaranteed to be stable across releases of this
+/// package; however, it will be stable for a given input within a given package
+/// version.
+///
+/// If [equals] is provided, it is used to compare nodes in the graph. If
+/// [equals] is omitted, the node's own [Object.==] is used instead.
+///
+/// Similarly, if [hashCode] is provided, it is used to produce a hash value
+/// for nodes to efficiently calculate the return value. If it is omitted, the
+/// key's own [Object.hashCode] is used.
+///
+/// If you supply one of [equals] or [hashCode], you should generally also to
+/// supply the other.
+///
+/// If you supply [secondarySort], the resulting list will be sorted by that
+/// comparison function as much as possible without violating the topological
+/// ordering. Note that even with a secondary sort, the result is _still_ not
+/// guaranteed to be unique or stable across releases of this package.
+///
+/// Note: this requires that [nodes] and each iterable returned by [edges]
+/// contain no duplicate entries.
+///
+/// Throws a [CycleException<T>] if the graph is cyclical.
+List<T> topologicalSort<T>(
+  Iterable<T> nodes,
+  Iterable<T> Function(T) edges, {
+  bool Function(T, T)? equals,
+  int Function(T)? hashCode,
+  Comparator<T>? secondarySort,
+}) {
+  if (secondarySort != null) {
+    return _topologicalSortWithSecondary(
+      [...nodes],
+      edges,
+      secondarySort,
+      equals,
+      hashCode,
+    );
+  }
+
+  // https://en.wikipedia.org/wiki/Topological_sorting#Depth-first_search
+  final result = QueueList<T>();
+  final permanentMark = HashSet<T>(equals: equals, hashCode: hashCode);
+  final temporaryMark = LinkedHashSet<T>(equals: equals, hashCode: hashCode);
+  final stack = [...nodes];
+  while (stack.isNotEmpty) {
+    final node = stack.removeLast();
+    if (permanentMark.contains(node)) continue;
+
+    // If we're visiting this node while it's already marked and not through a
+    // dependency, that must mean we've traversed all its dependencies and it's
+    // safe to add it to the result.
+    if (temporaryMark.contains(node)) {
+      temporaryMark.remove(node);
+      permanentMark.add(node);
+      result.addFirst(node);
+    } else {
+      temporaryMark.add(node);
+
+      // Revisit this node once we've visited all its children.
+      stack.add(node);
+      for (var child in edges(node)) {
+        if (temporaryMark.contains(child)) throw CycleException(temporaryMark);
+        stack.add(child);
+      }
+    }
+  }
+
+  return result;
+}
+
+/// An implementation of [topologicalSort] with a secondary comparison function.
+List<T> _topologicalSortWithSecondary<T>(
+  List<T> nodes,
+  Iterable<T> Function(T) edges,
+  Comparator<T> comparator,
+  bool Function(T, T)? equals,
+  int Function(T)? hashCode,
+) {
+  // https://en.wikipedia.org/wiki/Topological_sorting#Kahn's_algorithm,
+  // modified to sort the nodes to traverse. Also documented in
+  // https://www.algotree.org/algorithms/tree_graph_traversal/lexical_topological_sort_c++/
+
+  // For each node, the number of incoming edges it has that we haven't yet
+  // traversed.
+  final incomingEdges = HashMap<T, int>(equals: equals, hashCode: hashCode);
+  for (var node in nodes) {
+    for (var child in edges(node)) {
+      incomingEdges[child] = (incomingEdges[child] ?? 0) + 1;
+    }
+  }
+
+  // A priority queue of nodes that have no remaining incoming edges.
+  final nodesToTraverse = PriorityQueue<T>(comparator);
+  for (var node in nodes) {
+    if (!incomingEdges.containsKey(node)) nodesToTraverse.add(node);
+  }
+
+  final result = <T>[];
+  while (nodesToTraverse.isNotEmpty) {
+    final node = nodesToTraverse.removeFirst();
+    result.add(node);
+    for (var child in edges(node)) {
+      var remainingEdges = incomingEdges[child]!;
+      remainingEdges--;
+      incomingEdges[child] = remainingEdges;
+      if (remainingEdges == 0) nodesToTraverse.add(child);
+    }
+  }
+
+  if (result.length < nodes.length) {
+    // This algorithm doesn't automatically produce a cycle list as a side
+    // effect of sorting, so to throw the appropriate [CycleException] we just
+    // call the normal [topologicalSort] with a view of this graph that only
+    // includes nodes that still have edges.
+    bool nodeIsInCycle(T node) {
+      final edges = incomingEdges[node];
+      return edges != null && edges > 0;
+    }
+
+    topologicalSort<T>(
+      nodes.where(nodeIsInCycle),
+      edges,
+      equals: equals,
+      hashCode: hashCode,
+    );
+    assert(false, 'topologicalSort() should throw if the graph has a cycle');
+  }
+
+  return result;
+}
diff --git a/pkgs/graphs/lib/src/transitive_closure.dart b/pkgs/graphs/lib/src/transitive_closure.dart
new file mode 100644
index 0000000..24791d6
--- /dev/null
+++ b/pkgs/graphs/lib/src/transitive_closure.dart
@@ -0,0 +1,143 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:collection';
+
+import 'cycle_exception.dart';
+import 'strongly_connected_components.dart';
+import 'topological_sort.dart';
+
+/// Returns a transitive closure of a directed graph provided by [nodes] and
+/// [edges].
+///
+/// The result is a map from [nodes] to the sets of nodes that are transitively
+/// reachable through [edges]. No particular ordering is guaranteed.
+///
+/// If [equals] is provided, it is used to compare nodes in the graph. If
+/// [equals] is omitted, the node's own [Object.==] is used instead.
+///
+/// Similarly, if [hashCode] is provided, it is used to produce a hash value
+/// for nodes to efficiently calculate the return value. If it is omitted, the
+/// key's own [Object.hashCode] is used.
+///
+/// If you supply one of [equals] or [hashCode], you should generally also to
+/// supply the other.
+///
+/// Note: this requires that [nodes] and each iterable returned by [edges]
+/// contain no duplicate entries.
+///
+/// By default, this can handle either cyclic or acyclic graphs. If [acyclic] is
+/// true, this will run more efficiently but throw a [CycleException] if the
+/// graph is cyclical.
+Map<T, Set<T>> transitiveClosure<T extends Object>(
+  Iterable<T> nodes,
+  Iterable<T> Function(T) edges, {
+  bool Function(T, T)? equals,
+  int Function(T)? hashCode,
+  bool acyclic = false,
+}) {
+  if (!acyclic) {
+    return _cyclicTransitiveClosure(
+      nodes,
+      edges,
+      equals: equals,
+      hashCode: hashCode,
+    );
+  }
+
+  final topologicalOrder =
+      topologicalSort(nodes, edges, equals: equals, hashCode: hashCode);
+  final result = LinkedHashMap<T, Set<T>>(equals: equals, hashCode: hashCode);
+  for (final node in topologicalOrder.reversed) {
+    final closure = LinkedHashSet<T>(equals: equals, hashCode: hashCode);
+    for (var child in edges(node)) {
+      closure.add(child);
+      closure.addAll(result[child]!);
+    }
+
+    result[node] = closure;
+  }
+
+  return result;
+}
+
+/// Returns the transitive closure of a cyclic graph using [Purdom's algorithm].
+///
+/// [Purdom's algorithm]: https://algowiki-project.org/en/Purdom%27s_algorithm
+///
+/// This first computes the strongly connected components of the graph and finds
+/// the transitive closure of those before flattening it out into the transitive
+/// closure of the entire graph.
+Map<T, Set<T>> _cyclicTransitiveClosure<T extends Object>(
+  Iterable<T> nodes,
+  Iterable<T> Function(T) edges, {
+  bool Function(T, T)? equals,
+  int Function(T)? hashCode,
+}) {
+  final components = stronglyConnectedComponents<T>(
+    nodes,
+    edges,
+    equals: equals,
+    hashCode: hashCode,
+  );
+  final nodesToComponents =
+      HashMap<T, List<T>>(equals: equals, hashCode: hashCode);
+  for (final component in components) {
+    for (final node in component) {
+      nodesToComponents[node] = component;
+    }
+  }
+
+  // Because [stronglyConnectedComponents] returns the components in reverse
+  // topological order, we can avoid an additional topological sort here.
+  // Instead, we directly traverse the component list with the knowledge that
+  // once we reach a component, everything reachable from it has already been
+  // registered in [result].
+  final result = LinkedHashMap<T, Set<T>>(equals: equals, hashCode: hashCode);
+  for (final component in components) {
+    final closure = LinkedHashSet<T>(equals: equals, hashCode: hashCode);
+    if (_componentIncludesCycle(component, edges, equals)) {
+      closure.addAll(component);
+    }
+
+    // De-duplicate downstream components to avoid adding the same transitive
+    // children over and over.
+    final downstreamComponents = {
+      for (final node in component)
+        for (final child in edges(node)) nodesToComponents[child]!,
+    };
+    for (final childComponent in downstreamComponents) {
+      if (childComponent == component) continue;
+
+      // This if check is just for efficiency. If [childComponent] has multiple
+      // nodes, `result[childComponent.first]` will contain all the nodes in
+      // `childComponent` anyway since it's cyclical.
+      if (childComponent.length == 1) closure.addAll(childComponent);
+      closure.addAll(result[childComponent.first]!);
+    }
+
+    for (final node in component) {
+      result[node] = closure;
+    }
+  }
+  return result;
+}
+
+/// Returns whether the strongly-connected component [component] of a graph
+/// defined by [edges] includes a cycle.
+bool _componentIncludesCycle<T>(
+  List<T> component,
+  Iterable<T> Function(T) edges,
+  bool Function(T, T)? equals,
+) {
+  // A strongly-connected component with more than one node always contains a
+  // cycle, by definition.
+  if (component.length > 1) return true;
+
+  // A component with only a single node only contains a cycle if that node has
+  // an edge to itself.
+  final node = component.single;
+  return edges(node)
+      .any((edge) => equals == null ? edge == node : equals(edge, node));
+}
diff --git a/pkgs/graphs/pubspec.yaml b/pkgs/graphs/pubspec.yaml
new file mode 100644
index 0000000..5b5457a
--- /dev/null
+++ b/pkgs/graphs/pubspec.yaml
@@ -0,0 +1,19 @@
+name: graphs
+version: 2.3.3-wip
+description: Graph algorithms that operate on graphs in any representation.
+repository: https://github.com/dart-lang/tools/tree/main/pkgs/graphs
+
+environment:
+  sdk: ^3.4.0
+
+dependencies:
+  collection: ^1.15.0
+
+dev_dependencies:
+  dart_flutter_team_lints: ^3.0.0
+  test: ^1.21.6
+
+  # For examples
+  analyzer: '>=5.2.0 <7.0.0'
+  path: ^1.8.0
+  pool: ^1.5.0
diff --git a/pkgs/graphs/test/crawl_async_test.dart b/pkgs/graphs/test/crawl_async_test.dart
new file mode 100644
index 0000000..9e168e6
--- /dev/null
+++ b/pkgs/graphs/test/crawl_async_test.dart
@@ -0,0 +1,113 @@
+// Copyright (c) 2017, 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.
+
+import 'package:graphs/graphs.dart';
+import 'package:test/test.dart';
+
+import 'utils/graph.dart';
+
+void main() {
+  group('asyncCrawl', () {
+    Future<List<String?>> crawl(
+      Map<String, List<String>?> g,
+      Iterable<String> roots,
+    ) {
+      final graph = AsyncGraph(g);
+      return crawlAsync(roots, graph.readNode, graph.edges).toList();
+    }
+
+    test('empty result for empty graph', () async {
+      final result = await crawl({}, []);
+      expect(result, isEmpty);
+    });
+
+    test('single item for a single node', () async {
+      final result = await crawl({'a': []}, ['a']);
+      expect(result, ['a']);
+    });
+
+    test('hits every node in a graph', () async {
+      final result = await crawl({
+        'a': ['b', 'c'],
+        'b': ['c'],
+        'c': ['d'],
+        'd': [],
+      }, [
+        'a',
+      ]);
+      expect(result, hasLength(4));
+      expect(
+        result,
+        allOf(contains('a'), contains('b'), contains('c'), contains('d')),
+      );
+    });
+
+    test('handles cycles', () async {
+      final result = await crawl({
+        'a': ['b'],
+        'b': ['c'],
+        'c': ['b'],
+      }, [
+        'a',
+      ]);
+      expect(result, hasLength(3));
+      expect(result, allOf(contains('a'), contains('b'), contains('c')));
+    });
+
+    test('handles self cycles', () async {
+      final result = await crawl({
+        'a': ['b'],
+        'b': ['b'],
+      }, [
+        'a',
+      ]);
+      expect(result, hasLength(2));
+      expect(result, allOf(contains('a'), contains('b')));
+    });
+
+    test('allows null edges', () async {
+      final result = await crawl({
+        'a': ['b'],
+        'b': null,
+      }, [
+        'a',
+      ]);
+      expect(result, hasLength(2));
+      expect(result, allOf(contains('a'), contains('b')));
+    });
+
+    test('allows null nodes', () async {
+      final result = await crawl({
+        'a': ['b'],
+      }, [
+        'a',
+      ]);
+      expect(result, ['a', null]);
+    });
+
+    test('surfaces exceptions for crawling edges', () {
+      final graph = {
+        'a': ['b'],
+      };
+      final nodes = crawlAsync(
+        ['a'],
+        (n) => n,
+        (k, n) => k == 'b' ? throw ArgumentError() : graph[k] ?? <String>[],
+      );
+      expect(nodes, emitsThrough(emitsError(isArgumentError)));
+    });
+
+    test('surfaces exceptions for resolving keys', () {
+      final graph = {
+        'a': ['b'],
+      };
+      final nodes = crawlAsync(
+        ['a'],
+        (n) => n == 'b' ? throw ArgumentError() : n,
+        (k, n) => graph[k] ?? <Never>[],
+      );
+      expect(nodes, emitsThrough(emitsError(isArgumentError)));
+    });
+  });
+}
diff --git a/pkgs/graphs/test/shortest_path_test.dart b/pkgs/graphs/test/shortest_path_test.dart
new file mode 100644
index 0000000..88281d4
--- /dev/null
+++ b/pkgs/graphs/test/shortest_path_test.dart
@@ -0,0 +1,161 @@
+// Copyright (c) 2018, 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.
+
+import 'dart:collection';
+import 'dart:math' show Random;
+
+import 'package:graphs/graphs.dart';
+import 'package:test/test.dart';
+
+import 'utils/utils.dart';
+
+void main() {
+  const graph = <String, List<String>>{
+    '1': ['2', '5'],
+    '2': ['3'],
+    '3': ['4', '5'],
+    '4': ['1'],
+    '5': ['8'],
+    '6': ['7'],
+  };
+
+  List<String> readEdges(String key) => graph[key] ?? [];
+
+  List<X> getXValues(X key) => graph[key.value]?.map(X.new).toList() ?? [];
+
+  void singlePathTest(String from, String to, List<String>? expected) {
+    test('$from -> $to should be $expected (mapped)', () {
+      expect(
+        shortestPath<X>(
+          X(from),
+          X(to),
+          getXValues,
+          equals: xEquals,
+          hashCode: xHashCode,
+        )?.map((x) => x.value),
+        expected,
+      );
+    });
+
+    test('$from -> $to should be $expected', () {
+      expect(shortestPath(from, to, readEdges), expected);
+    });
+  }
+
+  void pathsTest(
+    String from,
+    Map<String, List<String>> expected,
+    List<String> nullPaths,
+  ) {
+    test('paths from $from (mapped)', () {
+      final result = shortestPaths<X>(
+        X(from),
+        getXValues,
+        equals: xEquals,
+        hashCode: xHashCode,
+      ).map((k, v) => MapEntry(k.value, v.map((x) => x.value).toList()));
+      expect(result, expected);
+    });
+
+    test('paths from $from', () {
+      final result = shortestPaths(from, readEdges);
+      expect(result, expected);
+    });
+
+    for (var entry in expected.entries) {
+      singlePathTest(from, entry.key, entry.value);
+    }
+
+    for (var entry in nullPaths) {
+      singlePathTest(from, entry, null);
+    }
+  }
+
+  pathsTest('1', {
+    '5': ['5'],
+    '3': ['2', '3'],
+    '8': ['5', '8'],
+    '1': [],
+    '2': ['2'],
+    '4': ['2', '3', '4'],
+  }, [
+    '6',
+    '7',
+  ]);
+
+  pathsTest('6', {
+    '7': ['7'],
+    '6': [],
+  }, [
+    '1',
+  ]);
+  pathsTest('7', {'7': []}, ['1', '6']);
+
+  pathsTest('42', {'42': []}, ['1', '6']);
+
+  test('integration test', () {
+    // Be deterministic in the generated graph. This test may have to be updated
+    // if the behavior of `Random` changes for the provided seed.
+    final rnd = Random(1);
+    const size = 1000;
+    final graph = HashMap<int, List<int>>();
+
+    Iterable<int>? resultForGraph() =>
+        shortestPath(0, size - 1, (e) => graph[e] ?? const []);
+
+    void addRandomEdge() {
+      final toList = graph.putIfAbsent(rnd.nextInt(size), () => <int>[]);
+
+      final toValue = rnd.nextInt(size);
+      if (!toList.contains(toValue)) {
+        toList.add(toValue);
+      }
+    }
+
+    Iterable<int>? result;
+
+    // Add edges until there is a shortest path between `0` and `size - 1`
+    do {
+      addRandomEdge();
+      result = resultForGraph();
+    } while (result == null);
+
+    expect(result, [313, 547, 91, 481, 74, 64, 439, 388, 660, 275, 999]);
+
+    var count = 0;
+    // Add edges until the shortest path between `0` and `size - 1` is 2 items
+    // Adding edges should never increase the length of the shortest path.
+    // Adding enough edges should reduce the length of the shortest path.
+    do {
+      expect(++count, lessThan(size * 5), reason: 'This loop should finish.');
+      addRandomEdge();
+      final previousResultLength = result!.length;
+      result = resultForGraph();
+      expect(result, hasLength(lessThanOrEqualTo(previousResultLength)));
+    } while (result!.length > 2);
+
+    expect(result, [275, 999]);
+
+    count = 0;
+    // Remove edges until there is no shortest path.
+    // Removing edges should never reduce the length of the shortest path.
+    // Removing enough edges should increase the length of the shortest path and
+    // eventually eliminate any path.
+    do {
+      expect(++count, lessThan(size * 5), reason: 'This loop should finish.');
+      final randomKey = graph.keys.elementAt(rnd.nextInt(graph.length));
+      final list = graph[randomKey]!;
+      expect(list, isNotEmpty);
+      list.removeAt(rnd.nextInt(list.length));
+      if (list.isEmpty) {
+        graph.remove(randomKey);
+      }
+      final previousResultLength = result!.length;
+      result = resultForGraph();
+      if (result != null) {
+        expect(result, hasLength(greaterThanOrEqualTo(previousResultLength)));
+      }
+    } while (result != null);
+  });
+}
diff --git a/pkgs/graphs/test/strongly_connected_components_test.dart b/pkgs/graphs/test/strongly_connected_components_test.dart
new file mode 100644
index 0000000..2fa4d88
--- /dev/null
+++ b/pkgs/graphs/test/strongly_connected_components_test.dart
@@ -0,0 +1,304 @@
+// Copyright (c) 2017, 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.
+
+import 'package:graphs/graphs.dart';
+import 'package:test/test.dart';
+
+import 'utils/graph.dart';
+import 'utils/utils.dart';
+
+void main() {
+  group('strongly connected components', () {
+    /// Run [stronglyConnectedComponents] on [g].
+    List<List<String>> components(
+      Map<String, List<String>?> g, {
+      Iterable<String>? startNodes,
+    }) {
+      final graph = Graph(g);
+      return stronglyConnectedComponents(
+        startNodes ?? graph.allNodes,
+        graph.edges,
+      );
+    }
+
+    test('empty result for empty graph', () {
+      final result = components({});
+      expect(result, isEmpty);
+    });
+
+    test('single item for single node', () {
+      final result = components({'a': []});
+      expect(result, [
+        ['a'],
+      ]);
+    });
+
+    test('handles non-cycles', () {
+      final result = components({
+        'a': ['b'],
+        'b': ['c'],
+        'c': [],
+      });
+      expect(result, [
+        ['c'],
+        ['b'],
+        ['a'],
+      ]);
+    });
+
+    test('handles entire graph as cycle', () {
+      final result = components({
+        'a': ['b'],
+        'b': ['c'],
+        'c': ['d'],
+        'd': ['a'],
+      });
+      expect(
+        result,
+        [allOf(contains('a'), contains('b'), contains('c'), contains('d'))],
+      );
+    });
+
+    test('includes the first passed root last in a cycle', () {
+      // In cases where this is used to find a topological ordering the first
+      // value in nodes should always come last.
+      final graph = {
+        'a': ['b'],
+        'b': ['a'],
+      };
+      final resultFromA = components(graph, startNodes: ['a']);
+      final resultFromB = components(graph, startNodes: ['b']);
+      expect(resultFromA.single.last, 'a');
+      expect(resultFromB.single.last, 'b');
+    });
+
+    test('handles cycles in the middle', () {
+      final result = components({
+        'a': ['b', 'c'],
+        'b': ['c', 'd'],
+        'c': ['b', 'd'],
+        'd': [],
+      });
+      expect(result, [
+        ['d'],
+        allOf(contains('b'), contains('c')),
+        ['a'],
+      ]);
+    });
+
+    test('handles self cycles', () {
+      final result = components({
+        'a': ['b'],
+        'b': ['b'],
+      });
+      expect(result, [
+        ['b'],
+        ['a'],
+      ]);
+    });
+
+    test('valid topological ordering for disjoint subgraphs', () {
+      final result = components({
+        'a': ['b', 'c'],
+        'b': ['b1', 'b2'],
+        'c': ['c1', 'c2'],
+        'b1': [],
+        'b2': [],
+        'c1': [],
+        'c2': [],
+      });
+
+      expect(
+        result,
+        containsAllInOrder([
+          ['c1'],
+          ['c'],
+          ['a'],
+        ]),
+      );
+      expect(
+        result,
+        containsAllInOrder([
+          ['c2'],
+          ['c'],
+          ['a'],
+        ]),
+      );
+      expect(
+        result,
+        containsAllInOrder([
+          ['b1'],
+          ['b'],
+          ['a'],
+        ]),
+      );
+      expect(
+        result,
+        containsAllInOrder([
+          ['b2'],
+          ['b'],
+          ['a'],
+        ]),
+      );
+    });
+
+    test('handles getting null for edges', () {
+      final result = components({
+        'a': ['b'],
+        'b': null,
+      });
+      expect(result, [
+        ['b'],
+        ['a'],
+      ]);
+    });
+  });
+
+  group('custom hashCode and equals', () {
+    /// Run [stronglyConnectedComponents] on [g].
+    List<List<String>> components(
+      Map<String, List<String>?> g, {
+      Iterable<String>? startNodes,
+    }) {
+      final graph = BadGraph(g);
+
+      startNodes ??= graph.allNodes.map((n) => n.value);
+
+      return stronglyConnectedComponents<X>(
+        startNodes.map(X.new),
+        graph.edges,
+        equals: xEquals,
+        hashCode: xHashCode,
+      ).map((list) => list.map((x) => x.value).toList()).toList();
+    }
+
+    test('empty result for empty graph', () {
+      final result = components({});
+      expect(result, isEmpty);
+    });
+
+    test('single item for single node', () {
+      final result = components({'a': []});
+      expect(result, [
+        ['a'],
+      ]);
+    });
+
+    test('handles non-cycles', () {
+      final result = components({
+        'a': ['b'],
+        'b': ['c'],
+        'c': [],
+      });
+      expect(result, [
+        ['c'],
+        ['b'],
+        ['a'],
+      ]);
+    });
+
+    test('handles entire graph as cycle', () {
+      final result = components({
+        'a': ['b'],
+        'b': ['c'],
+        'c': ['a'],
+      });
+      expect(result, [allOf(contains('a'), contains('b'), contains('c'))]);
+    });
+
+    test('includes the first passed root last in a cycle', () {
+      // In cases where this is used to find a topological ordering the first
+      // value in nodes should always come last.
+      final graph = {
+        'a': ['b'],
+        'b': ['a'],
+      };
+      final resultFromA = components(graph, startNodes: ['a']);
+      final resultFromB = components(graph, startNodes: ['b']);
+      expect(resultFromA.single.last, 'a');
+      expect(resultFromB.single.last, 'b');
+    });
+
+    test('handles cycles in the middle', () {
+      final result = components({
+        'a': ['b', 'c'],
+        'b': ['c', 'd'],
+        'c': ['b', 'd'],
+        'd': [],
+      });
+      expect(result, [
+        ['d'],
+        allOf(contains('b'), contains('c')),
+        ['a'],
+      ]);
+    });
+
+    test('handles self cycles', () {
+      final result = components({
+        'a': ['b'],
+        'b': ['b'],
+      });
+      expect(result, [
+        ['b'],
+        ['a'],
+      ]);
+    });
+
+    test('valid topological ordering for disjoint subgraphs', () {
+      final result = components({
+        'a': ['b', 'c'],
+        'b': ['b1', 'b2'],
+        'c': ['c1', 'c2'],
+        'b1': [],
+        'b2': [],
+        'c1': [],
+        'c2': [],
+      });
+
+      expect(
+        result,
+        containsAllInOrder([
+          ['c1'],
+          ['c'],
+          ['a'],
+        ]),
+      );
+      expect(
+        result,
+        containsAllInOrder([
+          ['c2'],
+          ['c'],
+          ['a'],
+        ]),
+      );
+      expect(
+        result,
+        containsAllInOrder([
+          ['b1'],
+          ['b'],
+          ['a'],
+        ]),
+      );
+      expect(
+        result,
+        containsAllInOrder([
+          ['b2'],
+          ['b'],
+          ['a'],
+        ]),
+      );
+    });
+
+    test('handles getting null for edges', () {
+      final result = components({
+        'a': ['b'],
+        'b': null,
+      });
+      expect(result, [
+        ['b'],
+        ['a'],
+      ]);
+    });
+  });
+}
diff --git a/pkgs/graphs/test/topological_sort_test.dart b/pkgs/graphs/test/topological_sort_test.dart
new file mode 100644
index 0000000..831946b
--- /dev/null
+++ b/pkgs/graphs/test/topological_sort_test.dart
@@ -0,0 +1,362 @@
+// Copyright (c) 2018, 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.
+
+import 'dart:collection';
+
+import 'package:graphs/graphs.dart';
+import 'package:test/test.dart';
+
+import 'utils/utils.dart';
+
+void main() {
+  group('without secondarySort', () {
+    group('topologically sorts a graph', () {
+      test('with no nodes', () {
+        expect(_topologicalSort({}), isEmpty);
+      });
+
+      test('with only one node', () {
+        expect(_topologicalSort({1: []}), equals([1]));
+      });
+
+      test('with no edges', () {
+        expect(
+          _topologicalSort({1: [], 2: [], 3: [], 4: []}),
+          unorderedEquals([1, 2, 3, 4]),
+        );
+      });
+
+      test('with single edges', () {
+        expect(
+          _topologicalSort({
+            1: [2],
+            2: [3],
+            3: [4],
+            4: [],
+          }),
+          equals([1, 2, 3, 4]),
+        );
+      });
+
+      test('with many edges from one node', () {
+        final result = _topologicalSort({
+          1: [2, 3, 4],
+          2: [],
+          3: [],
+          4: [],
+        });
+        expect(result.indexOf(1), lessThan(result.indexOf(2)));
+        expect(result.indexOf(1), lessThan(result.indexOf(3)));
+        expect(result.indexOf(1), lessThan(result.indexOf(4)));
+      });
+
+      test('with transitive edges', () {
+        final result = _topologicalSort({
+          1: [2, 4],
+          2: [],
+          3: [],
+          4: [3],
+        });
+        expect(result.indexOf(1), lessThan(result.indexOf(2)));
+        expect(result.indexOf(1), lessThan(result.indexOf(3)));
+        expect(result.indexOf(1), lessThan(result.indexOf(4)));
+        expect(result.indexOf(4), lessThan(result.indexOf(3)));
+      });
+
+      test('with diamond edges', () {
+        final result = _topologicalSort({
+          1: [2, 3],
+          2: [4],
+          3: [4],
+          4: [],
+        });
+        expect(result.indexOf(1), lessThan(result.indexOf(2)));
+        expect(result.indexOf(1), lessThan(result.indexOf(3)));
+        expect(result.indexOf(1), lessThan(result.indexOf(4)));
+        expect(result.indexOf(2), lessThan(result.indexOf(4)));
+        expect(result.indexOf(3), lessThan(result.indexOf(4)));
+      });
+    });
+
+    test('respects custom equality and hash functions', () {
+      expect(
+        _topologicalSort<int>(
+          {
+            0: [2],
+            3: [4],
+            5: [6],
+            7: [],
+          },
+          equals: (i, j) => (i ~/ 2) == (j ~/ 2),
+          hashCode: (i) => (i ~/ 2).hashCode,
+        ),
+        equals([
+          0,
+          anyOf([2, 3]),
+          anyOf([4, 5]),
+          anyOf([6, 7]),
+        ]),
+      );
+    });
+
+    group('throws a CycleException for a graph with', () {
+      test('a one-node cycle', () {
+        expect(
+          () => _topologicalSort({
+            1: [1],
+          }),
+          throwsCycleException([1]),
+        );
+      });
+
+      test('a multi-node cycle', () {
+        expect(
+          () => _topologicalSort({
+            1: [2],
+            2: [3],
+            3: [4],
+            4: [1],
+          }),
+          throwsCycleException([4, 1, 2, 3]),
+        );
+      });
+    });
+  });
+
+  group('with secondarySort', () {
+    group('topologically sorts a graph', () {
+      test('with no nodes', () {
+        expect(_topologicalSort({}, secondarySort: true), isEmpty);
+      });
+
+      test('with only one node', () {
+        expect(_topologicalSort({1: []}, secondarySort: true), equals([1]));
+      });
+
+      test('with no edges', () {
+        expect(
+          _topologicalSort({1: [], 2: [], 3: [], 4: []}, secondarySort: true),
+          unorderedEquals([1, 2, 3, 4]),
+        );
+      });
+
+      test('with single edges', () {
+        expect(
+          _topologicalSort(
+            {
+              1: [2],
+              2: [3],
+              3: [4],
+              4: [],
+            },
+            secondarySort: true,
+          ),
+          equals([1, 2, 3, 4]),
+        );
+      });
+
+      test('with many edges from one node', () {
+        final result = _topologicalSort(
+          {
+            1: [2, 3, 4],
+            2: [],
+            3: [],
+            4: [],
+          },
+          secondarySort: true,
+        );
+        expect(result.indexOf(1), lessThan(result.indexOf(2)));
+        expect(result.indexOf(1), lessThan(result.indexOf(3)));
+        expect(result.indexOf(1), lessThan(result.indexOf(4)));
+      });
+
+      test('with transitive edges', () {
+        final result = _topologicalSort(
+          {
+            1: [2, 4],
+            2: [],
+            3: [],
+            4: [3],
+          },
+          secondarySort: true,
+        );
+        expect(result.indexOf(1), lessThan(result.indexOf(2)));
+        expect(result.indexOf(1), lessThan(result.indexOf(3)));
+        expect(result.indexOf(1), lessThan(result.indexOf(4)));
+        expect(result.indexOf(4), lessThan(result.indexOf(3)));
+      });
+
+      test('with diamond edges', () {
+        final result = _topologicalSort(
+          {
+            1: [2, 3],
+            2: [4],
+            3: [4],
+            4: [],
+          },
+          secondarySort: true,
+        );
+        expect(result.indexOf(1), lessThan(result.indexOf(2)));
+        expect(result.indexOf(1), lessThan(result.indexOf(3)));
+        expect(result.indexOf(1), lessThan(result.indexOf(4)));
+        expect(result.indexOf(2), lessThan(result.indexOf(4)));
+        expect(result.indexOf(3), lessThan(result.indexOf(4)));
+      });
+    });
+
+    group('lexically sorts a graph where possible', () {
+      test('with no edges', () {
+        final result =
+            _topologicalSort({4: [], 3: [], 1: [], 2: []}, secondarySort: true);
+        expect(result, equals([1, 2, 3, 4]));
+      });
+
+      test('with one non-lexical edge', () {
+        final result = _topologicalSort(
+          {
+            4: [],
+            3: [1],
+            1: [],
+            2: [],
+          },
+          secondarySort: true,
+        );
+        expect(
+          result,
+          equals(
+            anyOf([
+              [2, 3, 1, 4],
+              [3, 1, 2, 4],
+            ]),
+          ),
+        );
+      });
+
+      test('with a non-lexical topolgical order', () {
+        final result = _topologicalSort(
+          {
+            4: [3],
+            3: [2],
+            2: [1],
+            1: [],
+          },
+          secondarySort: true,
+        );
+        expect(result, equals([4, 3, 2, 1]));
+      });
+
+      group('with multiple layers', () {
+        test('in lexical order', () {
+          final result = _topologicalSort(
+            {
+              1: [2],
+              2: [3],
+              3: [],
+              4: [5],
+              5: [6],
+              6: [],
+            },
+            secondarySort: true,
+          );
+          expect(result, equals([1, 2, 3, 4, 5, 6]));
+        });
+
+        test('in non-lexical order', () {
+          final result = _topologicalSort(
+            {
+              1: [3],
+              3: [5],
+              4: [2],
+              2: [6],
+              5: [],
+              6: [],
+            },
+            secondarySort: true,
+          );
+          expect(
+            result,
+            anyOf([
+              equals([1, 3, 4, 2, 5, 6]),
+              equals([1, 4, 2, 3, 5, 6]),
+            ]),
+          );
+        });
+      });
+    });
+
+    test('respects custom equality and hash functions', () {
+      expect(
+        _topologicalSort<int>(
+          {
+            0: [2],
+            3: [4],
+            5: [6],
+            7: [],
+          },
+          equals: (i, j) => (i ~/ 2) == (j ~/ 2),
+          hashCode: (i) => (i ~/ 2).hashCode,
+          secondarySort: true,
+        ),
+        equals([
+          0,
+          anyOf([2, 3]),
+          anyOf([4, 5]),
+          anyOf([6, 7]),
+        ]),
+      );
+    });
+
+    group('throws a CycleException for a graph with', () {
+      test('a one-node cycle', () {
+        expect(
+          () => _topologicalSort(
+            {
+              1: [1],
+            },
+            secondarySort: true,
+          ),
+          throwsCycleException([1]),
+        );
+      });
+
+      test('a multi-node cycle', () {
+        expect(
+          () => _topologicalSort(
+            {
+              1: [2],
+              2: [3],
+              3: [4],
+              4: [1],
+            },
+            secondarySort: true,
+          ),
+          throwsCycleException([4, 1, 2, 3]),
+        );
+      });
+    });
+  });
+}
+
+/// Runs a topological sort on a graph represented a map from keys to edges.
+List<T> _topologicalSort<T>(
+  Map<T, List<T>> graph, {
+  bool Function(T, T)? equals,
+  int Function(T)? hashCode,
+  bool secondarySort = false,
+}) {
+  if (equals != null) {
+    graph = LinkedHashMap(equals: equals, hashCode: hashCode)..addAll(graph);
+  }
+  return topologicalSort(
+    graph.keys,
+    (node) {
+      expect(graph, contains(node));
+      return graph[node]!;
+    },
+    equals: equals,
+    hashCode: hashCode,
+    secondarySort:
+        secondarySort ? (a, b) => (a as Comparable<T>).compareTo(b) : null,
+  );
+}
diff --git a/pkgs/graphs/test/transitive_closure_test.dart b/pkgs/graphs/test/transitive_closure_test.dart
new file mode 100644
index 0000000..f732573
--- /dev/null
+++ b/pkgs/graphs/test/transitive_closure_test.dart
@@ -0,0 +1,350 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:collection';
+
+import 'package:graphs/graphs.dart';
+import 'package:test/test.dart';
+
+import 'utils/utils.dart';
+
+void main() {
+  group('for an acyclic graph', () {
+    for (final acyclic in [true, false]) {
+      group('with acyclic: $acyclic', () {
+        group('returns the transitive closure for a graph', () {
+          test('with no nodes', () {
+            expect(_transitiveClosure<int>({}, acyclic: acyclic), isEmpty);
+          });
+
+          test('with only one node', () {
+            expect(
+              _transitiveClosure<int>({1: []}, acyclic: acyclic),
+              equals({1: <int>{}}),
+            );
+          });
+
+          test('with no edges', () {
+            expect(
+              _transitiveClosure<int>(
+                {1: [], 2: [], 3: [], 4: []},
+                acyclic: acyclic,
+              ),
+              equals(<int, Set<int>>{1: {}, 2: {}, 3: {}, 4: {}}),
+            );
+          });
+
+          test('with single edges', () {
+            expect(
+              _transitiveClosure<int>(
+                {
+                  1: [2],
+                  2: [3],
+                  3: [4],
+                  4: [],
+                },
+                acyclic: acyclic,
+              ),
+              equals({
+                1: {2, 3, 4},
+                2: {3, 4},
+                3: {4},
+                4: <int>{},
+              }),
+            );
+          });
+
+          test('with many edges from one node', () {
+            expect(
+              _transitiveClosure<int>(
+                {
+                  1: [2, 3, 4],
+                  2: [],
+                  3: [],
+                  4: [],
+                },
+                acyclic: acyclic,
+              ),
+              equals(<int, Set<int>>{
+                1: {2, 3, 4},
+                2: {},
+                3: {},
+                4: {},
+              }),
+            );
+          });
+
+          test('with transitive edges', () {
+            expect(
+              _transitiveClosure<int>(
+                {
+                  1: [2, 4],
+                  2: [],
+                  3: [],
+                  4: [3],
+                },
+                acyclic: acyclic,
+              ),
+              equals(<int, Set<int>>{
+                1: {2, 3, 4},
+                2: {},
+                3: {},
+                4: {3},
+              }),
+            );
+          });
+
+          test('with diamond edges', () {
+            expect(
+              _transitiveClosure<int>(
+                {
+                  1: [2, 3],
+                  2: [4],
+                  3: [4],
+                  4: [],
+                },
+                acyclic: acyclic,
+              ),
+              equals(<int, Set<int>>{
+                1: {2, 3, 4},
+                2: {4},
+                3: {4},
+                4: {},
+              }),
+            );
+          });
+
+          test('with disjoint subgraphs', () {
+            expect(
+              _transitiveClosure<int>(
+                {
+                  1: [2],
+                  2: [3],
+                  3: [],
+                  4: [5],
+                  5: [6],
+                  6: [],
+                },
+                acyclic: acyclic,
+              ),
+              equals(<int, Set<int>>{
+                1: {2, 3},
+                2: {3},
+                3: {},
+                4: {5, 6},
+                5: {6},
+                6: {},
+              }),
+            );
+          });
+        });
+
+        test('respects custom equality and hash functions', () {
+          final result = _transitiveClosure<int>(
+            {
+              0: [2],
+              3: [4],
+              5: [6],
+              7: [],
+            },
+            equals: (i, j) => (i ~/ 2) == (j ~/ 2),
+            hashCode: (i) => (i ~/ 2).hashCode,
+          );
+
+          expect(
+            result.keys,
+            unorderedMatches([
+              0,
+              anyOf([2, 3]),
+              anyOf([4, 5]),
+              anyOf([6, 7]),
+            ]),
+          );
+          expect(
+            result[0],
+            equals({
+              anyOf([2, 3]),
+              anyOf([4, 5]),
+              anyOf([6, 7]),
+            }),
+          );
+          expect(
+            result[2],
+            equals({
+              anyOf([4, 5]),
+              anyOf([6, 7]),
+            }),
+          );
+          expect(
+            result[4],
+            equals({
+              anyOf([6, 7]),
+            }),
+          );
+          expect(result[6], isEmpty);
+        });
+      });
+    }
+  });
+
+  group('for a cyclic graph', () {
+    group('with acyclic: true throws a CycleException for a graph with', () {
+      test('a one-node cycle', () {
+        expect(
+          () => _transitiveClosure<int>(
+            {
+              1: [1],
+            },
+            acyclic: true,
+          ),
+          throwsCycleException([1]),
+        );
+      });
+
+      test('a multi-node cycle', () {
+        expect(
+          () => _transitiveClosure<int>(
+            {
+              1: [2],
+              2: [3],
+              3: [4],
+              4: [1],
+            },
+            acyclic: true,
+          ),
+          throwsCycleException([4, 1, 2, 3]),
+        );
+      });
+    });
+
+    group('returns the transitive closure for a graph', () {
+      test('with a single one-node component', () {
+        expect(
+          _transitiveClosure<int>({
+            1: [1],
+          }),
+          equals({
+            1: {1},
+          }),
+        );
+      });
+
+      test('with a single multi-node component', () {
+        expect(
+          _transitiveClosure<int>({
+            1: [2],
+            2: [3],
+            3: [4],
+            4: [1],
+          }),
+          equals({
+            1: {1, 2, 3, 4},
+            2: {1, 2, 3, 4},
+            3: {1, 2, 3, 4},
+            4: {1, 2, 3, 4},
+          }),
+        );
+      });
+
+      test('with a series of multi-node components', () {
+        expect(
+          _transitiveClosure<int>({
+            1: [2],
+            2: [1, 3],
+            3: [4],
+            4: [3, 5],
+            5: [6],
+            6: [5, 7],
+            7: [8],
+            8: [7],
+          }),
+          equals({
+            1: {1, 2, 3, 4, 5, 6, 7, 8},
+            2: {1, 2, 3, 4, 5, 6, 7, 8},
+            3: {3, 4, 5, 6, 7, 8},
+            4: {3, 4, 5, 6, 7, 8},
+            5: {5, 6, 7, 8},
+            6: {5, 6, 7, 8},
+            7: {7, 8},
+            8: {7, 8},
+          }),
+        );
+      });
+
+      test('with a diamond of multi-node components', () {
+        expect(
+          _transitiveClosure<int>({
+            1: [2],
+            2: [1, 3, 5],
+            3: [4],
+            4: [3, 7],
+            5: [6],
+            6: [5, 7],
+            7: [8],
+            8: [7],
+          }),
+          equals({
+            1: {1, 2, 3, 4, 5, 6, 7, 8},
+            2: {1, 2, 3, 4, 5, 6, 7, 8},
+            3: {3, 4, 7, 8},
+            4: {3, 4, 7, 8},
+            5: {5, 6, 7, 8},
+            6: {5, 6, 7, 8},
+            7: {7, 8},
+            8: {7, 8},
+          }),
+        );
+      });
+
+      test('mixed single- and multi-node components', () {
+        expect(
+          _transitiveClosure<int>({
+            1: [2],
+            2: [1, 3],
+            3: [4],
+            4: [5],
+            5: [4, 6],
+            6: [7],
+            7: [8],
+            8: [7],
+          }),
+          equals({
+            1: {1, 2, 3, 4, 5, 6, 7, 8},
+            2: {1, 2, 3, 4, 5, 6, 7, 8},
+            3: {4, 5, 6, 7, 8},
+            4: {4, 5, 6, 7, 8},
+            5: {4, 5, 6, 7, 8},
+            6: {7, 8},
+            7: {7, 8},
+            8: {7, 8},
+          }),
+        );
+      });
+    });
+  });
+}
+
+/// Returns the transitive closure of a graph represented a map from keys to
+/// edges.
+Map<T, Set<T>> _transitiveClosure<T extends Object>(
+  Map<T, List<T>> graph, {
+  bool Function(T, T)? equals,
+  int Function(T)? hashCode,
+  bool acyclic = false,
+}) {
+  assert((equals == null) == (hashCode == null));
+  if (equals != null) {
+    graph = LinkedHashMap(equals: equals, hashCode: hashCode)..addAll(graph);
+  }
+  return transitiveClosure(
+    graph.keys,
+    (node) {
+      expect(graph, contains(node));
+      return graph[node]!;
+    },
+    equals: equals,
+    hashCode: hashCode,
+    acyclic: acyclic,
+  );
+}
diff --git a/pkgs/graphs/test/utils/graph.dart b/pkgs/graphs/test/utils/graph.dart
new file mode 100644
index 0000000..ffa24b5
--- /dev/null
+++ b/pkgs/graphs/test/utils/graph.dart
@@ -0,0 +1,47 @@
+// Copyright (c) 2017, 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.
+
+import 'dart:collection';
+
+import 'utils.dart';
+
+/// A representation of a Graph since none is specified in `lib/`.
+class Graph {
+  final Map<String, List<String>?> _graph;
+
+  Graph(this._graph);
+
+  List<String> edges(String node) => _graph[node] ?? <Never>[];
+
+  Iterable<String> get allNodes => _graph.keys;
+}
+
+class BadGraph {
+  final Map<X, List<X>?> _graph;
+
+  BadGraph(Map<String, List<String>?> values)
+      : _graph = LinkedHashMap(equals: xEquals, hashCode: xHashCode)
+          ..addEntries(
+            values.entries
+                .map((e) => MapEntry(X(e.key), e.value?.map(X.new).toList())),
+          );
+
+  List<X> edges(X node) => _graph[node] ?? <Never>[];
+
+  Iterable<X> get allNodes => _graph.keys;
+}
+
+/// A representation of a Graph where keys can asynchronously be resolved to
+/// real values or to edges.
+class AsyncGraph {
+  final Map<String, List<String>?> graph;
+
+  AsyncGraph(this.graph);
+
+  Future<String?> readNode(String node) async =>
+      graph.containsKey(node) ? node : null;
+
+  Future<Iterable<String>> edges(String key, String? node) async =>
+      graph[key] ?? <Never>[];
+}
diff --git a/pkgs/graphs/test/utils/utils.dart b/pkgs/graphs/test/utils/utils.dart
new file mode 100644
index 0000000..45a42c6
--- /dev/null
+++ b/pkgs/graphs/test/utils/utils.dart
@@ -0,0 +1,37 @@
+// Copyright (c) 2018, 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.
+
+import 'package:graphs/graphs.dart';
+import 'package:test/test.dart';
+
+bool xEquals(X a, X b) => a.value == b.value;
+
+int xHashCode(X a) => a.value.hashCode;
+
+/// Returns a matcher that verifies that a function throws a [CycleException<T>]
+/// with the given [cycle].
+Matcher throwsCycleException<T>(List<T> cycle) => throwsA(
+      allOf([
+        isA<CycleException<T>>(),
+        predicate((exception) {
+          expect((exception as CycleException<T>).cycle, equals(cycle));
+          return true;
+        }),
+      ]),
+    );
+
+class X {
+  final String value;
+
+  X(this.value);
+
+  @override
+  bool operator ==(Object other) => throw UnimplementedError();
+
+  @override
+  int get hashCode => 42;
+
+  @override
+  String toString() => '($value)';
+}
diff --git a/pkgs/mime/.gitignore b/pkgs/mime/.gitignore
new file mode 100644
index 0000000..a433102
--- /dev/null
+++ b/pkgs/mime/.gitignore
@@ -0,0 +1,5 @@
+.packages
+.dart_tool/
+.pub/
+packages
+pubspec.lock
diff --git a/pkgs/mime/AUTHORS b/pkgs/mime/AUTHORS
new file mode 100644
index 0000000..e8063a8
--- /dev/null
+++ b/pkgs/mime/AUTHORS
@@ -0,0 +1,6 @@
+# Below is a list of people and organizations that have contributed
+# to the project. Names should be added to the list like so:
+#
+#   Name/Organization <email address>
+
+Google Inc.
diff --git a/pkgs/mime/CHANGELOG.md b/pkgs/mime/CHANGELOG.md
new file mode 100644
index 0000000..fd5a249
--- /dev/null
+++ b/pkgs/mime/CHANGELOG.md
@@ -0,0 +1,110 @@
+## 2.0.0
+
+* **[Breaking]** `extensionFromMime(String mimeType)` returns `null` instead of `mimeType` for an unknown mime type.
+* Update `extensionFromMime` to return a default extension when a MIME type maps to multiple extensions.
+
+## 1.0.6
+
+* Add `topics` section to `pubspec.yaml`.
+* Move to `dart-lang/tools` monorepo.
+
+## 1.0.5
+
+* Update `video/mp4` mimeType lookup by header bytes.
+* Add `image/heic` mimeType lookup by header bytes.
+* Add `image/heif` mimeType lookup by header bytes.
+* Add m4b mimeType lookup by extension.
+* Add `text/markdown` mimeType lookup by extension.
+* Require Dart 3.2.0.
+
+## 1.0.4
+
+* Changed `.js` to `text/javascript` per 
+  https://datatracker.ietf.org/doc/html/rfc9239.
+* Added `.mjs` as `text/javascript`.
+* Add `application/dicom` mimeType lookup by extension.
+* Require Dart 2.18.
+
+## 1.0.3
+
+* Add application/manifest+json lookup by extension.
+* Add application/toml mimeType lookup by extension.
+* Add audio/aac mimeType lookup by header bytes.
+* Add audio/mpeg mimeType lookup by header bytes.
+* Add audio/ogg mimeType lookup by header bytes.
+* Add audio/weba mimeType lookup by header bytes.
+* Add font/woff2 lookup by extension and header bytes.
+* Add image/avif mimeType lookup by extension.
+* Add image/heic mimeType lookup by extension.
+* Add image/heif mimeType lookup by extension.
+* Change audio/x-aac to audio/aac when detected by extension.
+
+## 1.0.2
+
+* Add audio/x-aiff mimeType lookup by header bytes.
+* Add audio/x-flac mimeType lookup by header bytes.
+* Add audio/x-wav mimeType lookup by header bytes.
+* Add audio/mp4 mimeType lookup by file path.
+
+## 1.0.1
+
+* Add image/webp mimeType lookup by header bytes.
+
+## 1.0.0
+
+* Stable null safety release.
+
+## 1.0.0-nullsafety.0
+
+* Update to null safety.
+
+## 0.9.7
+
+* Add `extensionFromMime` utility function.
+
+## 0.9.6+3
+
+* Change the mime type for Dart source from `application/dart` to `text/x-dart`.
+* Add example.
+* Fix links and code in README.
+
+## 0.9.6+2
+
+* Set max SDK version to `<3.0.0`, and adjust other dependencies.
+
+## 0.9.6+1
+
+* Stop using deprecated constants from the SDK.
+
+## 0.9.6
+
+* Updates to support Dart 2.0 core library changes (wave
+  2.2). See [issue 31847][sdk#31847] for details.
+
+  [sdk#31847]: https://github.com/dart-lang/sdk/issues/31847
+
+## 0.9.5
+
+* Add support for the WebAssembly format.
+
+## 0.9.4
+
+* Updated Dart SDK requirement to `>= 1.8.3 <2.0.0`
+
+* Strong-mode clean.
+
+* Added support for glTF text and binary formats.
+
+## 0.9.3
+
+* Fixed erroneous behavior for listening and when pausing/resuming
+  stream of parts.
+
+## 0.9.2
+
+* Fixed erroneous behavior when pausing/canceling stream of parts but already
+  listened to one part.
+
+## 0.9.1
+
+* Handle parsing of MIME multipart content with no parts.
diff --git a/pkgs/mime/CONTRIBUTING.md b/pkgs/mime/CONTRIBUTING.md
new file mode 100644
index 0000000..463063a
--- /dev/null
+++ b/pkgs/mime/CONTRIBUTING.md
@@ -0,0 +1,37 @@
+Want to contribute? Great! First, read this page (including the small print at
+the end).
+
+### Before you contribute
+Before we can use your code, you must sign the
+[Google Individual Contributor License Agreement](https://cla.developers.google.com/about/google-individual)
+(CLA), which you can do online. The CLA is necessary mainly because you own the
+copyright to your changes, even after your contribution becomes part of our
+codebase, so we need your permission to use and distribute your code. We also
+need to be sure of various other things—for instance that you'll tell us if you
+know that your code infringes on other people's patents. You don't have to sign
+the CLA until after you've submitted your code for review and a member has
+approved it, but you must do it before we can put your code into our codebase.
+
+Before you start working on a larger contribution, you should get in touch with
+us first through the issue tracker with your idea so that we can help out and
+possibly guide you. Coordinating up front makes it much easier to avoid
+frustration later on.
+
+### Code reviews
+All submissions, including submissions by project members, require review.
+
+### File headers
+All files in the project must start with the following header.
+
+    // Copyright (c) 2015, 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.
+
+### The small print
+Contributions made by corporations are covered by a different agreement than the
+one above, the
+[Software Grant and Corporate Contributor License Agreement](https://developers.google.com/open-source/cla/corporate).
+
+### Adding an extension / MIME type mapping
+If a MIME type ends up with multiple extensions, it is recommended to define a 
+preferred extension in `_defaultMimeTypeMap` in [extension.dart](lib/src/extension.dart). 
\ No newline at end of file
diff --git a/pkgs/mime/LICENSE b/pkgs/mime/LICENSE
new file mode 100644
index 0000000..dbd2843
--- /dev/null
+++ b/pkgs/mime/LICENSE
@@ -0,0 +1,27 @@
+Copyright 2015, the Dart project authors. 
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+    * Redistributions of source code must retain the above copyright
+      notice, this list of conditions and the following disclaimer.
+    * Redistributions in binary form must reproduce the above
+      copyright notice, this list of conditions and the following
+      disclaimer in the documentation and/or other materials provided
+      with the distribution.
+    * Neither the name of Google LLC nor the names of its
+      contributors may be used to endorse or promote products derived
+      from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
diff --git a/pkgs/mime/README.md b/pkgs/mime/README.md
new file mode 100644
index 0000000..da06de6
--- /dev/null
+++ b/pkgs/mime/README.md
@@ -0,0 +1,70 @@
+[![Build Status](https://github.com/dart-lang/tools/actions/workflows/mime.yml/badge.svg)](https://github.com/dart-lang/tools/actions/workflows/mime.yml)
+[![Pub Package](https://img.shields.io/pub/v/mime.svg)](https://pub.dev/packages/mime)
+[![package publisher](https://img.shields.io/pub/publisher/mime.svg)](https://pub.dev/packages/mime/publisher)
+
+Package for working with MIME type definitions and for processing
+streams of MIME multipart media types.
+
+## Determining the MIME type for a file
+
+The `MimeTypeResolver` class can be used to determine the MIME type of
+a file. It supports both using the extension of the file name and
+looking at magic bytes from the beginning of the file.
+
+There is a builtin instance of `MimeTypeResolver` accessible through
+the top level function `lookupMimeType`. This builtin instance has
+the most common file name extensions and magic bytes registered.
+
+```dart
+import 'package:mime/mime.dart';
+
+void main() {
+  print(lookupMimeType('test.html'));
+  // text/html
+
+  print(lookupMimeType('test', headerBytes: [0xFF, 0xD8]));
+  // image/jpeg
+
+  print(lookupMimeType('test.html', headerBytes: [0xFF, 0xD8]));
+  // image/jpeg
+}
+```
+
+You can build you own resolver by creating an instance of
+`MimeTypeResolver` and adding file name extensions and magic bytes
+using `addExtension` and `addMagicNumber`.
+
+## Processing MIME multipart media types
+
+The class `MimeMultipartTransformer` is used to process a `Stream` of
+bytes encoded using a MIME multipart media types encoding. The
+transformer provides a new `Stream` of `MimeMultipart` objects each of
+which have the headers and the content of each part. The content of a
+part is provided as a stream of bytes.
+
+Below is an example showing how to process an HTTP request and print
+the length of the content of each part.
+
+```dart
+// HTTP request with content type multipart/form-data.
+HttpRequest request = ...;
+// Determine the boundary form the content type header
+String boundary = request.headers.contentType.parameters['boundary'];
+
+// Process the body just calculating the length of each part.
+request
+    .transform(new MimeMultipartTransformer(boundary))
+    .map((part) => part.fold(0, (p, d) => p + d))
+    .listen((length) => print('Part with length $length'));
+```
+
+## Determining file extension by MIME type
+
+The top level function `extensionFromMime` can be used to determine the
+file extension of a given MIME type.
+
+```dart
+print(extensionFromMime('text/html'));  // Prints "html".
+print(extensionFromMime('image/jpeg'));  // Prints "jpg".
+print(extensionFromMime('application/pdf'));  // Prints "pdf".
+```
diff --git a/pkgs/mime/analysis_options.yaml b/pkgs/mime/analysis_options.yaml
new file mode 100644
index 0000000..44b61cf
--- /dev/null
+++ b/pkgs/mime/analysis_options.yaml
@@ -0,0 +1,34 @@
+# https://dart.dev/tools/analysis#the-analysis-options-file
+include: package:dart_flutter_team_lints/analysis_options.yaml
+
+analyzer:
+  language:
+    strict-casts: true
+    strict-inference: true
+    strict-raw-types: true
+
+linter:
+  rules:
+    - avoid_bool_literals_in_conditional_expressions
+    - avoid_classes_with_only_static_members
+    - avoid_private_typedef_functions
+    - avoid_redundant_argument_values
+    - avoid_returning_this
+    - avoid_unused_constructor_parameters
+    - avoid_void_async
+    - cancel_subscriptions
+    - join_return_with_assignment
+    - literal_only_boolean_expressions
+    - missing_whitespace_between_adjacent_strings
+    - no_adjacent_strings_in_list
+    - no_runtimeType_toString
+    - package_api_docs
+    - prefer_const_declarations
+    - prefer_expression_function_bodies
+    - prefer_final_locals
+    - unnecessary_await_in_return
+    - unnecessary_breaks
+    - unnecessary_raw_strings
+    - use_if_null_to_convert_nulls_to_bools
+    - use_raw_strings
+    - use_string_buffers
diff --git a/pkgs/mime/example/example.dart b/pkgs/mime/example/example.dart
new file mode 100644
index 0000000..b54f8e7
--- /dev/null
+++ b/pkgs/mime/example/example.dart
@@ -0,0 +1,16 @@
+// Copyright (c) 2024, 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.
+
+import 'package:mime/mime.dart';
+
+void main() {
+  print(lookupMimeType('test.html'));
+  // text/html
+
+  print(lookupMimeType('test', headerBytes: [0xFF, 0xD8]));
+  // image/jpeg
+
+  print(lookupMimeType('test.html', headerBytes: [0xFF, 0xD8]));
+  // image/jpeg
+}
diff --git a/pkgs/mime/lib/mime.dart b/pkgs/mime/lib/mime.dart
new file mode 100644
index 0000000..cb45098
--- /dev/null
+++ b/pkgs/mime/lib/mime.dart
@@ -0,0 +1,15 @@
+// Copyright (c) 2013, 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.
+
+/// Help for working with file format identifiers
+/// such as `text/html` and `image/png`.
+///
+/// More details, including a list of types, are in the Wikipedia article
+/// [Internet media type](http://en.wikipedia.org/wiki/Internet_media_type).
+library;
+
+export 'src/extension.dart';
+export 'src/mime_multipart_transformer.dart';
+export 'src/mime_shared.dart';
+export 'src/mime_type.dart';
diff --git a/pkgs/mime/lib/src/bound_multipart_stream.dart b/pkgs/mime/lib/src/bound_multipart_stream.dart
new file mode 100644
index 0000000..03b213b
--- /dev/null
+++ b/pkgs/mime/lib/src/bound_multipart_stream.dart
@@ -0,0 +1,372 @@
+// 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.
+
+import 'dart:async';
+import 'dart:convert';
+
+import 'char_code.dart' as char_code;
+import 'mime_shared.dart';
+
+/// Bytes for `()<>@,;:\\"/[]?={} \t`.
+const _separators = {
+  40, 41, 60, 62, 64, 44, 59, 58, 92, 34, 47, 91, 93, 63, 61, 123, 125, 32, 9 //
+};
+
+bool _isTokenChar(int byte) =>
+    byte > 31 && byte < 128 && !_separators.contains(byte);
+
+int _toLowerCase(int byte) {
+  const delta = char_code.lowerA - char_code.upperA;
+  return (char_code.upperA <= byte && byte <= char_code.upperZ)
+      ? byte + delta
+      : byte;
+}
+
+void _expectByteValue(int val1, int val2) {
+  if (val1 != val2) {
+    throw const MimeMultipartException('Failed to parse multipart mime 1');
+  }
+}
+
+void _expectWhitespace(int byte) {
+  if (byte != char_code.sp && byte != char_code.ht) {
+    throw const MimeMultipartException('Failed to parse multipart mime 2');
+  }
+}
+
+class _MimeMultipart extends MimeMultipart {
+  @override
+  final Map<String, String> headers;
+  final Stream<List<int>> _stream;
+
+  _MimeMultipart(this.headers, this._stream);
+
+  @override
+  StreamSubscription<List<int>> listen(
+    void Function(List<int> data)? onData, {
+    void Function()? onDone,
+    Function? onError,
+    bool? cancelOnError,
+  }) =>
+      _stream.listen(
+        onData,
+        onDone: onDone,
+        onError: onError,
+        cancelOnError: cancelOnError,
+      );
+}
+
+class BoundMultipartStream {
+  static const int _startCode = 0;
+  static const int _boundaryEndingCode = 1;
+  static const int _boundaryEndCode = 2;
+  static const int _headerStartCode = 3;
+  static const int _headerFieldCode = 4;
+  static const int _headerValueStartCode = 5;
+  static const int _headerValueCode = 6;
+  static const int _headerValueFoldingOrEndingCode = 7;
+  static const int _headerValueFoldOrEndCode = 8;
+  static const int _headerEndingCode = 9;
+  static const int _contentCode = 10;
+  static const int _lastBoundaryDash2Code = 11;
+  static const int _lastBoundaryEndingCode = 12;
+  static const int _lastBoundaryEndCode = 13;
+  static const int _doneCode = 14;
+  static const int _failCode = 15;
+
+  final List<int> _boundary;
+  final List<int> _headerField = [];
+  final List<int> _headerValue = [];
+
+  // The following states belong to `_controller`, state changes will not be
+  // immediately acted upon but rather only after the current
+  // `_multipartController` is done.
+  static const int _controllerStateIdle = 0;
+  static const int _controllerStateActive = 1;
+  static const int _controllerStatePaused = 2;
+  static const int _controllerStateCanceled = 3;
+
+  int _controllerState = _controllerStateIdle;
+
+  final _controller = StreamController<MimeMultipart>(sync: true);
+
+  Stream<MimeMultipart> get stream => _controller.stream;
+
+  late StreamSubscription<void> _subscription;
+
+  StreamController<List<int>>? _multipartController;
+  Map<String, String>? _headers;
+
+  int _state = _startCode;
+  int _boundaryIndex = 2;
+
+  /// Current index into [_buffer].
+  ///
+  /// If index is negative then it is the index into the artificial prefix of
+  /// the boundary string.
+  int _index = 0;
+  List<int> _buffer = _placeholderBuffer;
+
+  BoundMultipartStream(this._boundary, Stream<List<int>> stream) {
+    _controller
+      ..onPause = _pauseStream
+      ..onResume = _resumeStream
+      ..onCancel = () {
+        _controllerState = _controllerStateCanceled;
+        _tryPropagateControllerState();
+      }
+      ..onListen = () {
+        _controllerState = _controllerStateActive;
+        _subscription = stream.listen((data) {
+          assert(_buffer == _placeholderBuffer);
+          _subscription.pause();
+          _buffer = data;
+          _index = 0;
+          _parse();
+        }, onDone: () {
+          if (_state != _doneCode) {
+            _controller
+                .addError(const MimeMultipartException('Bad multipart ending'));
+          }
+          _controller.close();
+        }, onError: _controller.addError);
+      };
+  }
+
+  void _resumeStream() {
+    assert(_controllerState == _controllerStatePaused);
+    _controllerState = _controllerStateActive;
+    _tryPropagateControllerState();
+  }
+
+  void _pauseStream() {
+    _controllerState = _controllerStatePaused;
+    _tryPropagateControllerState();
+  }
+
+  void _tryPropagateControllerState() {
+    if (_multipartController == null) {
+      switch (_controllerState) {
+        case _controllerStateActive:
+          if (_subscription.isPaused) _subscription.resume();
+        case _controllerStatePaused:
+          if (!_subscription.isPaused) _subscription.pause();
+        case _controllerStateCanceled:
+          _subscription.cancel();
+        default:
+          throw StateError('This code should never be reached.');
+      }
+    }
+  }
+
+  void _parse() {
+    // Number of boundary bytes to artificially place before the supplied data.
+    // The data to parse might be 'artificially' prefixed with a
+    // partial match of the boundary.
+    final boundaryPrefix = _boundaryIndex;
+    // Position where content starts. Will be null if no known content
+    // start exists. Will be negative of the content starts in the
+    // boundary prefix. Will be zero or position if the content starts
+    // in the current buffer.
+    var contentStartIndex =
+        _state == _contentCode && _boundaryIndex == 0 ? 0 : null;
+
+    // Function to report content data for the current part. The data
+    // reported is from the current content start index up til the
+    // current index. As the data can be artificially prefixed with a
+    // prefix of the boundary both the content start index and index
+    // can be negative.
+    void reportData() {
+      if (contentStartIndex! < 0) {
+        final contentLength = boundaryPrefix + _index - _boundaryIndex;
+        if (contentLength <= boundaryPrefix) {
+          _multipartController!.add(_boundary.sublist(0, contentLength));
+        } else {
+          _multipartController!.add(_boundary.sublist(0, boundaryPrefix));
+          _multipartController!
+              .add(_buffer.sublist(0, contentLength - boundaryPrefix));
+        }
+      } else {
+        final contentEndIndex = _index - _boundaryIndex;
+        _multipartController!
+            .add(_buffer.sublist(contentStartIndex, contentEndIndex));
+      }
+    }
+
+    while (
+        _index < _buffer.length && _state != _failCode && _state != _doneCode) {
+      final byte =
+          _index < 0 ? _boundary[boundaryPrefix + _index] : _buffer[_index];
+      switch (_state) {
+        case _startCode:
+          if (byte == _boundary[_boundaryIndex]) {
+            _boundaryIndex++;
+            if (_boundaryIndex == _boundary.length) {
+              _state = _boundaryEndingCode;
+              _boundaryIndex = 0;
+            }
+          } else {
+            // Restart matching of the boundary.
+            _index = _index - _boundaryIndex;
+            _boundaryIndex = 0;
+          }
+
+        case _boundaryEndingCode:
+          if (byte == char_code.cr) {
+            _state = _boundaryEndCode;
+          } else if (byte == char_code.dash) {
+            _state = _lastBoundaryDash2Code;
+          } else {
+            _expectWhitespace(byte);
+          }
+
+        case _boundaryEndCode:
+          _expectByteValue(byte, char_code.lf);
+          _multipartController?.close();
+          if (_multipartController != null) {
+            _multipartController = null;
+            _tryPropagateControllerState();
+          }
+          _state = _headerStartCode;
+
+        case _headerStartCode:
+          _headers = <String, String>{};
+          if (byte == char_code.cr) {
+            _state = _headerEndingCode;
+          } else {
+            // Start of new header field.
+            _headerField.add(_toLowerCase(byte));
+            _state = _headerFieldCode;
+          }
+
+        case _headerFieldCode:
+          if (byte == char_code.colon) {
+            _state = _headerValueStartCode;
+          } else {
+            if (!_isTokenChar(byte)) {
+              throw const MimeMultipartException('Invalid header field name');
+            }
+            _headerField.add(_toLowerCase(byte));
+          }
+
+        case _headerValueStartCode:
+          if (byte == char_code.cr) {
+            _state = _headerValueFoldingOrEndingCode;
+          } else if (byte != char_code.sp && byte != char_code.ht) {
+            // Start of new header value.
+            _headerValue.add(byte);
+            _state = _headerValueCode;
+          }
+
+        case _headerValueCode:
+          if (byte == char_code.cr) {
+            _state = _headerValueFoldingOrEndingCode;
+          } else {
+            _headerValue.add(byte);
+          }
+
+        case _headerValueFoldingOrEndingCode:
+          _expectByteValue(byte, char_code.lf);
+          _state = _headerValueFoldOrEndCode;
+
+        case _headerValueFoldOrEndCode:
+          if (byte == char_code.sp || byte == char_code.ht) {
+            _state = _headerValueStartCode;
+          } else {
+            final headerField = utf8.decode(_headerField);
+            final headerValue = utf8.decode(_headerValue);
+            _headers![headerField.toLowerCase()] = headerValue;
+            _headerField.clear();
+            _headerValue.clear();
+            if (byte == char_code.cr) {
+              _state = _headerEndingCode;
+            } else {
+              // Start of new header field.
+              _headerField.add(_toLowerCase(byte));
+              _state = _headerFieldCode;
+            }
+          }
+
+        case _headerEndingCode:
+          _expectByteValue(byte, char_code.lf);
+          _multipartController = StreamController(
+              sync: true,
+              onListen: () {
+                if (_subscription.isPaused) _subscription.resume();
+              },
+              onPause: _subscription.pause,
+              onResume: _subscription.resume);
+          _controller
+              .add(_MimeMultipart(_headers!, _multipartController!.stream));
+          _headers = null;
+          _state = _contentCode;
+          contentStartIndex = _index + 1;
+
+        case _contentCode:
+          if (byte == _boundary[_boundaryIndex]) {
+            _boundaryIndex++;
+            if (_boundaryIndex == _boundary.length) {
+              if (contentStartIndex != null) {
+                _index++;
+                reportData();
+                _index--;
+              }
+              _multipartController!.close();
+              _multipartController = null;
+              _tryPropagateControllerState();
+              _boundaryIndex = 0;
+              _state = _boundaryEndingCode;
+            }
+          } else {
+            // Restart matching of the boundary.
+            _index = _index - _boundaryIndex;
+            contentStartIndex ??= _index;
+            _boundaryIndex = 0;
+          }
+
+        case _lastBoundaryDash2Code:
+          _expectByteValue(byte, char_code.dash);
+          _state = _lastBoundaryEndingCode;
+
+        case _lastBoundaryEndingCode:
+          if (byte == char_code.cr) {
+            _state = _lastBoundaryEndCode;
+          } else {
+            _expectWhitespace(byte);
+          }
+
+        case _lastBoundaryEndCode:
+          _expectByteValue(byte, char_code.lf);
+          _multipartController?.close();
+          if (_multipartController != null) {
+            _multipartController = null;
+            _tryPropagateControllerState();
+          }
+          _state = _doneCode;
+
+        default:
+          // Should be unreachable.
+          assert(false);
+      }
+
+      // Move to the next byte.
+      _index++;
+    }
+
+    // Report any known content.
+    if (_state == _contentCode && contentStartIndex != null) {
+      reportData();
+    }
+
+    // Resume if at end.
+    if (_index == _buffer.length) {
+      _buffer = _placeholderBuffer;
+      _index = 0;
+      _subscription.resume();
+    }
+  }
+}
+
+// Used as a placeholder instead of having a nullable buffer.
+const _placeholderBuffer = <int>[];
diff --git a/pkgs/mime/lib/src/char_code.dart b/pkgs/mime/lib/src/char_code.dart
new file mode 100644
index 0000000..4cca1b1
--- /dev/null
+++ b/pkgs/mime/lib/src/char_code.dart
@@ -0,0 +1,13 @@
+// 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.
+
+const int ht = 9;
+const int lf = 10;
+const int cr = 13;
+const int sp = 32;
+const int dash = 45;
+const int colon = 58;
+const int upperA = 65;
+const int upperZ = 90;
+const int lowerA = 97;
diff --git a/pkgs/mime/lib/src/default_extension_map.dart b/pkgs/mime/lib/src/default_extension_map.dart
new file mode 100644
index 0000000..287c957
--- /dev/null
+++ b/pkgs/mime/lib/src/default_extension_map.dart
@@ -0,0 +1,1012 @@
+// Copyright (c) 2013, 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.
+
+const Map<String, String> defaultExtensionMap = <String, String>{
+  '123': 'application/vnd.lotus-1-2-3',
+  '3dml': 'text/vnd.in3d.3dml',
+  '3ds': 'image/x-3ds',
+  '3g2': 'video/3gpp2',
+  '3gp': 'video/3gpp',
+  '7z': 'application/x-7z-compressed',
+  'aab': 'application/x-authorware-bin',
+  'aac': 'audio/aac',
+  'aam': 'application/x-authorware-map',
+  'aas': 'application/x-authorware-seg',
+  'abw': 'application/x-abiword',
+  'ac': 'application/pkix-attr-cert',
+  'acc': 'application/vnd.americandynamics.acc',
+  'ace': 'application/x-ace-compressed',
+  'acu': 'application/vnd.acucobol',
+  'acutc': 'application/vnd.acucorp',
+  'adp': 'audio/adpcm',
+  'aep': 'application/vnd.audiograph',
+  'afm': 'application/x-font-type1',
+  'afp': 'application/vnd.ibm.modcap',
+  'ahead': 'application/vnd.ahead.space',
+  'ai': 'application/postscript',
+  'aif': 'audio/x-aiff',
+  'aifc': 'audio/x-aiff',
+  'aiff': 'audio/x-aiff',
+  'air': 'application/vnd.adobe.air-application-installer-package+zip',
+  'ait': 'application/vnd.dvb.ait',
+  'ami': 'application/vnd.amiga.ami',
+  'apk': 'application/vnd.android.package-archive',
+  'appcache': 'text/cache-manifest',
+  'application': 'application/x-ms-application',
+  'apr': 'application/vnd.lotus-approach',
+  'arc': 'application/x-freearc',
+  'asc': 'application/pgp-signature',
+  'asf': 'video/x-ms-asf',
+  'asm': 'text/x-asm',
+  'aso': 'application/vnd.accpac.simply.aso',
+  'asx': 'video/x-ms-asf',
+  'atc': 'application/vnd.acucorp',
+  'atom': 'application/atom+xml',
+  'atomcat': 'application/atomcat+xml',
+  'atomsvc': 'application/atomsvc+xml',
+  'atx': 'application/vnd.antix.game-component',
+  'au': 'audio/basic',
+  'avi': 'video/x-msvideo',
+  'avif': 'image/avif',
+  'aw': 'application/applixware',
+  'azf': 'application/vnd.airzip.filesecure.azf',
+  'azs': 'application/vnd.airzip.filesecure.azs',
+  'azw': 'application/vnd.amazon.ebook',
+  'bat': 'application/x-msdownload',
+  'bcpio': 'application/x-bcpio',
+  'bdf': 'application/x-font-bdf',
+  'bdm': 'application/vnd.syncml.dm+wbxml',
+  'bed': 'application/vnd.realvnc.bed',
+  'bh2': 'application/vnd.fujitsu.oasysprs',
+  'bin': 'application/octet-stream',
+  'blb': 'application/x-blorb',
+  'blorb': 'application/x-blorb',
+  'bmi': 'application/vnd.bmi',
+  'bmp': 'image/bmp',
+  'book': 'application/vnd.framemaker',
+  'box': 'application/vnd.previewsystems.box',
+  'boz': 'application/x-bzip2',
+  'bpk': 'application/octet-stream',
+  'btif': 'image/prs.btif',
+  'bz': 'application/x-bzip',
+  'bz2': 'application/x-bzip2',
+  'c': 'text/x-c',
+  'c11amc': 'application/vnd.cluetrust.cartomobile-config',
+  'c11amz': 'application/vnd.cluetrust.cartomobile-config-pkg',
+  'c4d': 'application/vnd.clonk.c4group',
+  'c4f': 'application/vnd.clonk.c4group',
+  'c4g': 'application/vnd.clonk.c4group',
+  'c4p': 'application/vnd.clonk.c4group',
+  'c4u': 'application/vnd.clonk.c4group',
+  'cab': 'application/vnd.ms-cab-compressed',
+  'caf': 'audio/x-caf',
+  'cap': 'application/vnd.tcpdump.pcap',
+  'car': 'application/vnd.curl.car',
+  'cat': 'application/vnd.ms-pki.seccat',
+  'cb7': 'application/x-cbr',
+  'cba': 'application/x-cbr',
+  'cbr': 'application/x-cbr',
+  'cbt': 'application/x-cbr',
+  'cbz': 'application/x-cbr',
+  'cc': 'text/x-c',
+  'cct': 'application/x-director',
+  'ccxml': 'application/ccxml+xml',
+  'cdbcmsg': 'application/vnd.contact.cmsg',
+  'cdf': 'application/x-netcdf',
+  'cdkey': 'application/vnd.mediastation.cdkey',
+  'cdmia': 'application/cdmi-capability',
+  'cdmic': 'application/cdmi-container',
+  'cdmid': 'application/cdmi-domain',
+  'cdmio': 'application/cdmi-object',
+  'cdmiq': 'application/cdmi-queue',
+  'cdx': 'chemical/x-cdx',
+  'cdxml': 'application/vnd.chemdraw+xml',
+  'cdy': 'application/vnd.cinderella',
+  'cer': 'application/pkix-cert',
+  'cfs': 'application/x-cfs-compressed',
+  'cgm': 'image/cgm',
+  'chat': 'application/x-chat',
+  'chm': 'application/vnd.ms-htmlhelp',
+  'chrt': 'application/vnd.kde.kchart',
+  'cif': 'chemical/x-cif',
+  'cii': 'application/vnd.anser-web-certificate-issue-initiation',
+  'cil': 'application/vnd.ms-artgalry',
+  'cla': 'application/vnd.claymore',
+  'class': 'application/java-vm',
+  'clkk': 'application/vnd.crick.clicker.keyboard',
+  'clkp': 'application/vnd.crick.clicker.palette',
+  'clkt': 'application/vnd.crick.clicker.template',
+  'clkw': 'application/vnd.crick.clicker.wordbank',
+  'clkx': 'application/vnd.crick.clicker',
+  'clp': 'application/x-msclip',
+  'cmc': 'application/vnd.cosmocaller',
+  'cmdf': 'chemical/x-cmdf',
+  'cml': 'chemical/x-cml',
+  'cmp': 'application/vnd.yellowriver-custom-menu',
+  'cmx': 'image/x-cmx',
+  'cod': 'application/vnd.rim.cod',
+  'com': 'application/x-msdownload',
+  'conf': 'text/plain',
+  'cpio': 'application/x-cpio',
+  'cpp': 'text/x-c',
+  'cpt': 'application/mac-compactpro',
+  'crd': 'application/x-mscardfile',
+  'crl': 'application/pkix-crl',
+  'crt': 'application/x-x509-ca-cert',
+  'cryptonote': 'application/vnd.rig.cryptonote',
+  'csh': 'application/x-csh',
+  'csml': 'chemical/x-csml',
+  'csp': 'application/vnd.commonspace',
+  'css': 'text/css',
+  'cst': 'application/x-director',
+  'csv': 'text/csv',
+  'cu': 'application/cu-seeme',
+  'curl': 'text/vnd.curl',
+  'cww': 'application/prs.cww',
+  'cxt': 'application/x-director',
+  'cxx': 'text/x-c',
+  'dae': 'model/vnd.collada+xml',
+  'daf': 'application/vnd.mobius.daf',
+  'dart': 'text/x-dart',
+  'dataless': 'application/vnd.fdsn.seed',
+  'davmount': 'application/davmount+xml',
+  'dbk': 'application/docbook+xml',
+  'dcm': 'application/dicom',
+  'dcr': 'application/x-director',
+  'dcurl': 'text/vnd.curl.dcurl',
+  'dd2': 'application/vnd.oma.dd2+xml',
+  'ddd': 'application/vnd.fujixerox.ddd',
+  'deb': 'application/x-debian-package',
+  'def': 'text/plain',
+  'deploy': 'application/octet-stream',
+  'der': 'application/x-x509-ca-cert',
+  'dfac': 'application/vnd.dreamfactory',
+  'dgc': 'application/x-dgc-compressed',
+  'dic': 'text/x-c',
+  'dir': 'application/x-director',
+  'dis': 'application/vnd.mobius.dis',
+  'dist': 'application/octet-stream',
+  'distz': 'application/octet-stream',
+  'djv': 'image/vnd.djvu',
+  'djvu': 'image/vnd.djvu',
+  'dll': 'application/x-msdownload',
+  'dmg': 'application/x-apple-diskimage',
+  'dmp': 'application/vnd.tcpdump.pcap',
+  'dms': 'application/octet-stream',
+  'dna': 'application/vnd.dna',
+  'doc': 'application/msword',
+  'docm': 'application/vnd.ms-word.document.macroenabled.12',
+  'docx':
+      'application/vnd.openxmlformats-officedocument.wordprocessingml.document',
+  'dot': 'application/msword',
+  'dotm': 'application/vnd.ms-word.template.macroenabled.12',
+  'dotx':
+      'application/vnd.openxmlformats-officedocument.wordprocessingml.template',
+  'dp': 'application/vnd.osgi.dp',
+  'dpg': 'application/vnd.dpgraph',
+  'dra': 'audio/vnd.dra',
+  'dsc': 'text/prs.lines.tag',
+  'dssc': 'application/dssc+der',
+  'dtb': 'application/x-dtbook+xml',
+  'dtd': 'application/xml-dtd',
+  'dts': 'audio/vnd.dts',
+  'dtshd': 'audio/vnd.dts.hd',
+  'dump': 'application/octet-stream',
+  'dvb': 'video/vnd.dvb.file',
+  'dvi': 'application/x-dvi',
+  'dwf': 'model/vnd.dwf',
+  'dwg': 'image/vnd.dwg',
+  'dxf': 'image/vnd.dxf',
+  'dxp': 'application/vnd.spotfire.dxp',
+  'dxr': 'application/x-director',
+  'ecelp4800': 'audio/vnd.nuera.ecelp4800',
+  'ecelp7470': 'audio/vnd.nuera.ecelp7470',
+  'ecelp9600': 'audio/vnd.nuera.ecelp9600',
+  'ecma': 'application/ecmascript',
+  'edm': 'application/vnd.novadigm.edm',
+  'edx': 'application/vnd.novadigm.edx',
+  'efif': 'application/vnd.picsel',
+  'ei6': 'application/vnd.pg.osasli',
+  'elc': 'application/octet-stream',
+  'emf': 'application/x-msmetafile',
+  'eml': 'message/rfc822',
+  'emma': 'application/emma+xml',
+  'emz': 'application/x-msmetafile',
+  'eol': 'audio/vnd.digital-winds',
+  'eot': 'application/vnd.ms-fontobject',
+  'eps': 'application/postscript',
+  'epub': 'application/epub+zip',
+  'es3': 'application/vnd.eszigno3+xml',
+  'esa': 'application/vnd.osgi.subsystem',
+  'esf': 'application/vnd.epson.esf',
+  'et3': 'application/vnd.eszigno3+xml',
+  'etx': 'text/x-setext',
+  'eva': 'application/x-eva',
+  'evy': 'application/x-envoy',
+  'exe': 'application/x-msdownload',
+  'exi': 'application/exi',
+  'ext': 'application/vnd.novadigm.ext',
+  'ez': 'application/andrew-inset',
+  'ez2': 'application/vnd.ezpix-album',
+  'ez3': 'application/vnd.ezpix-package',
+  'f': 'text/x-fortran',
+  'f4v': 'video/x-f4v',
+  'f77': 'text/x-fortran',
+  'f90': 'text/x-fortran',
+  'fbs': 'image/vnd.fastbidsheet',
+  'fcdt': 'application/vnd.adobe.formscentral.fcdt',
+  'fcs': 'application/vnd.isac.fcs',
+  'fdf': 'application/vnd.fdf',
+  'fe_launch': 'application/vnd.denovo.fcselayout-link',
+  'fg5': 'application/vnd.fujitsu.oasysgp',
+  'fgd': 'application/x-director',
+  'fh': 'image/x-freehand',
+  'fh4': 'image/x-freehand',
+  'fh5': 'image/x-freehand',
+  'fh7': 'image/x-freehand',
+  'fhc': 'image/x-freehand',
+  'fig': 'application/x-xfig',
+  'flac': 'audio/x-flac',
+  'fli': 'video/x-fli',
+  'flo': 'application/vnd.micrografx.flo',
+  'flv': 'video/x-flv',
+  'flw': 'application/vnd.kde.kivio',
+  'flx': 'text/vnd.fmi.flexstor',
+  'fly': 'text/vnd.fly',
+  'fm': 'application/vnd.framemaker',
+  'fnc': 'application/vnd.frogans.fnc',
+  'for': 'text/x-fortran',
+  'fpx': 'image/vnd.fpx',
+  'frame': 'application/vnd.framemaker',
+  'fsc': 'application/vnd.fsc.weblaunch',
+  'fst': 'image/vnd.fst',
+  'ftc': 'application/vnd.fluxtime.clip',
+  'fti': 'application/vnd.anser-web-funds-transfer-initiation',
+  'fvt': 'video/vnd.fvt',
+  'fxp': 'application/vnd.adobe.fxp',
+  'fxpl': 'application/vnd.adobe.fxp',
+  'fzs': 'application/vnd.fuzzysheet',
+  'g2w': 'application/vnd.geoplan',
+  'g3': 'image/g3fax',
+  'g3w': 'application/vnd.geospace',
+  'gac': 'application/vnd.groove-account',
+  'gam': 'application/x-tads',
+  'gbr': 'application/rpki-ghostbusters',
+  'gca': 'application/x-gca-compressed',
+  'gdl': 'model/vnd.gdl',
+  'geo': 'application/vnd.dynageo',
+  'gex': 'application/vnd.geometry-explorer',
+  'ggb': 'application/vnd.geogebra.file',
+  'ggt': 'application/vnd.geogebra.tool',
+  'ghf': 'application/vnd.groove-help',
+  'gif': 'image/gif',
+  'gim': 'application/vnd.groove-identity-message',
+  'glb': 'model/gltf-binary',
+  'gltf': 'model/gltf+json',
+  'gml': 'application/gml+xml',
+  'gmx': 'application/vnd.gmx',
+  'gnumeric': 'application/x-gnumeric',
+  'gph': 'application/vnd.flographit',
+  'gpx': 'application/gpx+xml',
+  'gqf': 'application/vnd.grafeq',
+  'gqs': 'application/vnd.grafeq',
+  'gram': 'application/srgs',
+  'gramps': 'application/x-gramps-xml',
+  'gre': 'application/vnd.geometry-explorer',
+  'grv': 'application/vnd.groove-injector',
+  'grxml': 'application/srgs+xml',
+  'gsf': 'application/x-font-ghostscript',
+  'gtar': 'application/x-gtar',
+  'gtm': 'application/vnd.groove-tool-message',
+  'gtw': 'model/vnd.gtw',
+  'gv': 'text/vnd.graphviz',
+  'gxf': 'application/gxf',
+  'gxt': 'application/vnd.geonext',
+  'h': 'text/x-c',
+  'h261': 'video/h261',
+  'h263': 'video/h263',
+  'h264': 'video/h264',
+  'hal': 'application/vnd.hal+xml',
+  'hbci': 'application/vnd.hbci',
+  'hdf': 'application/x-hdf',
+  'heic': 'image/heic',
+  'heif': 'image/heif',
+  'hh': 'text/x-c',
+  'hlp': 'application/winhlp',
+  'hpgl': 'application/vnd.hp-hpgl',
+  'hpid': 'application/vnd.hp-hpid',
+  'hps': 'application/vnd.hp-hps',
+  'hqx': 'application/mac-binhex40',
+  'htke': 'application/vnd.kenameaapp',
+  'htm': 'text/html',
+  'html': 'text/html',
+  'hvd': 'application/vnd.yamaha.hv-dic',
+  'hvp': 'application/vnd.yamaha.hv-voice',
+  'hvs': 'application/vnd.yamaha.hv-script',
+  'i2g': 'application/vnd.intergeo',
+  'icc': 'application/vnd.iccprofile',
+  'ice': 'x-conference/x-cooltalk',
+  'icm': 'application/vnd.iccprofile',
+  'ico': 'image/x-icon',
+  'ics': 'text/calendar',
+  'ief': 'image/ief',
+  'ifb': 'text/calendar',
+  'ifm': 'application/vnd.shana.informed.formdata',
+  'iges': 'model/iges',
+  'igl': 'application/vnd.igloader',
+  'igm': 'application/vnd.insors.igm',
+  'igs': 'model/iges',
+  'igx': 'application/vnd.micrografx.igx',
+  'iif': 'application/vnd.shana.informed.interchange',
+  'imp': 'application/vnd.accpac.simply.imp',
+  'ims': 'application/vnd.ms-ims',
+  'in': 'text/plain',
+  'ink': 'application/inkml+xml',
+  'inkml': 'application/inkml+xml',
+  'install': 'application/x-install-instructions',
+  'iota': 'application/vnd.astraea-software.iota',
+  'ipfix': 'application/ipfix',
+  'ipk': 'application/vnd.shana.informed.package',
+  'irm': 'application/vnd.ibm.rights-management',
+  'irp': 'application/vnd.irepository.package+xml',
+  'iso': 'application/x-iso9660-image',
+  'itp': 'application/vnd.shana.informed.formtemplate',
+  'ivp': 'application/vnd.immervision-ivp',
+  'ivu': 'application/vnd.immervision-ivu',
+  'jad': 'text/vnd.sun.j2me.app-descriptor',
+  'jam': 'application/vnd.jam',
+  'jar': 'application/java-archive',
+  'java': 'text/x-java-source',
+  'jisp': 'application/vnd.jisp',
+  'jlt': 'application/vnd.hp-jlyt',
+  'jnlp': 'application/x-java-jnlp-file',
+  'joda': 'application/vnd.joost.joda-archive',
+  'jpe': 'image/jpeg',
+  'jpeg': 'image/jpeg',
+  'jpg': 'image/jpeg',
+  'jpgm': 'video/jpm',
+  'jpgv': 'video/jpeg',
+  'jpm': 'video/jpm',
+  'js': 'text/javascript',
+  'json': 'application/json',
+  'jsonml': 'application/jsonml+json',
+  'kar': 'audio/midi',
+  'karbon': 'application/vnd.kde.karbon',
+  'kfo': 'application/vnd.kde.kformula',
+  'kia': 'application/vnd.kidspiration',
+  'kml': 'application/vnd.google-earth.kml+xml',
+  'kmz': 'application/vnd.google-earth.kmz',
+  'kne': 'application/vnd.kinar',
+  'knp': 'application/vnd.kinar',
+  'kon': 'application/vnd.kde.kontour',
+  'kpr': 'application/vnd.kde.kpresenter',
+  'kpt': 'application/vnd.kde.kpresenter',
+  'kpxx': 'application/vnd.ds-keypoint',
+  'ksp': 'application/vnd.kde.kspread',
+  'ktr': 'application/vnd.kahootz',
+  'ktx': 'image/ktx',
+  'ktz': 'application/vnd.kahootz',
+  'kwd': 'application/vnd.kde.kword',
+  'kwt': 'application/vnd.kde.kword',
+  'lasxml': 'application/vnd.las.las+xml',
+  'latex': 'application/x-latex',
+  'lbd': 'application/vnd.llamagraphics.life-balance.desktop',
+  'lbe': 'application/vnd.llamagraphics.life-balance.exchange+xml',
+  'les': 'application/vnd.hhe.lesson-player',
+  'lha': 'application/x-lzh-compressed',
+  'link66': 'application/vnd.route66.link66+xml',
+  'list': 'text/plain',
+  'list3820': 'application/vnd.ibm.modcap',
+  'listafp': 'application/vnd.ibm.modcap',
+  'lnk': 'application/x-ms-shortcut',
+  'log': 'text/plain',
+  'lostxml': 'application/lost+xml',
+  'lrf': 'application/octet-stream',
+  'lrm': 'application/vnd.ms-lrm',
+  'ltf': 'application/vnd.frogans.ltf',
+  'lvp': 'audio/vnd.lucent.voice',
+  'lwp': 'application/vnd.lotus-wordpro',
+  'lzh': 'application/x-lzh-compressed',
+  'm13': 'application/x-msmediaview',
+  'm14': 'application/x-msmediaview',
+  'm1v': 'video/mpeg',
+  'm21': 'application/mp21',
+  'm2a': 'audio/mpeg',
+  'm2v': 'video/mpeg',
+  'm3a': 'audio/mpeg',
+  'm3u': 'audio/x-mpegurl',
+  'm3u8': 'application/vnd.apple.mpegurl',
+  // Source: https://datatracker.ietf.org/doc/html/rfc4337#section-2
+  'm4a': 'audio/mp4',
+  'm4b': 'audio/mp4',
+  'm4u': 'video/vnd.mpegurl',
+  'm4v': 'video/x-m4v',
+  'ma': 'application/mathematica',
+  'mads': 'application/mads+xml',
+  'mag': 'application/vnd.ecowin.chart',
+  'maker': 'application/vnd.framemaker',
+  'man': 'text/troff',
+  'mar': 'application/octet-stream',
+  'mathml': 'application/mathml+xml',
+  'mb': 'application/mathematica',
+  'mbk': 'application/vnd.mobius.mbk',
+  'mbox': 'application/mbox',
+  'mc1': 'application/vnd.medcalcdata',
+  'mcd': 'application/vnd.mcd',
+  'mcurl': 'text/vnd.curl.mcurl',
+  // https://www.rfc-editor.org/rfc/rfc7763
+  'md': 'text/markdown',
+  'markdown': 'text/markdown',
+  'mdb': 'application/x-msaccess',
+  'mdi': 'image/vnd.ms-modi',
+  'me': 'text/troff',
+  'mesh': 'model/mesh',
+  'meta4': 'application/metalink4+xml',
+  'metalink': 'application/metalink+xml',
+  'mets': 'application/mets+xml',
+  'mfm': 'application/vnd.mfmp',
+  'mft': 'application/rpki-manifest',
+  'mgp': 'application/vnd.osgeo.mapguide.package',
+  'mgz': 'application/vnd.proteus.magazine',
+  'mid': 'audio/midi',
+  'midi': 'audio/midi',
+  'mie': 'application/x-mie',
+  'mif': 'application/vnd.mif',
+  'mime': 'message/rfc822',
+  'mj2': 'video/mj2',
+  'mjp2': 'video/mj2',
+  'mjs': 'text/javascript',
+  'mk3d': 'video/x-matroska',
+  'mka': 'audio/x-matroska',
+  'mks': 'video/x-matroska',
+  'mkv': 'video/x-matroska',
+  'mlp': 'application/vnd.dolby.mlp',
+  'mmd': 'application/vnd.chipnuts.karaoke-mmd',
+  'mmf': 'application/vnd.smaf',
+  'mmr': 'image/vnd.fujixerox.edmics-mmr',
+  'mng': 'video/x-mng',
+  'mny': 'application/x-msmoney',
+  'mobi': 'application/x-mobipocket-ebook',
+  'mods': 'application/mods+xml',
+  'mov': 'video/quicktime',
+  'movie': 'video/x-sgi-movie',
+  'mp2': 'audio/mpeg',
+  'mp21': 'application/mp21',
+  'mp2a': 'audio/mpeg',
+  'mp3': 'audio/mpeg',
+  'mp4': 'video/mp4',
+  'mp4a': 'audio/mp4',
+  'mp4s': 'application/mp4',
+  'mp4v': 'video/mp4',
+  'mpc': 'application/vnd.mophun.certificate',
+  'mpe': 'video/mpeg',
+  'mpeg': 'video/mpeg',
+  'mpg': 'video/mpeg',
+  'mpg4': 'video/mp4',
+  'mpga': 'audio/mpeg',
+  'mpkg': 'application/vnd.apple.installer+xml',
+  'mpm': 'application/vnd.blueice.multipass',
+  'mpn': 'application/vnd.mophun.application',
+  'mpp': 'application/vnd.ms-project',
+  'mpt': 'application/vnd.ms-project',
+  'mpy': 'application/vnd.ibm.minipay',
+  'mqy': 'application/vnd.mobius.mqy',
+  'mrc': 'application/marc',
+  'mrcx': 'application/marcxml+xml',
+  'ms': 'text/troff',
+  'mscml': 'application/mediaservercontrol+xml',
+  'mseed': 'application/vnd.fdsn.mseed',
+  'mseq': 'application/vnd.mseq',
+  'msf': 'application/vnd.epson.msf',
+  'msh': 'model/mesh',
+  'msi': 'application/x-msdownload',
+  'msl': 'application/vnd.mobius.msl',
+  'msty': 'application/vnd.muvee.style',
+  'mts': 'model/vnd.mts',
+  'mus': 'application/vnd.musician',
+  'musicxml': 'application/vnd.recordare.musicxml+xml',
+  'mvb': 'application/x-msmediaview',
+  'mwf': 'application/vnd.mfer',
+  'mxf': 'application/mxf',
+  'mxl': 'application/vnd.recordare.musicxml',
+  'mxml': 'application/xv+xml',
+  'mxs': 'application/vnd.triscape.mxs',
+  'mxu': 'video/vnd.mpegurl',
+  'n-gage': 'application/vnd.nokia.n-gage.symbian.install',
+  'n3': 'text/n3',
+  'nb': 'application/mathematica',
+  'nbp': 'application/vnd.wolfram.player',
+  'nc': 'application/x-netcdf',
+  'ncx': 'application/x-dtbncx+xml',
+  'nfo': 'text/x-nfo',
+  'ngdat': 'application/vnd.nokia.n-gage.data',
+  'nitf': 'application/vnd.nitf',
+  'nlu': 'application/vnd.neurolanguage.nlu',
+  'nml': 'application/vnd.enliven',
+  'nnd': 'application/vnd.noblenet-directory',
+  'nns': 'application/vnd.noblenet-sealer',
+  'nnw': 'application/vnd.noblenet-web',
+  'npx': 'image/vnd.net-fpx',
+  'nsc': 'application/x-conference',
+  'nsf': 'application/vnd.lotus-notes',
+  'ntf': 'application/vnd.nitf',
+  'nzb': 'application/x-nzb',
+  'oa2': 'application/vnd.fujitsu.oasys2',
+  'oa3': 'application/vnd.fujitsu.oasys3',
+  'oas': 'application/vnd.fujitsu.oasys',
+  'obd': 'application/x-msbinder',
+  'obj': 'application/x-tgif',
+  'oda': 'application/oda',
+  'odb': 'application/vnd.oasis.opendocument.database',
+  'odc': 'application/vnd.oasis.opendocument.chart',
+  'odf': 'application/vnd.oasis.opendocument.formula',
+  'odft': 'application/vnd.oasis.opendocument.formula-template',
+  'odg': 'application/vnd.oasis.opendocument.graphics',
+  'odi': 'application/vnd.oasis.opendocument.image',
+  'odm': 'application/vnd.oasis.opendocument.text-master',
+  'odp': 'application/vnd.oasis.opendocument.presentation',
+  'ods': 'application/vnd.oasis.opendocument.spreadsheet',
+  'odt': 'application/vnd.oasis.opendocument.text',
+  'oga': 'audio/ogg',
+  'ogg': 'audio/ogg',
+  'ogv': 'video/ogg',
+  'ogx': 'application/ogg',
+  'omdoc': 'application/omdoc+xml',
+  'onepkg': 'application/onenote',
+  'onetmp': 'application/onenote',
+  'onetoc': 'application/onenote',
+  'onetoc2': 'application/onenote',
+  'opf': 'application/oebps-package+xml',
+  'opml': 'text/x-opml',
+  'oprc': 'application/vnd.palm',
+  'org': 'application/vnd.lotus-organizer',
+  'osf': 'application/vnd.yamaha.openscoreformat',
+  'osfpvg': 'application/vnd.yamaha.openscoreformat.osfpvg+xml',
+  'otc': 'application/vnd.oasis.opendocument.chart-template',
+  'otf': 'application/x-font-otf',
+  'otg': 'application/vnd.oasis.opendocument.graphics-template',
+  'oth': 'application/vnd.oasis.opendocument.text-web',
+  'oti': 'application/vnd.oasis.opendocument.image-template',
+  'otp': 'application/vnd.oasis.opendocument.presentation-template',
+  'ots': 'application/vnd.oasis.opendocument.spreadsheet-template',
+  'ott': 'application/vnd.oasis.opendocument.text-template',
+  'oxps': 'application/oxps',
+  'oxt': 'application/vnd.openofficeorg.extension',
+  'p': 'text/x-pascal',
+  'p10': 'application/pkcs10',
+  'p12': 'application/x-pkcs12',
+  'p7b': 'application/x-pkcs7-certificates',
+  'p7c': 'application/pkcs7-mime',
+  'p7m': 'application/pkcs7-mime',
+  'p7r': 'application/x-pkcs7-certreqresp',
+  'p7s': 'application/pkcs7-signature',
+  'p8': 'application/pkcs8',
+  'pas': 'text/x-pascal',
+  'paw': 'application/vnd.pawaafile',
+  'pbd': 'application/vnd.powerbuilder6',
+  'pbm': 'image/x-portable-bitmap',
+  'pcap': 'application/vnd.tcpdump.pcap',
+  'pcf': 'application/x-font-pcf',
+  'pcl': 'application/vnd.hp-pcl',
+  'pclxl': 'application/vnd.hp-pclxl',
+  'pct': 'image/x-pict',
+  'pcurl': 'application/vnd.curl.pcurl',
+  'pcx': 'image/x-pcx',
+  'pdb': 'application/vnd.palm',
+  'pdf': 'application/pdf',
+  'pfa': 'application/x-font-type1',
+  'pfb': 'application/x-font-type1',
+  'pfm': 'application/x-font-type1',
+  'pfr': 'application/font-tdpfr',
+  'pfx': 'application/x-pkcs12',
+  'pgm': 'image/x-portable-graymap',
+  'pgn': 'application/x-chess-pgn',
+  'pgp': 'application/pgp-encrypted',
+  'pic': 'image/x-pict',
+  'pkg': 'application/octet-stream',
+  'pki': 'application/pkixcmp',
+  'pkipath': 'application/pkix-pkipath',
+  'plb': 'application/vnd.3gpp.pic-bw-large',
+  'plc': 'application/vnd.mobius.plc',
+  'plf': 'application/vnd.pocketlearn',
+  'pls': 'application/pls+xml',
+  'pml': 'application/vnd.ctc-posml',
+  'png': 'image/png',
+  'pnm': 'image/x-portable-anymap',
+  'portpkg': 'application/vnd.macports.portpkg',
+  'pot': 'application/vnd.ms-powerpoint',
+  'potm': 'application/vnd.ms-powerpoint.template.macroenabled.12',
+  'potx':
+      'application/vnd.openxmlformats-officedocument.presentationml.template',
+  'ppam': 'application/vnd.ms-powerpoint.addin.macroenabled.12',
+  'ppd': 'application/vnd.cups-ppd',
+  'ppm': 'image/x-portable-pixmap',
+  'pps': 'application/vnd.ms-powerpoint',
+  'ppsm': 'application/vnd.ms-powerpoint.slideshow.macroenabled.12',
+  'ppsx':
+      'application/vnd.openxmlformats-officedocument.presentationml.slideshow',
+  'ppt': 'application/vnd.ms-powerpoint',
+  'pptm': 'application/vnd.ms-powerpoint.presentation.macroenabled.12',
+  'pptx':
+      'application/vnd.openxmlformats-officedocument.presentationml.presentation',
+  'pqa': 'application/vnd.palm',
+  'prc': 'application/x-mobipocket-ebook',
+  'pre': 'application/vnd.lotus-freelance',
+  'prf': 'application/pics-rules',
+  'ps': 'application/postscript',
+  'psb': 'application/vnd.3gpp.pic-bw-small',
+  'psd': 'image/vnd.adobe.photoshop',
+  'psf': 'application/x-font-linux-psf',
+  'pskcxml': 'application/pskc+xml',
+  'ptid': 'application/vnd.pvi.ptid1',
+  'pub': 'application/x-mspublisher',
+  'pvb': 'application/vnd.3gpp.pic-bw-var',
+  'pwn': 'application/vnd.3m.post-it-notes',
+  'pya': 'audio/vnd.ms-playready.media.pya',
+  'pyv': 'video/vnd.ms-playready.media.pyv',
+  'qam': 'application/vnd.epson.quickanime',
+  'qbo': 'application/vnd.intu.qbo',
+  'qfx': 'application/vnd.intu.qfx',
+  'qps': 'application/vnd.publishare-delta-tree',
+  'qt': 'video/quicktime',
+  'qwd': 'application/vnd.quark.quarkxpress',
+  'qwt': 'application/vnd.quark.quarkxpress',
+  'qxb': 'application/vnd.quark.quarkxpress',
+  'qxd': 'application/vnd.quark.quarkxpress',
+  'qxl': 'application/vnd.quark.quarkxpress',
+  'qxt': 'application/vnd.quark.quarkxpress',
+  'ra': 'audio/x-pn-realaudio',
+  'ram': 'audio/x-pn-realaudio',
+  'rar': 'application/x-rar-compressed',
+  'ras': 'image/x-cmu-raster',
+  'rcprofile': 'application/vnd.ipunplugged.rcprofile',
+  'rdf': 'application/rdf+xml',
+  'rdz': 'application/vnd.data-vision.rdz',
+  'rep': 'application/vnd.businessobjects',
+  'res': 'application/x-dtbresource+xml',
+  'rgb': 'image/x-rgb',
+  'rif': 'application/reginfo+xml',
+  'rip': 'audio/vnd.rip',
+  'ris': 'application/x-research-info-systems',
+  'rl': 'application/resource-lists+xml',
+  'rlc': 'image/vnd.fujixerox.edmics-rlc',
+  'rld': 'application/resource-lists-diff+xml',
+  'rm': 'application/vnd.rn-realmedia',
+  'rmi': 'audio/midi',
+  'rmp': 'audio/x-pn-realaudio-plugin',
+  'rms': 'application/vnd.jcp.javame.midlet-rms',
+  'rmvb': 'application/vnd.rn-realmedia-vbr',
+  'rnc': 'application/relax-ng-compact-syntax',
+  'roa': 'application/rpki-roa',
+  'roff': 'text/troff',
+  'rp9': 'application/vnd.cloanto.rp9',
+  'rpss': 'application/vnd.nokia.radio-presets',
+  'rpst': 'application/vnd.nokia.radio-preset',
+  'rq': 'application/sparql-query',
+  'rs': 'application/rls-services+xml',
+  'rsd': 'application/rsd+xml',
+  'rss': 'application/rss+xml',
+  'rtf': 'application/rtf',
+  'rtx': 'text/richtext',
+  's': 'text/x-asm',
+  's3m': 'audio/s3m',
+  'saf': 'application/vnd.yamaha.smaf-audio',
+  'sbml': 'application/sbml+xml',
+  'sc': 'application/vnd.ibm.secure-container',
+  'scd': 'application/x-msschedule',
+  'scm': 'application/vnd.lotus-screencam',
+  'scq': 'application/scvp-cv-request',
+  'scs': 'application/scvp-cv-response',
+  'scurl': 'text/vnd.curl.scurl',
+  'sda': 'application/vnd.stardivision.draw',
+  'sdc': 'application/vnd.stardivision.calc',
+  'sdd': 'application/vnd.stardivision.impress',
+  'sdkd': 'application/vnd.solent.sdkm+xml',
+  'sdkm': 'application/vnd.solent.sdkm+xml',
+  'sdp': 'application/sdp',
+  'sdw': 'application/vnd.stardivision.writer',
+  'see': 'application/vnd.seemail',
+  'seed': 'application/vnd.fdsn.seed',
+  'sema': 'application/vnd.sema',
+  'semd': 'application/vnd.semd',
+  'semf': 'application/vnd.semf',
+  'ser': 'application/java-serialized-object',
+  'setpay': 'application/set-payment-initiation',
+  'setreg': 'application/set-registration-initiation',
+  'sfd-hdstx': 'application/vnd.hydrostatix.sof-data',
+  'sfs': 'application/vnd.spotfire.sfs',
+  'sfv': 'text/x-sfv',
+  'sgi': 'image/sgi',
+  'sgl': 'application/vnd.stardivision.writer-global',
+  'sgm': 'text/sgml',
+  'sgml': 'text/sgml',
+  'sh': 'application/x-sh',
+  'shar': 'application/x-shar',
+  'shf': 'application/shf+xml',
+  'sid': 'image/x-mrsid-image',
+  'sig': 'application/pgp-signature',
+  'sil': 'audio/silk',
+  'silo': 'model/mesh',
+  'sis': 'application/vnd.symbian.install',
+  'sisx': 'application/vnd.symbian.install',
+  'sit': 'application/x-stuffit',
+  'sitx': 'application/x-stuffitx',
+  'skd': 'application/vnd.koan',
+  'skm': 'application/vnd.koan',
+  'skp': 'application/vnd.koan',
+  'skt': 'application/vnd.koan',
+  'sldm': 'application/vnd.ms-powerpoint.slide.macroenabled.12',
+  'sldx': 'application/vnd.openxmlformats-officedocument.presentationml.slide',
+  'slt': 'application/vnd.epson.salt',
+  'sm': 'application/vnd.stepmania.stepchart',
+  'smf': 'application/vnd.stardivision.math',
+  'smi': 'application/smil+xml',
+  'smil': 'application/smil+xml',
+  'smv': 'video/x-smv',
+  'smzip': 'application/vnd.stepmania.package',
+  'snd': 'audio/basic',
+  'snf': 'application/x-font-snf',
+  'so': 'application/octet-stream',
+  'spc': 'application/x-pkcs7-certificates',
+  'spf': 'application/vnd.yamaha.smaf-phrase',
+  'spl': 'application/x-futuresplash',
+  'spot': 'text/vnd.in3d.spot',
+  'spp': 'application/scvp-vp-response',
+  'spq': 'application/scvp-vp-request',
+  'spx': 'audio/ogg',
+  'sql': 'application/x-sql',
+  'src': 'application/x-wais-source',
+  'srt': 'application/x-subrip',
+  'sru': 'application/sru+xml',
+  'srx': 'application/sparql-results+xml',
+  'ssdl': 'application/ssdl+xml',
+  'sse': 'application/vnd.kodak-descriptor',
+  'ssf': 'application/vnd.epson.ssf',
+  'ssml': 'application/ssml+xml',
+  'st': 'application/vnd.sailingtracker.track',
+  'stc': 'application/vnd.sun.xml.calc.template',
+  'std': 'application/vnd.sun.xml.draw.template',
+  'stf': 'application/vnd.wt.stf',
+  'sti': 'application/vnd.sun.xml.impress.template',
+  'stk': 'application/hyperstudio',
+  'stl': 'application/vnd.ms-pki.stl',
+  'str': 'application/vnd.pg.format',
+  'stw': 'application/vnd.sun.xml.writer.template',
+  'sub': 'text/vnd.dvb.subtitle',
+  'sus': 'application/vnd.sus-calendar',
+  'susp': 'application/vnd.sus-calendar',
+  'sv4cpio': 'application/x-sv4cpio',
+  'sv4crc': 'application/x-sv4crc',
+  'svc': 'application/vnd.dvb.service',
+  'svd': 'application/vnd.svd',
+  'svg': 'image/svg+xml',
+  'svgz': 'image/svg+xml',
+  'swa': 'application/x-director',
+  'swf': 'application/x-shockwave-flash',
+  'swi': 'application/vnd.aristanetworks.swi',
+  'sxc': 'application/vnd.sun.xml.calc',
+  'sxd': 'application/vnd.sun.xml.draw',
+  'sxg': 'application/vnd.sun.xml.writer.global',
+  'sxi': 'application/vnd.sun.xml.impress',
+  'sxm': 'application/vnd.sun.xml.math',
+  'sxw': 'application/vnd.sun.xml.writer',
+  't': 'text/troff',
+  't3': 'application/x-t3vm-image',
+  'taglet': 'application/vnd.mynfc',
+  'tao': 'application/vnd.tao.intent-module-archive',
+  'tar': 'application/x-tar',
+  'tcap': 'application/vnd.3gpp2.tcap',
+  'tcl': 'application/x-tcl',
+  'teacher': 'application/vnd.smart.teacher',
+  'tei': 'application/tei+xml',
+  'teicorpus': 'application/tei+xml',
+  'tex': 'application/x-tex',
+  'texi': 'application/x-texinfo',
+  'texinfo': 'application/x-texinfo',
+  'text': 'text/plain',
+  'tfi': 'application/thraud+xml',
+  'tfm': 'application/x-tex-tfm',
+  'tga': 'image/x-tga',
+  'thmx': 'application/vnd.ms-officetheme',
+  'tif': 'image/tiff',
+  'tiff': 'image/tiff',
+  'tmo': 'application/vnd.tmobile-livetv',
+  // Source: https://toml.io/en/v1.0.0#mime-type
+  'toml': 'application/toml',
+  'torrent': 'application/x-bittorrent',
+  'tpl': 'application/vnd.groove-tool-template',
+  'tpt': 'application/vnd.trid.tpt',
+  'tr': 'text/troff',
+  'tra': 'application/vnd.trueapp',
+  'trm': 'application/x-msterminal',
+  'tsd': 'application/timestamped-data',
+  'tsv': 'text/tab-separated-values',
+  'ttc': 'application/x-font-ttf',
+  'ttf': 'application/x-font-ttf',
+  'ttl': 'text/turtle',
+  'twd': 'application/vnd.simtech-mindmapper',
+  'twds': 'application/vnd.simtech-mindmapper',
+  'txd': 'application/vnd.genomatix.tuxedo',
+  'txf': 'application/vnd.mobius.txf',
+  'txt': 'text/plain',
+  'u32': 'application/x-authorware-bin',
+  'udeb': 'application/x-debian-package',
+  'ufd': 'application/vnd.ufdl',
+  'ufdl': 'application/vnd.ufdl',
+  'ulx': 'application/x-glulx',
+  'umj': 'application/vnd.umajin',
+  'unityweb': 'application/vnd.unity',
+  'uoml': 'application/vnd.uoml+xml',
+  'uri': 'text/uri-list',
+  'uris': 'text/uri-list',
+  'urls': 'text/uri-list',
+  'ustar': 'application/x-ustar',
+  'utz': 'application/vnd.uiq.theme',
+  'uu': 'text/x-uuencode',
+  'uva': 'audio/vnd.dece.audio',
+  'uvd': 'application/vnd.dece.data',
+  'uvf': 'application/vnd.dece.data',
+  'uvg': 'image/vnd.dece.graphic',
+  'uvh': 'video/vnd.dece.hd',
+  'uvi': 'image/vnd.dece.graphic',
+  'uvm': 'video/vnd.dece.mobile',
+  'uvp': 'video/vnd.dece.pd',
+  'uvs': 'video/vnd.dece.sd',
+  'uvt': 'application/vnd.dece.ttml+xml',
+  'uvu': 'video/vnd.uvvu.mp4',
+  'uvv': 'video/vnd.dece.video',
+  'uvva': 'audio/vnd.dece.audio',
+  'uvvd': 'application/vnd.dece.data',
+  'uvvf': 'application/vnd.dece.data',
+  'uvvg': 'image/vnd.dece.graphic',
+  'uvvh': 'video/vnd.dece.hd',
+  'uvvi': 'image/vnd.dece.graphic',
+  'uvvm': 'video/vnd.dece.mobile',
+  'uvvp': 'video/vnd.dece.pd',
+  'uvvs': 'video/vnd.dece.sd',
+  'uvvt': 'application/vnd.dece.ttml+xml',
+  'uvvu': 'video/vnd.uvvu.mp4',
+  'uvvv': 'video/vnd.dece.video',
+  'uvvx': 'application/vnd.dece.unspecified',
+  'uvvz': 'application/vnd.dece.zip',
+  'uvx': 'application/vnd.dece.unspecified',
+  'uvz': 'application/vnd.dece.zip',
+  'vcard': 'text/vcard',
+  'vcd': 'application/x-cdlink',
+  'vcf': 'text/x-vcard',
+  'vcg': 'application/vnd.groove-vcard',
+  'vcs': 'text/x-vcalendar',
+  'vcx': 'application/vnd.vcx',
+  'vis': 'application/vnd.visionary',
+  'viv': 'video/vnd.vivo',
+  'vob': 'video/x-ms-vob',
+  'vor': 'application/vnd.stardivision.writer',
+  'vox': 'application/x-authorware-bin',
+  'vrml': 'model/vrml',
+  'vsd': 'application/vnd.visio',
+  'vsf': 'application/vnd.vsf',
+  'vss': 'application/vnd.visio',
+  'vst': 'application/vnd.visio',
+  'vsw': 'application/vnd.visio',
+  'vtu': 'model/vnd.vtu',
+  'vxml': 'application/voicexml+xml',
+  'w3d': 'application/x-director',
+  'wad': 'application/x-doom',
+  'wasm': 'application/wasm',
+  'wav': 'audio/x-wav',
+  'wax': 'audio/x-ms-wax',
+  'wbmp': 'image/vnd.wap.wbmp',
+  'wbs': 'application/vnd.criticaltools.wbs+xml',
+  'wbxml': 'application/vnd.wap.wbxml',
+  'wcm': 'application/vnd.ms-works',
+  'wdb': 'application/vnd.ms-works',
+  'wdp': 'image/vnd.ms-photo',
+  'weba': 'audio/webm',
+  'webm': 'video/webm',
+  // Source: https://w3c.github.io/manifest/#media-type-registration
+  'webmanifest': 'application/manifest+json',
+  'webp': 'image/webp',
+  'wg': 'application/vnd.pmi.widget',
+  'wgt': 'application/widget',
+  'wks': 'application/vnd.ms-works',
+  'wm': 'video/x-ms-wm',
+  'wma': 'audio/x-ms-wma',
+  'wmd': 'application/x-ms-wmd',
+  'wmf': 'application/x-msmetafile',
+  'wml': 'text/vnd.wap.wml',
+  'wmlc': 'application/vnd.wap.wmlc',
+  'wmls': 'text/vnd.wap.wmlscript',
+  'wmlsc': 'application/vnd.wap.wmlscriptc',
+  'wmv': 'video/x-ms-wmv',
+  'wmx': 'video/x-ms-wmx',
+  'wmz': 'application/x-ms-wmz',
+  'woff': 'application/x-font-woff',
+  'woff2': 'font/woff2',
+  'wpd': 'application/vnd.wordperfect',
+  'wpl': 'application/vnd.ms-wpl',
+  'wps': 'application/vnd.ms-works',
+  'wqd': 'application/vnd.wqd',
+  'wri': 'application/x-mswrite',
+  'wrl': 'model/vrml',
+  'wsdl': 'application/wsdl+xml',
+  'wspolicy': 'application/wspolicy+xml',
+  'wtb': 'application/vnd.webturbo',
+  'wvx': 'video/x-ms-wvx',
+  'x32': 'application/x-authorware-bin',
+  'x3d': 'model/x3d+xml',
+  'x3db': 'model/x3d+binary',
+  'x3dbz': 'model/x3d+binary',
+  'x3dv': 'model/x3d+vrml',
+  'x3dvz': 'model/x3d+vrml',
+  'x3dz': 'model/x3d+xml',
+  'xaml': 'application/xaml+xml',
+  'xap': 'application/x-silverlight-app',
+  'xar': 'application/vnd.xara',
+  'xbap': 'application/x-ms-xbap',
+  'xbd': 'application/vnd.fujixerox.docuworks.binder',
+  'xbm': 'image/x-xbitmap',
+  'xdf': 'application/xcap-diff+xml',
+  'xdm': 'application/vnd.syncml.dm+xml',
+  'xdp': 'application/vnd.adobe.xdp+xml',
+  'xdssc': 'application/dssc+xml',
+  'xdw': 'application/vnd.fujixerox.docuworks',
+  'xenc': 'application/xenc+xml',
+  'xer': 'application/patch-ops-error+xml',
+  'xfdf': 'application/vnd.adobe.xfdf',
+  'xfdl': 'application/vnd.xfdl',
+  'xht': 'application/xhtml+xml',
+  'xhtml': 'application/xhtml+xml',
+  'xhvml': 'application/xv+xml',
+  'xif': 'image/vnd.xiff',
+  'xla': 'application/vnd.ms-excel',
+  'xlam': 'application/vnd.ms-excel.addin.macroenabled.12',
+  'xlc': 'application/vnd.ms-excel',
+  'xlf': 'application/x-xliff+xml',
+  'xlm': 'application/vnd.ms-excel',
+  'xls': 'application/vnd.ms-excel',
+  'xlsb': 'application/vnd.ms-excel.sheet.binary.macroenabled.12',
+  'xlsm': 'application/vnd.ms-excel.sheet.macroenabled.12',
+  'xlsx': 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet',
+  'xlt': 'application/vnd.ms-excel',
+  'xltm': 'application/vnd.ms-excel.template.macroenabled.12',
+  'xltx':
+      'application/vnd.openxmlformats-officedocument.spreadsheetml.template',
+  'xlw': 'application/vnd.ms-excel',
+  'xm': 'audio/xm',
+  'xml': 'application/xml',
+  'xo': 'application/vnd.olpc-sugar',
+  'xop': 'application/xop+xml',
+  'xpi': 'application/x-xpinstall',
+  'xpl': 'application/xproc+xml',
+  'xpm': 'image/x-xpixmap',
+  'xpr': 'application/vnd.is-xpr',
+  'xps': 'application/vnd.ms-xpsdocument',
+  'xpw': 'application/vnd.intercon.formnet',
+  'xpx': 'application/vnd.intercon.formnet',
+  'xsl': 'application/xml',
+  'xslt': 'application/xslt+xml',
+  'xsm': 'application/vnd.syncml+xml',
+  'xspf': 'application/xspf+xml',
+  'xul': 'application/vnd.mozilla.xul+xml',
+  'xvm': 'application/xv+xml',
+  'xvml': 'application/xv+xml',
+  'xwd': 'image/x-xwindowdump',
+  'xyz': 'chemical/x-xyz',
+  'xz': 'application/x-xz',
+  'yang': 'application/yang',
+  'yin': 'application/yin+xml',
+  'z1': 'application/x-zmachine',
+  'z2': 'application/x-zmachine',
+  'z3': 'application/x-zmachine',
+  'z4': 'application/x-zmachine',
+  'z5': 'application/x-zmachine',
+  'z6': 'application/x-zmachine',
+  'z7': 'application/x-zmachine',
+  'z8': 'application/x-zmachine',
+  'zaz': 'application/vnd.zzazz.deck+xml',
+  'zip': 'application/zip',
+  'zir': 'application/vnd.zul',
+  'zirz': 'application/vnd.zul',
+  'zmm': 'application/vnd.handheld-entertainment+xml',
+};
diff --git a/pkgs/mime/lib/src/extension.dart b/pkgs/mime/lib/src/extension.dart
new file mode 100644
index 0000000..293449a
--- /dev/null
+++ b/pkgs/mime/lib/src/extension.dart
@@ -0,0 +1,55 @@
+// Copyright (c) 2023, 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.
+
+import 'default_extension_map.dart';
+
+/// Default extension for recognized MIME types.
+///
+/// Is the inverse of [defaultExtensionMap], and where that
+/// map has multiple extensions which map to the same
+/// MIME type, this map maps that MIME type to a *default*
+/// extension.
+///
+/// Used by [extensionFromMime].
+final Map<String, String> _defaultMimeTypeMap = {
+  for (var entry in defaultExtensionMap.entries) entry.value: entry.key,
+  'application/msword': 'doc',
+  'application/vnd.ms-excel': 'xls',
+  'application/vnd.ms-powerpoint': 'ppt',
+  'application/x-debian-package': 'deb',
+  'application/xhtml+xml': 'xhtml',
+  'application/xml': 'xml',
+  'audio/x-aiff': 'aif',
+  'audio/midi': 'mid',
+  'audio/mp4': 'm4a',
+  'audio/ogg': 'ogg',
+  'image/jpeg': 'jpg',
+  'image/tiff': 'tif',
+  'image/svg+xml': 'svg',
+  'model/vrml': 'vrml',
+  'text/calendar': 'ics',
+  'text/html': 'html',
+  'text/javascript': 'js',
+  'text/markdown': 'md',
+  'text/plain': 'txt',
+  'text/sgml': 'sgml',
+  'text/x-asm': 'asm',
+  'text/x-c': 'c',
+  'text/x-pascal': 'pas',
+  'video/mp4': 'mp4',
+  'video/mpeg': 'mpg',
+  'video/quicktime': 'mov',
+  'video/x-matroska': 'mkv',
+};
+
+/// The default file extension for a given MIME type.
+///
+/// If [mimeType] has multiple associated extensions,
+/// the returned string is one of those, chosen as the default
+/// extension for that MIME type.
+///
+/// Returns `null` if [mimeType] is not a recognized and
+/// supported MIME type.
+String? extensionFromMime(String mimeType) =>
+    _defaultMimeTypeMap[mimeType.toLowerCase()];
diff --git a/pkgs/mime/lib/src/magic_number.dart b/pkgs/mime/lib/src/magic_number.dart
new file mode 100644
index 0000000..c8b5c3b
--- /dev/null
+++ b/pkgs/mime/lib/src/magic_number.dart
@@ -0,0 +1,407 @@
+// Copyright (c) 2013, 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.
+
+class MagicNumber {
+  final String mimeType;
+  final List<int> numbers;
+  final List<int>? mask;
+
+  const MagicNumber(this.mimeType, this.numbers, {this.mask});
+
+  bool matches(List<int> header) {
+    if (header.length < numbers.length) return false;
+
+    for (var i = 0; i < numbers.length; i++) {
+      if (mask != null) {
+        if ((mask![i] & numbers[i]) != (mask![i] & header[i])) return false;
+      } else {
+        if (numbers[i] != header[i]) return false;
+      }
+    }
+
+    return true;
+  }
+}
+
+const int initialMagicNumbersMaxLength = 12;
+
+const List<MagicNumber> initialMagicNumbers = [
+  MagicNumber('application/pdf', [0x25, 0x50, 0x44, 0x46]),
+  MagicNumber('application/postscript', [0x25, 0x51]),
+
+  /// AIFF is based on the EA IFF 85 Standard for Interchange Format Files.
+  /// -> 4 bytes have the ASCII characters 'F' 'O' 'R' 'M'.
+  /// -> 4 bytes indicating the size of the file
+  /// -> 4 bytes have the ASCII characters 'A' 'I' 'F' 'F'.
+  /// http://www-mmsp.ece.mcgill.ca/Documents/AudioFormats/AIFF/Docs/AIFF-1.3.pdf
+  MagicNumber('audio/x-aiff', [
+    0x46,
+    0x4F,
+    0x52,
+    0x4D,
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0x41,
+    0x49,
+    0x46,
+    0x46
+  ], mask: [
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF
+  ]),
+
+  /// -> 4 bytes have the ASCII characters 'f' 'L' 'a' 'C'.
+  /// https://xiph.org/flac/format.html
+  MagicNumber('audio/x-flac', [0x66, 0x4C, 0x61, 0x43]),
+
+  /// The WAVE file format is based on the RIFF document format.
+  /// -> 4 bytes have the ASCII characters 'R' 'I' 'F' 'F'.
+  /// -> 4 bytes indicating the size of the file
+  /// -> 4 bytes have the ASCII characters 'W' 'A' 'V' 'E'.
+  /// http://www-mmsp.ece.mcgill.ca/Documents/AudioFormats/WAVE/Docs/riffmci.pdf
+  MagicNumber('audio/x-wav', [
+    0x52,
+    0x49,
+    0x46,
+    0x46,
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0x57,
+    0x41,
+    0x56,
+    0x45
+  ], mask: [
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF
+  ]),
+  MagicNumber('image/gif', [0x47, 0x49, 0x46, 0x38, 0x37, 0x61]),
+  MagicNumber('image/gif', [0x47, 0x49, 0x46, 0x38, 0x39, 0x61]),
+  MagicNumber('image/jpeg', [0xFF, 0xD8]),
+  MagicNumber('image/png', [0x89, 0x50, 0x4E, 0x47, 0x0D, 0x0A, 0x1A, 0x0A]),
+  MagicNumber('image/tiff', [0x49, 0x49, 0x2A, 0x00]),
+  MagicNumber('image/tiff', [0x4D, 0x4D, 0x00, 0x2A]),
+  MagicNumber('audio/aac', [0xFF, 0xF1]),
+  MagicNumber('audio/aac', [0xFF, 0xF9]),
+  MagicNumber('audio/weba', [0x1A, 0x45, 0xDF, 0xA3]),
+  MagicNumber('audio/mpeg', [0x49, 0x44, 0x33]),
+  MagicNumber('audio/mpeg', [0xFF, 0xFB]),
+  MagicNumber('audio/ogg', [0x4F, 0x70, 0x75]),
+  MagicNumber('video/3gpp', [
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0x66,
+    0x74,
+    0x79,
+    0x70,
+    0x33,
+    0x67,
+    0x70,
+    0x35
+  ], mask: [
+    0xFF,
+    0xFF,
+    0xFF,
+    0x00,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF
+  ]),
+  MagicNumber('video/mp4', [
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0x66,
+    0x74,
+    0x79,
+    0x70,
+    0x61,
+    0x76,
+    0x63,
+    0x31
+  ], mask: [
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF
+  ]),
+  MagicNumber('video/mp4', [
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0x66,
+    0x74,
+    0x79,
+    0x70,
+    0x69,
+    0x73,
+    0x6F,
+    0x32
+  ], mask: [
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF
+  ]),
+  MagicNumber('video/mp4', [
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0x66,
+    0x74,
+    0x79,
+    0x70,
+    0x69,
+    0x73,
+    0x6F,
+    0x6D
+  ], mask: [
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF
+  ]),
+  MagicNumber('video/mp4', [
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0x66,
+    0x74,
+    0x79,
+    0x70,
+    0x6D,
+    0x70,
+    0x34,
+    0x31
+  ], mask: [
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF
+  ]),
+  MagicNumber('video/mp4', [
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0x66,
+    0x74,
+    0x79,
+    0x70,
+    0x6D,
+    0x70,
+    0x34,
+    0x32
+  ], mask: [
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF
+  ]),
+  MagicNumber('model/gltf-binary', [0x46, 0x54, 0x6C, 0x67]),
+
+  /// The WebP file format is based on the RIFF document format.
+  /// -> 4 bytes have the ASCII characters 'R' 'I' 'F' 'F'.
+  /// -> 4 bytes indicating the size of the file
+  /// -> 4 bytes have the ASCII characters 'W' 'E' 'B' 'P'.
+  /// https://developers.google.com/speed/webp/docs/riff_container
+  MagicNumber('image/webp', [
+    0x52,
+    0x49,
+    0x46,
+    0x46,
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0x57,
+    0x45,
+    0x42,
+    0x50
+  ], mask: [
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF
+  ]),
+
+  MagicNumber('font/woff2', [0x77, 0x4f, 0x46, 0x32]),
+
+  /// High Efficiency Image File Format (ISO/IEC 23008-12).
+  /// -> 4 bytes indicating the ftyp box length.
+  /// -> 4 bytes have the ASCII characters 'f' 't' 'y' 'p'.
+  /// -> 4 bytes have the ASCII characters 'h' 'e' 'i' 'c'.
+  /// https://www.iana.org/assignments/media-types/image/heic
+  MagicNumber('image/heic', [
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0x66,
+    0x74,
+    0x79,
+    0x70,
+    0x68,
+    0x65,
+    0x69,
+    0x63
+  ], mask: [
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF
+  ]),
+
+  /// -> 4 bytes indicating the ftyp box length.
+  /// -> 4 bytes have the ASCII characters 'f' 't' 'y' 'p'.
+  /// -> 4 bytes have the ASCII characters 'h' 'e' 'i' 'x'.
+  MagicNumber('image/heic', [
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0x66,
+    0x74,
+    0x79,
+    0x70,
+    0x68,
+    0x65,
+    0x69,
+    0x78
+  ], mask: [
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF
+  ]),
+
+  /// -> 4 bytes indicating the ftyp box length.
+  /// -> 4 bytes have the ASCII characters 'f' 't' 'y' 'p'.
+  /// -> 4 bytes have the ASCII characters 'm' 'i' 'f' '1'.
+  MagicNumber('image/heif', [
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0x66,
+    0x74,
+    0x79,
+    0x70,
+    0x6D,
+    0x69,
+    0x66,
+    0x31
+  ], mask: [
+    0x00,
+    0x00,
+    0x00,
+    0x00,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF,
+    0xFF
+  ]),
+];
diff --git a/pkgs/mime/lib/src/mime_multipart_transformer.dart b/pkgs/mime/lib/src/mime_multipart_transformer.dart
new file mode 100644
index 0000000..2648d7d
--- /dev/null
+++ b/pkgs/mime/lib/src/mime_multipart_transformer.dart
@@ -0,0 +1,42 @@
+// Copyright (c) 2012, 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.
+
+import 'dart:async';
+import 'dart:typed_data';
+
+import 'bound_multipart_stream.dart';
+import 'char_code.dart' as char_code;
+import 'mime_shared.dart';
+
+Uint8List _getBoundary(String boundary) {
+  final charCodes = boundary.codeUnits;
+
+  final boundaryList = Uint8List(4 + charCodes.length);
+  // Set-up the matching boundary preceding it with CRLF and two
+  // dashes.
+  boundaryList[0] = char_code.cr;
+  boundaryList[1] = char_code.lf;
+  boundaryList[2] = char_code.dash;
+  boundaryList[3] = char_code.dash;
+  boundaryList.setRange(4, 4 + charCodes.length, charCodes);
+  return boundaryList;
+}
+
+/// Parser for MIME multipart types of data as described in RFC 2046
+/// section 5.1.1. The data is transformed into [MimeMultipart] objects, each
+/// of them streaming the multipart data.
+class MimeMultipartTransformer
+    extends StreamTransformerBase<List<int>, MimeMultipart> {
+  final List<int> _boundary;
+
+  /// Construct a new MIME multipart parser with the boundary
+  /// [boundary]. The boundary should be as specified in the content
+  /// type parameter, that is without the -- prefix.
+  MimeMultipartTransformer(String boundary)
+      : _boundary = _getBoundary(boundary);
+
+  @override
+  Stream<MimeMultipart> bind(Stream<List<int>> stream) =>
+      BoundMultipartStream(_boundary, stream).stream;
+}
diff --git a/pkgs/mime/lib/src/mime_shared.dart b/pkgs/mime/lib/src/mime_shared.dart
new file mode 100644
index 0000000..1c98971
--- /dev/null
+++ b/pkgs/mime/lib/src/mime_shared.dart
@@ -0,0 +1,20 @@
+// 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.
+
+import 'mime_multipart_transformer.dart';
+
+class MimeMultipartException implements Exception {
+  final String message;
+
+  const MimeMultipartException([this.message = '']);
+
+  @override
+  String toString() => 'MimeMultipartException: $message';
+}
+
+/// A Mime Multipart class representing each part parsed by
+/// [MimeMultipartTransformer]. The data is streamed in as it become available.
+abstract class MimeMultipart extends Stream<List<int>> {
+  Map<String, String> get headers;
+}
diff --git a/pkgs/mime/lib/src/mime_type.dart b/pkgs/mime/lib/src/mime_type.dart
new file mode 100644
index 0000000..9cf9194
--- /dev/null
+++ b/pkgs/mime/lib/src/mime_type.dart
@@ -0,0 +1,109 @@
+// Copyright (c) 2013, 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.
+
+import 'default_extension_map.dart';
+import 'magic_number.dart';
+
+final MimeTypeResolver _globalResolver = MimeTypeResolver();
+
+/// The maximum number of bytes needed, to match all default magic-numbers.
+int get defaultMagicNumbersMaxLength => _globalResolver.magicNumbersMaxLength;
+
+/// Extract the extension from [path] and use that for MIME-type lookup, using
+/// the default extension map.
+///
+/// If no matching MIME-type was found, `null` is returned.
+///
+/// If [headerBytes] is present, a match for known magic-numbers will be
+/// performed first. This allows the correct mime-type to be found, even though
+/// a file have been saved using the wrong file-name extension. If less than
+/// [defaultMagicNumbersMaxLength] bytes was provided, some magic-numbers won't
+/// be matched against.
+String? lookupMimeType(String path, {List<int>? headerBytes}) =>
+    _globalResolver.lookup(path, headerBytes: headerBytes);
+
+/// MIME-type resolver class, used to customize the lookup of mime-types.
+class MimeTypeResolver {
+  final Map<String, String> _extensionMap = {};
+  final List<MagicNumber> _magicNumbers = [];
+  final bool _useDefault;
+  int _magicNumbersMaxLength;
+
+  /// Create a new empty [MimeTypeResolver].
+  MimeTypeResolver.empty()
+      : _useDefault = false,
+        _magicNumbersMaxLength = 0;
+
+  /// Create a new [MimeTypeResolver] containing the default scope.
+  MimeTypeResolver()
+      : _useDefault = true,
+        _magicNumbersMaxLength = initialMagicNumbersMaxLength;
+
+  /// Get the maximum number of bytes required to match all magic numbers, when
+  /// performing [lookup] with headerBytes present.
+  int get magicNumbersMaxLength => _magicNumbersMaxLength;
+
+  /// Extract the extension from [path] and use that for MIME-type lookup.
+  ///
+  /// If no matching MIME-type was found, `null` is returned.
+  ///
+  /// If [headerBytes] is present, a match for known magic-numbers will be
+  /// performed first. This allows the correct mime-type to be found, even
+  /// though a file have been saved using the wrong file-name extension. If less
+  /// than [magicNumbersMaxLength] bytes was provided, some magic-numbers won't
+  /// be matched against.
+  String? lookup(String path, {List<int>? headerBytes}) {
+    String? result;
+    if (headerBytes != null) {
+      result = _matchMagic(headerBytes, _magicNumbers);
+      if (result != null) return result;
+      if (_useDefault) {
+        result = _matchMagic(headerBytes, initialMagicNumbers);
+        if (result != null) return result;
+      }
+    }
+    final ext = _ext(path);
+    result = _extensionMap[ext];
+    if (result != null) return result;
+    if (_useDefault) {
+      result = defaultExtensionMap[ext];
+      if (result != null) return result;
+    }
+    return null;
+  }
+
+  /// Add a new MIME-type mapping to the [MimeTypeResolver]. If the [extension]
+  /// is already present in the [MimeTypeResolver], it'll be overwritten.
+  void addExtension(String extension, String mimeType) {
+    _extensionMap[extension] = mimeType;
+  }
+
+  /// Add a new magic-number mapping to the [MimeTypeResolver].
+  ///
+  /// If [mask] is present,the [mask] is used to only perform matching on
+  /// selective bits. The [mask] must have the same length as [bytes].
+  void addMagicNumber(List<int> bytes, String mimeType, {List<int>? mask}) {
+    if (mask != null && bytes.length != mask.length) {
+      throw ArgumentError('Bytes and mask are of different lengths');
+    }
+    if (bytes.length > _magicNumbersMaxLength) {
+      _magicNumbersMaxLength = bytes.length;
+    }
+    _magicNumbers.add(MagicNumber(mimeType, bytes, mask: mask));
+  }
+
+  static String? _matchMagic(
+      List<int> headerBytes, List<MagicNumber> magicNumbers) {
+    for (var mn in magicNumbers) {
+      if (mn.matches(headerBytes)) return mn.mimeType;
+    }
+    return null;
+  }
+
+  static String _ext(String path) {
+    final index = path.lastIndexOf('.');
+    if (index < 0 || index + 1 >= path.length) return path;
+    return path.substring(index + 1).toLowerCase();
+  }
+}
diff --git a/pkgs/mime/pubspec.yaml b/pkgs/mime/pubspec.yaml
new file mode 100644
index 0000000..41b3842
--- /dev/null
+++ b/pkgs/mime/pubspec.yaml
@@ -0,0 +1,18 @@
+name: mime
+version: 2.0.0
+description: >-
+  Utilities for handling media (MIME) types, including determining a type from
+  a file extension and file contents.
+repository: https://github.com/dart-lang/tools/tree/main/pkgs/mime
+topics:
+ - magic-numbers
+ - mime
+ - mimetype
+ - multipart-form
+
+environment:
+  sdk: ^3.2.0
+
+dev_dependencies:
+  dart_flutter_team_lints: ^3.0.0
+  test: ^1.16.0
diff --git a/pkgs/mime/test/default_extension_map_test.dart b/pkgs/mime/test/default_extension_map_test.dart
new file mode 100644
index 0000000..b5539dd
--- /dev/null
+++ b/pkgs/mime/test/default_extension_map_test.dart
@@ -0,0 +1,16 @@
+// Copyright (c) 2020, 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.
+
+import 'package:mime/src/default_extension_map.dart';
+import 'package:test/test.dart';
+
+void main() {
+  group('defaultExtensionMap', () {
+    test('keys are lowercase', () {
+      for (final key in defaultExtensionMap.keys) {
+        expect(key, equals(key.toLowerCase()));
+      }
+    });
+  });
+}
diff --git a/pkgs/mime/test/extension_test.dart b/pkgs/mime/test/extension_test.dart
new file mode 100644
index 0000000..40dae6d
--- /dev/null
+++ b/pkgs/mime/test/extension_test.dart
@@ -0,0 +1,33 @@
+// Copyright (c) 2023, 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.
+
+import 'package:mime/mime.dart';
+import 'package:test/test.dart';
+
+void main() {
+  test('valid-mime-type', () {
+    expect(extensionFromMime('text/x-dart'), equals('dart'));
+    expect(extensionFromMime('text/javascript'), equals('js'));
+    expect(extensionFromMime('application/java-archive'), equals('jar'));
+    expect(extensionFromMime('application/json'), equals('json'));
+    expect(extensionFromMime('application/pdf'), equals('pdf'));
+    expect(extensionFromMime('application/vnd.ms-excel'), equals('xls'));
+    expect(extensionFromMime('application/xhtml+xml'), equals('xhtml'));
+    expect(extensionFromMime('image/jpeg'), equals('jpg'));
+    expect(extensionFromMime('image/png'), equals('png'));
+    expect(extensionFromMime('text/css'), equals('css'));
+    expect(extensionFromMime('text/html'), equals('html'));
+    expect(extensionFromMime('text/plain'), equals('txt'));
+    expect(extensionFromMime('text/x-c'), equals('c'));
+  });
+
+  test('invalid-mime-type', () {
+    expect(extensionFromMime('invalid-mime-type'), isNull);
+    expect(extensionFromMime('invalid/mime/type'), isNull);
+  });
+
+  test('unknown-mime-type', () {
+    expect(extensionFromMime('application/to-be-invented'), isNull);
+  });
+}
diff --git a/pkgs/mime/test/mime_multipart_transformer_test.dart b/pkgs/mime/test/mime_multipart_transformer_test.dart
new file mode 100644
index 0000000..109a9bc
--- /dev/null
+++ b/pkgs/mime/test/mime_multipart_transformer_test.dart
@@ -0,0 +1,469 @@
+// Copyright (c) 2013, 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.
+
+import 'dart:async';
+import 'dart:math';
+
+import 'package:mime/mime.dart';
+import 'package:test/test.dart';
+
+void _writeInChunks(
+    List<int> data, int chunkSize, StreamController<List<int>> controller) {
+  if (chunkSize == -1) chunkSize = data.length;
+
+  for (var pos = 0; pos < data.length; pos += chunkSize) {
+    final remaining = data.length - pos;
+    final writeLength = min(chunkSize, remaining);
+    controller.add(data.sublist(pos, pos + writeLength));
+  }
+  controller.close();
+}
+
+enum TestMode { immediateListen, delayListen, pauseResume }
+
+void _runParseTest(
+  String message,
+  String boundary,
+  TestMode mode, [
+  List<Map<String, String>>? expectedHeaders,
+  List<String?>? expectedParts,
+  bool expectError = false,
+]) {
+  Future<void> testWrite(List<int> data, [int chunkSize = -1]) {
+    final controller = StreamController<List<int>>(sync: true);
+
+    final stream =
+        controller.stream.transform(MimeMultipartTransformer(boundary));
+    var i = 0;
+    final completer = Completer<void>();
+    final futures = <Future<void>>[];
+    stream.listen((multipart) {
+      final part = i++;
+      if (expectedHeaders != null) {
+        expect(multipart.headers, equals(expectedHeaders[part]));
+      }
+      switch (mode) {
+        case TestMode.immediateListen:
+          futures.add(multipart.fold<List<int>>(
+              [], (buffer, data) => buffer..addAll(data)).then((data) {
+            if (expectedParts?[part] != null) {
+              expect(data, equals(expectedParts?[part]!.codeUnits));
+            }
+          }));
+
+        case TestMode.delayListen:
+          futures.add(
+            Future(
+              () => multipart.fold<List<int>>(
+                [],
+                (buffer, data) => buffer..addAll(data),
+              ).then(
+                (data) {
+                  if (expectedParts?[part] != null) {
+                    expect(data, equals(expectedParts?[part]!.codeUnits));
+                  }
+                },
+              ),
+            ),
+          );
+
+        case TestMode.pauseResume:
+          final completer = Completer<void>();
+          futures.add(completer.future);
+          final buffer = <int>[];
+          late StreamSubscription<List<int>> subscription;
+          subscription = multipart.listen((data) {
+            buffer.addAll(data);
+            subscription.pause();
+            Future(() => subscription.resume());
+          }, onDone: () {
+            if (expectedParts?[part] != null) {
+              expect(buffer, equals(expectedParts?[part]!.codeUnits));
+            }
+            completer.complete();
+          });
+          addTearDown(subscription.cancel);
+      }
+    }, onError: (Object error) {
+      // ignore: only_throw_errors
+      if (!expectError) throw error;
+    }, onDone: () {
+      if (expectedParts != null) {
+        expect(i, equals(expectedParts.length));
+      }
+      Future.wait(futures).then(completer.complete);
+    });
+
+    _writeInChunks(data, chunkSize, controller);
+
+    return completer.future;
+  }
+
+  Future<void> testFirstPartOnly(List<int> data, [int chunkSize = -1]) {
+    final completer = Completer<void>();
+    final controller = StreamController<List<int>>(sync: true);
+
+    final stream =
+        controller.stream.transform(MimeMultipartTransformer(boundary));
+
+    stream.first.then((multipart) {
+      if (expectedHeaders != null) {
+        expect(multipart.headers, equals(expectedHeaders[0]));
+      }
+      return multipart.fold<List<int>>([], (b, d) => b..addAll(d)).then(
+        (data) {
+          if (expectedParts != null && expectedParts[0] != null) {
+            expect(data, equals(expectedParts[0]!.codeUnits));
+          }
+        },
+      );
+    }).then((_) {
+      completer.complete();
+    });
+
+    _writeInChunks(data, chunkSize, controller);
+
+    return completer.future;
+  }
+
+  Future<void> testCompletePartAfterCancel(List<int> data, int parts,
+      [int chunkSize = -1]) {
+    final completer = Completer<void>();
+    final controller = StreamController<List<int>>(sync: true);
+    final stream =
+        controller.stream.transform(MimeMultipartTransformer(boundary));
+    late StreamSubscription<void> subscription;
+    var i = 0;
+    final futures = <Future<void>>[];
+    subscription = stream.listen((multipart) {
+      final partIndex = i;
+
+      if (partIndex >= parts) {
+        throw StateError('Expected no more parts, but got one.');
+      }
+
+      if (expectedHeaders != null) {
+        expect(multipart.headers, equals(expectedHeaders[partIndex]));
+      }
+      futures.add(
+          multipart.fold<List<int>>([], (b, d) => b..addAll(d)).then((data) {
+        if (expectedParts != null && expectedParts[partIndex] != null) {
+          expect(data, equals(expectedParts[partIndex]!.codeUnits));
+        }
+      }));
+
+      if (partIndex == (parts - 1)) {
+        subscription.cancel();
+        Future.wait(futures).then(completer.complete);
+      }
+      i++;
+    });
+
+    _writeInChunks(data, chunkSize, controller);
+
+    return completer.future;
+  }
+
+  // Test parsing the data three times delivering the data in
+  // different chunks.
+  final data = message.codeUnits;
+  test('test', () {
+    expect(
+        Future.wait([
+          testWrite(data),
+          testWrite(data, 10),
+          testWrite(data, 2),
+          testWrite(data, 1),
+        ]),
+        completes);
+  });
+
+  if (expectedParts!.isNotEmpty) {
+    test('test-first-part-only', () {
+      expect(
+          Future.wait([
+            testFirstPartOnly(data),
+            testFirstPartOnly(data, 10),
+            testFirstPartOnly(data, 2),
+            testFirstPartOnly(data, 1),
+          ]),
+          completes);
+    });
+
+    test('test-n-parts-only', () {
+      var numPartsExpected = expectedParts.length - 1;
+      if (numPartsExpected == 0) numPartsExpected = 1;
+
+      expect(
+          Future.wait([
+            testCompletePartAfterCancel(data, numPartsExpected),
+            testCompletePartAfterCancel(data, numPartsExpected, 10),
+            testCompletePartAfterCancel(data, numPartsExpected, 2),
+            testCompletePartAfterCancel(data, numPartsExpected, 1),
+          ]),
+          completes);
+    });
+  }
+}
+
+void _testParse(String message, String boundary,
+    [List<Map<String, String>>? expectedHeaders,
+    List<String?>? expectedParts,
+    bool expectError = false]) {
+  _runParseTest(message, boundary, TestMode.immediateListen, expectedHeaders,
+      expectedParts, expectError);
+  _runParseTest(message, boundary, TestMode.delayListen, expectedHeaders,
+      expectedParts, expectError);
+  _runParseTest(message, boundary, TestMode.pauseResume, expectedHeaders,
+      expectedParts, expectError);
+}
+
+void _testParseValid() {
+  // Empty message from Chrome form post.
+  var message = '------WebKitFormBoundaryU3FBruSkJKG0Yor1--\r\n';
+  _testParse(message, '----WebKitFormBoundaryU3FBruSkJKG0Yor1', [], []);
+
+  // Sample from Wikipedia.
+  message = '''
+This is a message with multiple parts in MIME format.\r
+--frontier\r
+Content-Type: text/plain\r
+\r
+This is the body of the message.\r
+--frontier\r
+Content-Type: application/octet-stream\r
+Content-Transfer-Encoding: base64\r
+\r
+PGh0bWw+CiAgPGhlYWQ+CiAgPC9oZWFkPgogIDxib2R5PgogICAgPHA+VGhpcyBpcyB0aGUg
+Ym9keSBvZiB0aGUgbWVzc2FnZS48L3A+CiAgPC9ib2R5Pgo8L2h0bWw+Cg=\r
+--frontier--\r\n''';
+  var headers1 = <String, String>{'content-type': 'text/plain'};
+  var headers2 = <String, String>{
+    'content-type': 'application/octet-stream',
+    'content-transfer-encoding': 'base64'
+  };
+  var body1 = 'This is the body of the message.';
+  var body2 = '''
+PGh0bWw+CiAgPGhlYWQ+CiAgPC9oZWFkPgogIDxib2R5PgogICAgPHA+VGhpcyBpcyB0aGUg
+Ym9keSBvZiB0aGUgbWVzc2FnZS48L3A+CiAgPC9ib2R5Pgo8L2h0bWw+Cg=''';
+  _testParse(message, 'frontier', [headers1, headers2], [body1, body2]);
+
+  // Sample from HTML 4.01 Specification.
+  message = '''
+\r\n--AaB03x\r
+Content-Disposition: form-data; name="submit-name"\r
+\r
+Larry\r
+--AaB03x\r
+Content-Disposition: form-data; name="files"; filename="file1.txt"\r
+Content-Type: text/plain\r
+\r
+... contents of file1.txt ...\r
+--AaB03x--\r\n''';
+  headers1 = <String, String>{
+    'content-disposition': 'form-data; name="submit-name"'
+  };
+  headers2 = <String, String>{
+    'content-type': 'text/plain',
+    'content-disposition': 'form-data; name="files"; filename="file1.txt"'
+  };
+  body1 = 'Larry';
+  body2 = '... contents of file1.txt ...';
+  _testParse(message, 'AaB03x', [headers1, headers2], [body1, body2]);
+
+  // Longer form from submitting the following from Chrome.
+  //
+  // <html>
+  // <body>
+  // <FORM action="http://127.0.0.1:1234/"
+  //     enctype="multipart/form-data"
+  //     method='post'>
+  //  <P>
+  //  Text: <INPUT type='text' name='text_input'>
+  //  Password: <INPUT type='password' name='password_input'>
+  //  Checkbox: <INPUT type='checkbox' name='checkbox_input'>
+  //  Radio: <INPUT type='radio' name='radio_input'>
+  //  Send <INPUT type='submit'>
+  //  </P>
+  // </FORM>
+  // </body>
+  // </html>
+
+  message = '''
+\r\n------WebKitFormBoundaryQ3cgYAmGRF8yOeYB\r
+Content-Disposition: form-data; name="text_input"\r
+\r
+text\r
+------WebKitFormBoundaryQ3cgYAmGRF8yOeYB\r
+Content-Disposition: form-data; name="password_input"\r
+\r
+password\r
+------WebKitFormBoundaryQ3cgYAmGRF8yOeYB\r
+Content-Disposition: form-data; name="checkbox_input"\r
+\r
+on\r
+------WebKitFormBoundaryQ3cgYAmGRF8yOeYB\r
+Content-Disposition: form-data; name="radio_input"\r
+\r
+on\r
+------WebKitFormBoundaryQ3cgYAmGRF8yOeYB--\r\n''';
+  headers1 = <String, String>{
+    'content-disposition': 'form-data; name="text_input"'
+  };
+  headers2 = <String, String>{
+    'content-disposition': 'form-data; name="password_input"'
+  };
+  final headers3 = <String, String>{
+    'content-disposition': 'form-data; name="checkbox_input"'
+  };
+  final headers4 = <String, String>{
+    'content-disposition': 'form-data; name="radio_input"'
+  };
+  body1 = 'text';
+  body2 = 'password';
+  const body3 = 'on';
+  const body4 = 'on';
+  _testParse(message, '----WebKitFormBoundaryQ3cgYAmGRF8yOeYB',
+      [headers1, headers2, headers3, headers4], [body1, body2, body3, body4]);
+
+  // Same form from Firefox.
+  message = '''
+\r\n-----------------------------52284550912143824192005403738\r
+Content-Disposition: form-data; name="text_input"\r
+\r
+text\r
+-----------------------------52284550912143824192005403738\r
+Content-Disposition: form-data; name="password_input"\r
+\r
+password\r
+-----------------------------52284550912143824192005403738\r
+Content-Disposition: form-data; name="checkbox_input"\r
+\r
+on\r
+-----------------------------52284550912143824192005403738\r
+Content-Disposition: form-data; name="radio_input"\r
+\r
+on\r
+-----------------------------52284550912143824192005403738--\r\n''';
+  _testParse(
+      message,
+      '---------------------------52284550912143824192005403738',
+      [headers1, headers2, headers3, headers4],
+      [body1, body2, body3, body4]);
+
+  // And Internet Explorer
+  message = '''
+\r\n-----------------------------7dc8f38c60326\r
+Content-Disposition: form-data; name="text_input"\r
+\r
+text\r
+-----------------------------7dc8f38c60326\r
+Content-Disposition: form-data; name="password_input"\r
+\r
+password\r
+-----------------------------7dc8f38c60326\r
+Content-Disposition: form-data; name="checkbox_input"\r
+\r
+on\r
+-----------------------------7dc8f38c60326\r
+Content-Disposition: form-data; name="radio_input"\r
+\r
+on\r
+-----------------------------7dc8f38c60326--\r\n''';
+  _testParse(message, '---------------------------7dc8f38c60326',
+      [headers1, headers2, headers3, headers4], [body1, body2, body3, body4]);
+
+  // Test boundary prefix inside prefix and content.
+  message = '''
+-\r
+--\r
+--b\r
+--bo\r
+--bou\r
+--boun\r
+--bound\r
+--bounda\r
+--boundar\r
+--boundary\r
+Content-Type: text/plain\r
+\r
+-\r
+--\r
+--b\r
+--bo\r
+--bou\r
+--boun\r
+--bound\r\r
+--bounda\r\r\r
+--boundar\r\r\r\r
+--boundary\r
+Content-Type: text/plain\r
+\r
+--boundar\r
+--bounda\r
+--bound\r
+--boun\r
+--bou\r
+--bo\r
+--b\r\r\r\r
+--\r\r\r
+-\r\r
+--boundary--\r\n''';
+  final headers = <String, String>{'content-type': 'text/plain'};
+  body1 = '''
+-\r
+--\r
+--b\r
+--bo\r
+--bou\r
+--boun\r
+--bound\r\r
+--bounda\r\r\r
+--boundar\r\r\r''';
+  body2 = '''
+--boundar\r
+--bounda\r
+--bound\r
+--boun\r
+--bou\r
+--bo\r
+--b\r\r\r\r
+--\r\r\r
+-\r''';
+  _testParse(message, 'boundary', [headers, headers], [body1, body2]);
+
+  // Without initial CRLF.
+  message = '''
+--xxx\r
+\r
+\r
+Body 1\r
+--xxx\r
+\r
+\r
+Body2\r
+--xxx--\r\n''';
+  _testParse(message, 'xxx', null, ['\r\nBody 1', '\r\nBody2']);
+}
+
+void _testParseInvalid() {
+  // Missing end boundary.
+  const message = '''
+\r
+--xxx\r
+\r
+\r
+Body 1\r
+--xxx\r
+\r
+\r
+Body2\r
+--xxx\r\n''';
+  _testParse(message, 'xxx', null, [null, null], true);
+}
+
+void main() {
+  _testParseValid();
+  _testParseInvalid();
+}
diff --git a/pkgs/mime/test/mime_type_test.dart b/pkgs/mime/test/mime_type_test.dart
new file mode 100644
index 0000000..23cb34a
--- /dev/null
+++ b/pkgs/mime/test/mime_type_test.dart
@@ -0,0 +1,320 @@
+// Copyright (c) 2013, 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.
+
+import 'dart:math' as math;
+
+import 'package:mime/mime.dart';
+import 'package:mime/src/magic_number.dart';
+import 'package:test/test.dart';
+
+void _expectMimeType(String path, String? expectedMimeType,
+    {List<int>? headerBytes, MimeTypeResolver? resolver}) {
+  String? mimeType;
+  if (resolver == null) {
+    mimeType = lookupMimeType(path, headerBytes: headerBytes);
+  } else {
+    mimeType = resolver.lookup(path, headerBytes: headerBytes);
+  }
+
+  expect(mimeType, expectedMimeType);
+}
+
+void main() {
+  group('global-lookup', () {
+    test('by-path', () {
+      _expectMimeType('file.dart', 'text/x-dart');
+      // Test mixed-case
+      _expectMimeType('file.DaRT', 'text/x-dart');
+      _expectMimeType('file.dcm', 'application/dicom');
+      _expectMimeType('file.html', 'text/html');
+      _expectMimeType('file.xhtml', 'application/xhtml+xml');
+      _expectMimeType('file.jpeg', 'image/jpeg');
+      _expectMimeType('file.jpg', 'image/jpeg');
+      _expectMimeType('file.png', 'image/png');
+      _expectMimeType('file.gif', 'image/gif');
+      _expectMimeType('file.cc', 'text/x-c');
+      _expectMimeType('file.c', 'text/x-c');
+      _expectMimeType('file.css', 'text/css');
+      _expectMimeType('file.js', 'text/javascript');
+      _expectMimeType('file.mjs', 'text/javascript');
+      _expectMimeType('file.ps', 'application/postscript');
+      _expectMimeType('file.pdf', 'application/pdf');
+      _expectMimeType('file.tiff', 'image/tiff');
+      _expectMimeType('file.tif', 'image/tiff');
+      _expectMimeType('file.webp', 'image/webp');
+      _expectMimeType('file.mp3', 'audio/mpeg');
+      _expectMimeType('file.aac', 'audio/aac');
+      _expectMimeType('file.ogg', 'audio/ogg');
+      _expectMimeType('file.aiff', 'audio/x-aiff');
+      _expectMimeType('file.m4a', 'audio/mp4');
+      _expectMimeType('file.m4b', 'audio/mp4');
+      _expectMimeType('file.toml', 'application/toml');
+      _expectMimeType('file.md', 'text/markdown');
+      _expectMimeType('file.markdown', 'text/markdown');
+      _expectMimeType('file.heif', 'image/heif');
+      _expectMimeType('file.heic', 'image/heic');
+    });
+
+    test('unknown-mime-type', () {
+      _expectMimeType('file.unsupported-extension', null);
+    });
+
+    test('by-header-bytes', () {
+      _expectMimeType('file.jpg', 'image/png',
+          headerBytes: [0x89, 0x50, 0x4E, 0x47, 0x0D, 0x0A, 0x1A, 0x0A]);
+      _expectMimeType('file.jpg', 'image/gif', headerBytes: [
+        0x47,
+        0x49,
+        0x46,
+        0x38,
+        0x39,
+        0x61,
+        0x0D,
+        0x0A,
+        0x1A,
+        0x0A
+      ]);
+      _expectMimeType('file.gif', 'image/jpeg', headerBytes: [
+        0xFF,
+        0xD8,
+        0x46,
+        0x38,
+        0x39,
+        0x61,
+        0x0D,
+        0x0A,
+        0x1A,
+        0x0A
+      ]);
+      _expectMimeType('file', 'video/3gpp', headerBytes: [
+        0x00,
+        0x00,
+        0x00,
+        0x04,
+        0x66,
+        0x74,
+        0x79,
+        0x70,
+        0x33,
+        0x67,
+        0x70,
+        0x35
+      ]);
+      _expectMimeType('file.mp4', 'video/mp4', headerBytes: [
+        0x00,
+        0x00,
+        0x00,
+        0x04,
+        0x66,
+        0x74,
+        0x79,
+        0x70,
+        0xFF,
+        0xFF,
+        0xFF,
+        0xFF
+      ]);
+      _expectMimeType('file', 'video/mp4', headerBytes: [
+        0x00,
+        0xF0,
+        0xF0,
+        0xF0,
+        0x66,
+        0x74,
+        0x79,
+        0x70,
+        0x61,
+        0x76,
+        0x63,
+        0x31
+      ]);
+      _expectMimeType('file', 'video/mp4', headerBytes: [
+        0x00,
+        0xF0,
+        0xF0,
+        0xF0,
+        0x66,
+        0x74,
+        0x79,
+        0x70,
+        0x69,
+        0x73,
+        0x6F,
+        0x32
+      ]);
+      _expectMimeType('file', 'video/mp4', headerBytes: [
+        0x00,
+        0xF0,
+        0xF0,
+        0xF0,
+        0x66,
+        0x74,
+        0x79,
+        0x70,
+        0x69,
+        0x73,
+        0x6F,
+        0x6D
+      ]);
+      _expectMimeType('file', 'video/mp4', headerBytes: [
+        0x00,
+        0xF0,
+        0xF0,
+        0xF0,
+        0x66,
+        0x74,
+        0x79,
+        0x70,
+        0x6D,
+        0x70,
+        0x34,
+        0x31
+      ]);
+      _expectMimeType('file', 'video/mp4', headerBytes: [
+        0x00,
+        0xF0,
+        0xF0,
+        0xF0,
+        0x66,
+        0x74,
+        0x79,
+        0x70,
+        0x6D,
+        0x70,
+        0x34,
+        0x32
+      ]);
+      _expectMimeType('file', 'image/webp', headerBytes: [
+        0x52,
+        0x49,
+        0x46,
+        0x46,
+        0xE2,
+        0x4A,
+        0x01,
+        0x00,
+        0x57,
+        0x45,
+        0x42,
+        0x50
+      ]);
+      _expectMimeType('file', 'audio/mpeg',
+          headerBytes: [0x49, 0x44, 0x33, 0x0D, 0x0A, 0x1A, 0x0A]);
+      _expectMimeType('file', 'audio/aac',
+          headerBytes: [0xFF, 0xF1, 0x0D, 0x0A, 0x1A, 0x0A]);
+      _expectMimeType('file', 'audio/ogg',
+          headerBytes: [0x4F, 0x70, 0x75, 0x0D, 0x0A, 0x1A, 0x0A]);
+      _expectMimeType('file', 'audio/x-aiff', headerBytes: [
+        0x46,
+        0x4F,
+        0x52,
+        0x4D,
+        0x04,
+        0x0B,
+        0xEF,
+        0xF4,
+        0x41,
+        0x49,
+        0x46,
+        0x46
+      ]);
+      _expectMimeType('file', 'audio/x-flac',
+          headerBytes: [0x66, 0x4C, 0x61, 0x43]);
+      _expectMimeType('file', 'audio/x-wav', headerBytes: [
+        0x52,
+        0x49,
+        0x46,
+        0x46,
+        0xA6,
+        0x4E,
+        0x70,
+        0x03,
+        0x57,
+        0x41,
+        0x56,
+        0x45
+      ]);
+      _expectMimeType('file', 'image/heic', headerBytes: [
+        0x00,
+        0x00,
+        0x00,
+        0x18,
+        0x66,
+        0x74,
+        0x79,
+        0x70,
+        0x68,
+        0x65,
+        0x69,
+        0x63,
+        0x00
+      ]);
+      _expectMimeType('file', 'image/heic', headerBytes: [
+        0x00,
+        0x00,
+        0x00,
+        0x18,
+        0x66,
+        0x74,
+        0x79,
+        0x70,
+        0x68,
+        0x65,
+        0x69,
+        0x78,
+        0x00
+      ]);
+      _expectMimeType('file', 'image/heif', headerBytes: [
+        0x00,
+        0x00,
+        0x00,
+        0x18,
+        0x66,
+        0x74,
+        0x79,
+        0x70,
+        0x6D,
+        0x69,
+        0x66,
+        0x31,
+        0x00
+      ]);
+    });
+  });
+
+  group('custom-resolver', () {
+    test('override-extension', () {
+      final resolver = MimeTypeResolver();
+      resolver.addExtension('jpg', 'my-mime-type');
+      _expectMimeType('file.jpg', 'my-mime-type', resolver: resolver);
+    });
+
+    test('fallthrough-extension', () {
+      final resolver = MimeTypeResolver();
+      resolver.addExtension('jpg2', 'my-mime-type');
+      _expectMimeType('file.jpg', 'image/jpeg', resolver: resolver);
+    });
+
+    test('with-mask', () {
+      final resolver = MimeTypeResolver.empty();
+      resolver.addMagicNumber([0x01, 0x02, 0x03], 'my-mime-type',
+          mask: [0x01, 0xFF, 0xFE]);
+      _expectMimeType('file', 'my-mime-type',
+          headerBytes: [0x01, 0x02, 0x03], resolver: resolver);
+      _expectMimeType('file', null,
+          headerBytes: [0x01, 0x03, 0x03], resolver: resolver);
+      _expectMimeType('file', 'my-mime-type',
+          headerBytes: [0xFF, 0x02, 0x02], resolver: resolver);
+    });
+  });
+
+  test('default magic number', () {
+    final actualMaxBytes = initialMagicNumbers.fold<int>(
+      0,
+      (previous, magic) => math.max(previous, magic.numbers.length),
+    );
+
+    expect(initialMagicNumbersMaxLength, actualMaxBytes);
+  });
+}
diff --git a/pkgs/oauth2/.gitignore b/pkgs/oauth2/.gitignore
new file mode 100644
index 0000000..bbe1007
--- /dev/null
+++ b/pkgs/oauth2/.gitignore
@@ -0,0 +1,16 @@
+# Don’t commit the following directories created by pub.
+.buildlog
+.pub/
+.dart_tool/
+build/
+packages
+.packages
+
+# Or the files created by dart2js.
+*.dart.js
+*.js_
+*.js.deps
+*.js.map
+
+# Include when developing application packages.
+pubspec.lock
\ No newline at end of file
diff --git a/pkgs/oauth2/CHANGELOG.md b/pkgs/oauth2/CHANGELOG.md
new file mode 100644
index 0000000..ff39de3
--- /dev/null
+++ b/pkgs/oauth2/CHANGELOG.md
@@ -0,0 +1,135 @@
+## 2.0.4-wip
+
+* Require Dart 3.4
+
+## 2.0.3
+
+* Require `package:http` v1.0.0
+* Move to `dart-lang/tools`.
+
+## 2.0.2
+
+* Require Dart 3.0.
+* Support `package:http` 1.0.0.
+
+## 2.0.1
+
+* Handle `expires_in` when encoded as string.
+* Populate the pubspec `repository` field.
+* Increase the minimum Dart SDK to `2.17.0`.
+
+## 2.0.0
+
+* Migrate to null safety.
+
+## 1.6.3
+
+* Added optional `codeVerifier` parameter to `AuthorizationCodeGrant` constructor.
+
+## 1.6.1
+
+* Added fix to make sure that credentials are only refreshed once when multiple calls are made.
+
+## 1.6.0
+
+* Added PKCE support to `AuthorizationCodeGrant`.
+
+## 1.5.0
+
+* Added support for `clientCredentialsGrant`.
+
+## 1.4.0
+
+* OpenID's id_token treated.
+
+## 1.3.0
+
+* Added `onCredentialsRefreshed` option when creating `Client` objects.
+
+## 1.2.3
+
+* Support the latest `package:http` release.
+
+## 1.2.2
+
+* Allow the stable 2.0 SDK.
+
+## 1.2.1
+
+* Updated SDK version to 2.0.0-dev.17.0
+
+## 1.2.0
+
+* Add a `getParameter()` parameter to `new AuthorizationCodeGrant()`, `new
+  Credentials()`, and `resourceOwnerPasswordGrant()`. This controls how the
+  authorization server's response is parsed for servers that don't provide the
+  standard JSON response.
+
+## 1.1.1
+
+* `resourceOwnerPasswordGrant()` now properly uses its HTTP client for requests
+  made by the OAuth2 client it returns.
+
+## 1.1.0
+
+* Add a `delimiter` parameter to `new AuthorizationCodeGrant()`, `new
+  Credentials()`, and `resourceOwnerPasswordGrant()`. This controls the
+  delimiter between scopes, which some authorization servers require to be
+  different values than the specified `' '`.
+
+## 1.0.2
+
+* Fix all strong-mode warnings.
+* Support `crypto` 1.0.0.
+* Support `http_parser` 3.0.0.
+
+## 1.0.1
+
+* Support `http_parser` 2.0.0.
+
+## 1.0.0
+
+### Breaking changes
+
+* Requests that use client authentication, such as the
+  `AuthorizationCodeGrant`'s access token request and `Credentials`' refresh
+  request, now use HTTP Basic authentication by default. This form of
+  authentication is strongly recommended by the OAuth 2.0 spec. The new
+  `basicAuth` parameter may be set to `false` to force form-based authentication
+  for servers that require it.
+
+* `new AuthorizationCodeGrant()` now takes `secret` as an optional named
+  argument rather than a required argument. This matches the OAuth 2.0 spec,
+  which says that a client secret is only required for confidential clients.
+
+* `new Client()` and `Credentials.refresh()` now take both `identifier` and
+  `secret` as optional named arguments rather than required arguments. This
+  matches the OAuth 2.0 spec, which says that the server may choose not to
+  require client authentication for some flows.
+
+* `new Credentials()` now takes named arguments rather than optional positional
+  arguments.
+
+### Non-breaking changes
+
+* Added a `resourceOwnerPasswordGrant` method.
+
+* The `scopes` argument to `AuthorizationCodeGrant.getAuthorizationUrl()` and
+  `new Credentials()` and the `newScopes` argument to `Credentials.refresh` now
+  take an `Iterable` rather than just a `List`.
+
+* The `scopes` argument to `AuthorizationCodeGrant.getAuthorizationUrl()` now
+  defaults to `null` rather than `const []`.
+
+# 0.9.3
+
+* Update the `http` dependency.
+
+* Since `http` 0.11.0 now works in non-`dart:io` contexts, `oauth2` does as
+  well.
+
+## 0.9.2
+
+* Expand the dependency on the HTTP package to include 0.10.x.
+
+* Add a README file.
diff --git a/pkgs/oauth2/LICENSE b/pkgs/oauth2/LICENSE
new file mode 100644
index 0000000..162572a
--- /dev/null
+++ b/pkgs/oauth2/LICENSE
@@ -0,0 +1,27 @@
+Copyright 2014, the Dart project authors.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+    * Redistributions of source code must retain the above copyright
+      notice, this list of conditions and the following disclaimer.
+    * Redistributions in binary form must reproduce the above
+      copyright notice, this list of conditions and the following
+      disclaimer in the documentation and/or other materials provided
+      with the distribution.
+    * Neither the name of Google LLC nor the names of its
+      contributors may be used to endorse or promote products derived
+      from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
diff --git a/pkgs/oauth2/README.md b/pkgs/oauth2/README.md
new file mode 100644
index 0000000..07a5976
--- /dev/null
+++ b/pkgs/oauth2/README.md
@@ -0,0 +1,260 @@
+[![Dart CI](https://github.com/dart-lang/tools/actions/workflows/oauth2.yml/badge.svg)](https://github.com/dart-lang/tools/actions/workflows/oauth2.yml)
+[![pub package](https://img.shields.io/pub/v/oauth2.svg)](https://pub.dev/packages/oauth2)
+[![package publisher](https://img.shields.io/pub/publisher/oauth2.svg)](https://pub.dev/packages/oauth2/publisher)
+
+A client library for authenticating with a remote service via OAuth2 on behalf
+of a user, and making authorized HTTP requests with the user's OAuth2
+credentials.
+
+## About OAuth2
+
+OAuth2 allows a client (the program using this library) to access and manipulate
+a resource that's owned by a resource owner (the end user) and lives on a remote
+server. The client directs the resource owner to an authorization server
+(usually but not always the same as the server that hosts the resource), where
+the resource owner tells the authorization server to give the client an access
+token. This token serves as proof that the client has permission to access
+resources on behalf of the resource owner.
+
+OAuth2 provides several different methods for the client to obtain
+authorization. At the time of writing, this library only supports the
+[Authorization Code Grant][authorizationCodeGrantSection],
+[Client Credentials Grant][clientCredentialsGrantSection] and
+[Resource Owner Password Grant][resourceOwnerPasswordGrantSection] flows, but
+more may be added in the future.
+
+## Authorization Code Grant
+
+**Resources:** [Class summary][authorizationCodeGrantMethod],
+[OAuth documentation][authorizationCodeGrantDocs]
+
+```dart
+import 'dart:io';
+
+import 'package:oauth2/oauth2.dart' as oauth2;
+
+// These URLs are endpoints that are provided by the authorization
+// server. They're usually included in the server's documentation of its
+// OAuth2 API.
+final authorizationEndpoint =
+    Uri.parse('http://example.com/oauth2/authorization');
+final tokenEndpoint = Uri.parse('http://example.com/oauth2/token');
+
+// The authorization server will issue each client a separate client
+// identifier and secret, which allows the server to tell which client
+// is accessing it. Some servers may also have an anonymous
+// identifier/secret pair that any client may use.
+//
+// Note that clients whose source code or binary executable is readily
+// available may not be able to make sure the client secret is kept a
+// secret. This is fine; OAuth2 servers generally won't rely on knowing
+// with certainty that a client is who it claims to be.
+final identifier = 'my client identifier';
+final secret = 'my client secret';
+
+// This is a URL on your application's server. The authorization server
+// will redirect the resource owner here once they've authorized the
+// client. The redirection will include the authorization code in the
+// query parameters.
+final redirectUrl = Uri.parse('http://my-site.com/oauth2-redirect');
+
+/// A file in which the users credentials are stored persistently. If the server
+/// issues a refresh token allowing the client to refresh outdated credentials,
+/// these may be valid indefinitely, meaning the user never has to
+/// re-authenticate.
+final credentialsFile = File('~/.myapp/credentials.json');
+
+/// Either load an OAuth2 client from saved credentials or authenticate a new
+/// one.
+Future<oauth2.Client> createClient() async {
+  var exists = await credentialsFile.exists();
+
+  // If the OAuth2 credentials have already been saved from a previous run, we
+  // just want to reload them.
+  if (exists) {
+    var credentials =
+        oauth2.Credentials.fromJson(await credentialsFile.readAsString());
+    return oauth2.Client(credentials, identifier: identifier, secret: secret);
+  }
+
+  // If we don't have OAuth2 credentials yet, we need to get the resource owner
+  // to authorize us. We're assuming here that we're a command-line application.
+  var grant = oauth2.AuthorizationCodeGrant(
+      identifier, authorizationEndpoint, tokenEndpoint,
+      secret: secret);
+
+  // A URL on the authorization server (authorizationEndpoint with some additional
+  // query parameters). Scopes and state can optionally be passed into this method.
+  var authorizationUrl = grant.getAuthorizationUrl(redirectUrl);
+
+  // Redirect the resource owner to the authorization URL. Once the resource
+  // owner has authorized, they'll be redirected to `redirectUrl` with an
+  // authorization code. The `redirect` should cause the browser to redirect to
+  // another URL which should also have a listener.
+  //
+  // `redirect` and `listen` are not shown implemented here. See below for the
+  // details.
+  await redirect(authorizationUrl);
+  var responseUrl = await listen(redirectUrl);
+
+  // Once the user is redirected to `redirectUrl`, pass the query parameters to
+  // the AuthorizationCodeGrant. It will validate them and extract the
+  // authorization code to create a new Client.
+  return await grant.handleAuthorizationResponse(responseUrl.queryParameters);
+}
+
+void main() async {
+  var client = await createClient();
+
+  // Once you have a Client, you can use it just like any other HTTP client.
+  print(await client.read('http://example.com/protected-resources.txt'));
+
+  // Once we're done with the client, save the credentials file. This ensures
+  // that if the credentials were automatically refreshed while using the
+  // client, the new credentials are available for the next run of the
+  // program.
+  await credentialsFile.writeAsString(client.credentials.toJson());
+}
+```
+
+<details>
+  <summary>Click here to learn how to implement `redirect` and `listen`.</summary>
+
+--------------------------------------------------------------------------------
+
+There is not a universal example for implementing `redirect` and `listen`,
+because different options exist for each platform.
+
+For Flutter apps, there's two popular approaches:
+
+1.  Launch a browser using [url_launcher][] and listen for a redirect using
+    [uni_links][].
+
+    ```dart
+      if (await canLaunch(authorizationUrl.toString())) {
+        await launch(authorizationUrl.toString()); }
+
+      // ------- 8< -------
+
+      final linksStream = getLinksStream().listen((Uri uri) async {
+       if (uri.toString().startsWith(redirectUrl)) {
+         responseUrl = uri;
+       }
+     });
+    ```
+
+1.  Launch a WebView inside the app and listen for a redirect using
+    [webview_flutter][].
+
+    ```dart
+      WebView(
+        javascriptMode: JavascriptMode.unrestricted,
+        initialUrl: authorizationUrl.toString(),
+        navigationDelegate: (navReq) {
+          if (navReq.url.startsWith(redirectUrl)) {
+            responseUrl = Uri.parse(navReq.url);
+            return NavigationDecision.prevent;
+          }
+          return NavigationDecision.navigate;
+        },
+        // ------- 8< -------
+      );
+    ```
+
+For Dart apps, the best approach depends on the available options for accessing
+a browser. In general, you'll need to launch the authorization URL through the
+client's browser and listen for the redirect URL.
+</details>
+
+## Client Credentials Grant
+
+**Resources:** [Method summary][clientCredentialsGrantMethod],
+[OAuth documentation][clientCredentialsGrantDocs]
+
+```dart
+// This URL is an endpoint that's provided by the authorization server. It's
+// usually included in the server's documentation of its OAuth2 API.
+final authorizationEndpoint =
+    Uri.parse('http://example.com/oauth2/authorization');
+
+// The OAuth2 specification expects a client's identifier and secret
+// to be sent when using the client credentials grant.
+//
+// Because the client credentials grant is not inherently associated with a user,
+// it is up to the server in question whether the returned token allows limited
+// API access.
+//
+// Either way, you must provide both a client identifier and a client secret:
+final identifier = 'my client identifier';
+final secret = 'my client secret';
+
+// Calling the top-level `clientCredentialsGrant` function will return a
+// [Client] instead.
+var client = await oauth2.clientCredentialsGrant(
+    authorizationEndpoint, identifier, secret);
+
+// With an authenticated client, you can make requests, and the `Bearer` token
+// returned by the server during the client credentials grant will be attached
+// to any request you make.
+var response =
+    await client.read('https://example.com/api/some_resource.json');
+
+// You can save the client's credentials, which consists of an access token, and
+// potentially a refresh token and expiry date, to a file. This way, subsequent runs
+// do not need to reauthenticate, and you can avoid saving the client identifier and
+// secret.
+await credentialsFile.writeAsString(client.credentials.toJson());
+```
+
+## Resource Owner Password Grant
+
+**Resources:** [Method summary][resourceOwnerPasswordGrantMethod],
+[OAuth documentation][resourceOwnerPasswordGrantDocs]
+
+```dart
+// This URL is an endpoint that's provided by the authorization server. It's
+// usually included in the server's documentation of its OAuth2 API.
+final authorizationEndpoint =
+    Uri.parse('http://example.com/oauth2/authorization');
+
+// The user should supply their own username and password.
+final username = 'example user';
+final password = 'example password';
+
+// The authorization server may issue each client a separate client
+// identifier and secret, which allows the server to tell which client
+// is accessing it. Some servers may also have an anonymous
+// identifier/secret pair that any client may use.
+//
+// Some servers don't require the client to authenticate itself, in which case
+// these should be omitted.
+final identifier = 'my client identifier';
+final secret = 'my client secret';
+
+// Make a request to the authorization endpoint that will produce the fully
+// authenticated Client.
+var client = await oauth2.resourceOwnerPasswordGrant(
+    authorizationEndpoint, username, password,
+    identifier: identifier, secret: secret);
+
+// Once you have the client, you can use it just like any other HTTP client.
+var result = await client.read('http://example.com/protected-resources.txt');
+
+// Once we're done with the client, save the credentials file. This will allow
+// us to re-use the credentials and avoid storing the username and password
+// directly.
+File('~/.myapp/credentials.json').writeAsString(client.credentials.toJson());
+```
+
+[authorizationCodeGrantDocs]: https://oauth.net/2/grant-types/authorization-code/
+[authorizationCodeGrantMethod]: https://pub.dev/documentation/oauth2/latest/oauth2/AuthorizationCodeGrant-class.html
+[authorizationCodeGrantSection]: #authorization-code-grant
+[clientCredentialsGrantDocs]: https://oauth.net/2/grant-types/client-credentials/
+[clientCredentialsGrantMethod]: https://pub.dev/documentation/oauth2/latest/oauth2/clientCredentialsGrant.html
+[clientCredentialsGrantSection]: #client-credentials-grant
+[resourceOwnerPasswordGrantDocs]: https://oauth.net/2/grant-types/password/
+[resourceOwnerPasswordGrantMethod]: https://pub.dev/documentation/oauth2/latest/oauth2/resourceOwnerPasswordGrant.html
+[resourceOwnerPasswordGrantSection]: #resource-owner-password-grant
+[uni_links]: https://pub.dev/packages/uni_links
+[url_launcher]: https://pub.dev/packages/url_launcher
+[webview_flutter]: https://pub.dev/packages/webview_flutter
diff --git a/pkgs/oauth2/analysis_options.yaml b/pkgs/oauth2/analysis_options.yaml
new file mode 100644
index 0000000..e21412c
--- /dev/null
+++ b/pkgs/oauth2/analysis_options.yaml
@@ -0,0 +1,23 @@
+include: package:dart_flutter_team_lints/analysis_options.yaml
+
+analyzer:
+  errors:
+    # Too many exceptions
+    comment_references: ignore
+  language:
+    strict-casts: true
+    strict-raw-types: true
+
+linter:
+  rules:
+    - avoid_private_typedef_functions
+    - avoid_unused_constructor_parameters
+    - avoid_void_async
+    - cancel_subscriptions
+    - literal_only_boolean_expressions
+    - no_adjacent_strings_in_list
+    - no_runtimeType_toString
+    - package_api_docs
+    - prefer_const_declarations
+    - unnecessary_await_in_return
+    - use_string_buffers
diff --git a/pkgs/oauth2/example/main.dart b/pkgs/oauth2/example/main.dart
new file mode 100644
index 0000000..68e5aa0
--- /dev/null
+++ b/pkgs/oauth2/example/main.dart
@@ -0,0 +1,100 @@
+// Copyright (c) 2024, 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.
+
+import 'dart:async';
+import 'dart:io';
+
+import 'package:oauth2/oauth2.dart' as oauth2;
+
+// These URLs are endpoints that are provided by the authorization
+// server. They're usually included in the server's documentation of its
+// OAuth2 API.
+final authorizationEndpoint =
+    Uri.parse('http://example.com/oauth2/authorization');
+final tokenEndpoint = Uri.parse('http://example.com/oauth2/token');
+
+// The authorization server will issue each client a separate client
+// identifier and secret, which allows the server to tell which client
+// is accessing it. Some servers may also have an anonymous
+// identifier/secret pair that any client may use.
+//
+// Note that clients whose source code or binary executable is readily
+// available may not be able to make sure the client secret is kept a
+// secret. This is fine; OAuth2 servers generally won't rely on knowing
+// with certainty that a client is who it claims to be.
+const identifier = 'my client identifier';
+const secret = 'my client secret';
+
+// This is a URL on your application's server. The authorization server
+// will redirect the resource owner here once they've authorized the
+// client. The redirection will include the authorization code in the
+// query parameters.
+final redirectUrl = Uri.parse('http://my-site.com/oauth2-redirect');
+
+/// A file in which the users credentials are stored persistently. If the server
+/// issues a refresh token allowing the client to refresh outdated credentials,
+/// these may be valid indefinitely, meaning the user never has to
+/// re-authenticate.
+final credentialsFile = File('~/.myapp/credentials.json');
+
+/// Either load an OAuth2 client from saved credentials or authenticate a new
+/// one.
+Future<oauth2.Client> createClient() async {
+  var exists = await credentialsFile.exists();
+
+  // If the OAuth2 credentials have already been saved from a previous run, we
+  // just want to reload them.
+  if (exists) {
+    var credentials =
+        oauth2.Credentials.fromJson(await credentialsFile.readAsString());
+    return oauth2.Client(credentials, identifier: identifier, secret: secret);
+  }
+
+  // If we don't have OAuth2 credentials yet, we need to get the resource owner
+  // to authorize us. We're assuming here that we're a command-line application.
+  var grant = oauth2.AuthorizationCodeGrant(
+      identifier, authorizationEndpoint, tokenEndpoint,
+      secret: secret);
+
+  // A URL on the authorization server (authorizationEndpoint with some
+  // additional query parameters). Scopes and state can optionally be passed
+  // into this method.
+  var authorizationUrl = grant.getAuthorizationUrl(redirectUrl);
+
+  // Redirect the resource owner to the authorization URL. Once the resource
+  // owner has authorized, they'll be redirected to `redirectUrl` with an
+  // authorization code. The `redirect` should cause the browser to redirect to
+  // another URL which should also have a listener.
+  //
+  // `redirect` and `listen` are not shown implemented here.
+  await redirect(authorizationUrl);
+  var responseUrl = await listen(redirectUrl);
+
+  // Once the user is redirected to `redirectUrl`, pass the query parameters to
+  // the AuthorizationCodeGrant. It will validate them and extract the
+  // authorization code to create a new Client.
+  return grant.handleAuthorizationResponse(responseUrl.queryParameters);
+}
+
+void main() async {
+  var client = await createClient();
+
+  // Once you have a Client, you can use it just like any other HTTP client.
+  print(await client.read(Uri.http('example.com', 'protected-resources.txt')));
+
+  // Once we're done with the client, save the credentials file. This ensures
+  // that if the credentials were automatically refreshed while using the
+  // client, the new credentials are available for the next run of the
+  // program.
+  await credentialsFile.writeAsString(client.credentials.toJson());
+}
+
+Future<void> redirect(Uri url) async {
+  // Client implementation detail
+}
+
+Future<Uri> listen(Uri url) async {
+  // Client implementation detail
+  return Uri();
+}
diff --git a/pkgs/oauth2/lib/oauth2.dart b/pkgs/oauth2/lib/oauth2.dart
new file mode 100644
index 0000000..45efc5c
--- /dev/null
+++ b/pkgs/oauth2/lib/oauth2.dart
@@ -0,0 +1,11 @@
+// Copyright (c) 2012, 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.
+
+export 'src/authorization_code_grant.dart';
+export 'src/authorization_exception.dart';
+export 'src/client.dart';
+export 'src/client_credentials_grant.dart';
+export 'src/credentials.dart';
+export 'src/expiration_exception.dart';
+export 'src/resource_owner_password_grant.dart';
diff --git a/pkgs/oauth2/lib/src/authorization_code_grant.dart b/pkgs/oauth2/lib/src/authorization_code_grant.dart
new file mode 100644
index 0000000..fac56ba
--- /dev/null
+++ b/pkgs/oauth2/lib/src/authorization_code_grant.dart
@@ -0,0 +1,371 @@
+// Copyright (c) 2012, 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.
+
+import 'dart:async';
+import 'dart:convert';
+import 'dart:math';
+
+import 'package:crypto/crypto.dart';
+import 'package:http/http.dart' as http;
+import 'package:http_parser/http_parser.dart';
+
+import 'authorization_exception.dart';
+import 'client.dart';
+import 'credentials.dart';
+import 'handle_access_token_response.dart';
+import 'parameters.dart';
+import 'utils.dart';
+
+/// A class for obtaining credentials via an [authorization code grant][].
+///
+/// This method of authorization involves sending the resource owner to the
+/// authorization server where they will authorize the client. They're then
+/// redirected back to your server, along with an authorization code. This is
+/// used to obtain [Credentials] and create a fully-authorized [Client].
+///
+/// To use this class, you must first call [getAuthorizationUrl] to get the URL
+/// to which to redirect the resource owner. Then once they've been redirected
+/// back to your application, call [handleAuthorizationResponse] or
+/// [handleAuthorizationCode] to process the authorization server's response and
+/// construct a [Client].
+///
+/// [authorization code grant]: http://tools.ietf.org/html/draft-ietf-oauth-v2-31#section-4.1
+class AuthorizationCodeGrant {
+  /// The function used to parse parameters from a host's response.
+  final GetParameters _getParameters;
+
+  /// The client identifier for this client.
+  ///
+  /// The authorization server will issue each client a separate client
+  /// identifier and secret, which allows the server to tell which client is
+  /// accessing it. Some servers may also have an anonymous identifier/secret
+  /// pair that any client may use.
+  ///
+  /// This is usually global to the program using this library.
+  final String identifier;
+
+  /// The client secret for this client.
+  ///
+  /// The authorization server will issue each client a separate client
+  /// identifier and secret, which allows the server to tell which client is
+  /// accessing it. Some servers may also have an anonymous identifier/secret
+  /// pair that any client may use.
+  ///
+  /// This is usually global to the program using this library.
+  ///
+  /// Note that clients whose source code or binary executable is readily
+  /// available may not be able to make sure the client secret is kept a secret.
+  /// This is fine; OAuth2 servers generally won't rely on knowing with
+  /// certainty that a client is who it claims to be.
+  final String? secret;
+
+  /// A URL provided by the authorization server that serves as the base for the
+  /// URL that the resource owner will be redirected to to authorize this
+  /// client.
+  ///
+  /// This will usually be listed in the authorization server's OAuth2 API
+  /// documentation.
+  final Uri authorizationEndpoint;
+
+  /// A URL provided by the authorization server that this library uses to
+  /// obtain long-lasting credentials.
+  ///
+  /// This will usually be listed in the authorization server's OAuth2 API
+  /// documentation.
+  final Uri tokenEndpoint;
+
+  /// Callback to be invoked whenever the credentials are refreshed.
+  ///
+  /// This will be passed as-is to the constructed [Client].
+  final CredentialsRefreshedCallback? _onCredentialsRefreshed;
+
+  /// Whether to use HTTP Basic authentication for authorizing the client.
+  final bool _basicAuth;
+
+  /// A [String] used to separate scopes; defaults to `" "`.
+  final String _delimiter;
+
+  /// The HTTP client used to make HTTP requests.
+  http.Client? _httpClient;
+
+  /// The URL to which the resource owner will be redirected after they
+  /// authorize this client with the authorization server.
+  Uri? _redirectEndpoint;
+
+  /// The scopes that the client is requesting access to.
+  List<String>? _scopes;
+
+  /// An opaque string that users of this library may specify that will be
+  /// included in the response query parameters.
+  String? _stateString;
+
+  /// The current state of the grant object.
+  _State _state = _State.initial;
+
+  /// Allowed characters for generating the _codeVerifier
+  static const String _charset =
+      'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-._~';
+
+  /// The PKCE code verifier. Will be generated if one is not provided in the
+  /// constructor.
+  final String _codeVerifier;
+
+  /// Creates a new grant.
+  ///
+  /// If [basicAuth] is `true` (the default), the client credentials are sent to
+  /// the server using using HTTP Basic authentication as defined in [RFC 2617].
+  /// Otherwise, they're included in the request body. Note that the latter form
+  /// is not recommended by the OAuth 2.0 spec, and should only be used if the
+  /// server doesn't support Basic authentication.
+  ///
+  /// [RFC 2617]: https://tools.ietf.org/html/rfc2617
+  ///
+  /// [httpClient] is used for all HTTP requests made by this grant, as well as
+  /// those of the [Client] is constructs.
+  ///
+  /// [onCredentialsRefreshed] will be called by the constructed [Client]
+  /// whenever the credentials are refreshed.
+  ///
+  /// [codeVerifier] String to be used as PKCE code verifier. If none is
+  /// provided a random codeVerifier will be generated.
+  /// The codeVerifier must meet requirements specified in [RFC 7636].
+  ///
+  /// [RFC 7636]: https://tools.ietf.org/html/rfc7636#section-4.1
+  ///
+  /// The scope strings will be separated by the provided [delimiter]. This
+  /// defaults to `" "`, the OAuth2 standard, but some APIs (such as Facebook's)
+  /// use non-standard delimiters.
+  ///
+  /// By default, this follows the OAuth2 spec and requires the server's
+  /// responses to be in JSON format. However, some servers return non-standard
+  /// response formats, which can be parsed using the [getParameters] function.
+  ///
+  /// This function is passed the `Content-Type` header of the response as well
+  /// as its body as a UTF-8-decoded string. It should return a map in the same
+  /// format as the [standard JSON response][].
+  ///
+  /// [standard JSON response]: https://tools.ietf.org/html/rfc6749#section-5.1
+  AuthorizationCodeGrant(
+      this.identifier, this.authorizationEndpoint, this.tokenEndpoint,
+      {this.secret,
+      String? delimiter,
+      bool basicAuth = true,
+      http.Client? httpClient,
+      CredentialsRefreshedCallback? onCredentialsRefreshed,
+      Map<String, dynamic> Function(MediaType? contentType, String body)?
+          getParameters,
+      String? codeVerifier})
+      : _basicAuth = basicAuth,
+        _httpClient = httpClient ?? http.Client(),
+        _delimiter = delimiter ?? ' ',
+        _getParameters = getParameters ?? parseJsonParameters,
+        _onCredentialsRefreshed = onCredentialsRefreshed,
+        _codeVerifier = codeVerifier ?? _createCodeVerifier();
+
+  /// Returns the URL to which the resource owner should be redirected to
+  /// authorize this client.
+  ///
+  /// The resource owner will then be redirected to [redirect], which should
+  /// point to a server controlled by the client. This redirect will have
+  /// additional query parameters that should be passed to
+  /// [handleAuthorizationResponse].
+  ///
+  /// The specific permissions being requested from the authorization server may
+  /// be specified via [scopes]. The scope strings are specific to the
+  /// authorization server and may be found in its documentation. Note that you
+  /// may not be granted access to every scope you request; you may check the
+  /// [Credentials.scopes] field of [Client.credentials] to see which scopes you
+  /// were granted.
+  ///
+  /// An opaque [state] string may also be passed that will be present in the
+  /// query parameters provided to the redirect URL.
+  ///
+  /// It is a [StateError] to call this more than once.
+  Uri getAuthorizationUrl(Uri redirect,
+      {Iterable<String>? scopes, String? state}) {
+    if (_state != _State.initial) {
+      throw StateError('The authorization URL has already been generated.');
+    }
+    _state = _State.awaitingResponse;
+
+    var scopeList = scopes?.toList() ?? <String>[];
+    var codeChallenge = base64Url
+        .encode(sha256.convert(ascii.encode(_codeVerifier)).bytes)
+        .replaceAll('=', '');
+
+    _redirectEndpoint = redirect;
+    _scopes = scopeList;
+    _stateString = state;
+    var parameters = {
+      'response_type': 'code',
+      'client_id': identifier,
+      'redirect_uri': redirect.toString(),
+      'code_challenge': codeChallenge,
+      'code_challenge_method': 'S256'
+    };
+
+    if (state != null) parameters['state'] = state;
+    if (scopeList.isNotEmpty) parameters['scope'] = scopeList.join(_delimiter);
+
+    return addQueryParameters(authorizationEndpoint, parameters);
+  }
+
+  /// Processes the query parameters added to a redirect from the authorization
+  /// server.
+  ///
+  /// Note that this "response" is not an HTTP response, but rather the data
+  /// passed to a server controlled by the client as query parameters on the
+  /// redirect URL.
+  ///
+  /// It is a [StateError] to call this more than once, to call it before
+  /// [getAuthorizationUrl] is called, or to call it after
+  /// [handleAuthorizationCode] is called.
+  ///
+  /// Throws [FormatException] if [parameters] is invalid according to the
+  /// OAuth2 spec or if the authorization server otherwise provides invalid
+  /// responses. If `state` was passed to [getAuthorizationUrl], this will throw
+  /// a [FormatException] if the `state` parameter doesn't match the original
+  /// value.
+  ///
+  /// Throws [AuthorizationException] if the authorization fails.
+  Future<Client> handleAuthorizationResponse(
+      Map<String, String> parameters) async {
+    if (_state == _State.initial) {
+      throw StateError('The authorization URL has not yet been generated.');
+    } else if (_state == _State.finished) {
+      throw StateError('The authorization code has already been received.');
+    }
+    _state = _State.finished;
+
+    if (_stateString != null) {
+      if (!parameters.containsKey('state')) {
+        throw FormatException('Invalid OAuth response for '
+            '"$authorizationEndpoint": parameter "state" expected to be '
+            '"$_stateString", was missing.');
+      } else if (parameters['state'] != _stateString) {
+        throw FormatException('Invalid OAuth response for '
+            '"$authorizationEndpoint": parameter "state" expected to be '
+            '"$_stateString", was "${parameters['state']}".');
+      }
+    }
+
+    if (parameters.containsKey('error')) {
+      var description = parameters['error_description'];
+      var uriString = parameters['error_uri'];
+      var uri = uriString == null ? null : Uri.parse(uriString);
+      throw AuthorizationException(parameters['error']!, description, uri);
+    } else if (!parameters.containsKey('code')) {
+      throw FormatException('Invalid OAuth response for '
+          '"$authorizationEndpoint": did not contain required parameter '
+          '"code".');
+    }
+
+    return _handleAuthorizationCode(parameters['code']);
+  }
+
+  /// Processes an authorization code directly.
+  ///
+  /// Usually [handleAuthorizationResponse] is preferable to this method, since
+  /// it validates all of the query parameters. However, some authorization
+  /// servers allow the user to copy and paste an authorization code into a
+  /// command-line application, in which case this method must be used.
+  ///
+  /// It is a [StateError] to call this more than once, to call it before
+  /// [getAuthorizationUrl] is called, or to call it after
+  /// [handleAuthorizationCode] is called.
+  ///
+  /// Throws [FormatException] if the authorization server provides invalid
+  /// responses while retrieving credentials.
+  ///
+  /// Throws [AuthorizationException] if the authorization fails.
+  Future<Client> handleAuthorizationCode(String authorizationCode) async {
+    if (_state == _State.initial) {
+      throw StateError('The authorization URL has not yet been generated.');
+    } else if (_state == _State.finished) {
+      throw StateError('The authorization code has already been received.');
+    }
+    _state = _State.finished;
+
+    return _handleAuthorizationCode(authorizationCode);
+  }
+
+  /// This works just like [handleAuthorizationCode], except it doesn't validate
+  /// the state beforehand.
+  Future<Client> _handleAuthorizationCode(String? authorizationCode) async {
+    var startTime = DateTime.now();
+
+    var headers = <String, String>{};
+
+    var body = {
+      'grant_type': 'authorization_code',
+      'code': authorizationCode,
+      'redirect_uri': _redirectEndpoint.toString(),
+      'code_verifier': _codeVerifier
+    };
+
+    var secret = this.secret;
+    if (_basicAuth && secret != null) {
+      headers['Authorization'] = basicAuthHeader(identifier, secret);
+    } else {
+      // The ID is required for this request any time basic auth isn't being
+      // used, even if there's no actual client authentication to be done.
+      body['client_id'] = identifier;
+      if (secret != null) body['client_secret'] = secret;
+    }
+
+    var response =
+        await _httpClient!.post(tokenEndpoint, headers: headers, body: body);
+
+    var credentials = handleAccessTokenResponse(
+        response, tokenEndpoint, startTime, _scopes, _delimiter,
+        getParameters: _getParameters);
+    return Client(credentials,
+        identifier: identifier,
+        secret: secret,
+        basicAuth: _basicAuth,
+        httpClient: _httpClient,
+        onCredentialsRefreshed: _onCredentialsRefreshed);
+  }
+
+  // Randomly generate a 128 character string to be used as the PKCE code
+  // verifier.
+  static String _createCodeVerifier() => List.generate(
+        128,
+        (i) => _charset[Random.secure().nextInt(_charset.length)],
+      ).join();
+
+  /// Closes the grant and frees its resources.
+  ///
+  /// This will close the underlying HTTP client, which is shared by the
+  /// [Client] created by this grant, so it's not safe to close the grant and
+  /// continue using the client.
+  void close() {
+    _httpClient?.close();
+    _httpClient = null;
+  }
+}
+
+/// States that [AuthorizationCodeGrant] can be in.
+class _State {
+  /// [AuthorizationCodeGrant.getAuthorizationUrl] has not yet been called for
+  /// this grant.
+  static const initial = _State('initial');
+
+  // [AuthorizationCodeGrant.getAuthorizationUrl] has been called but neither
+  // [AuthorizationCodeGrant.handleAuthorizationResponse] nor
+  // [AuthorizationCodeGrant.handleAuthorizationCode] has been called.
+  static const awaitingResponse = _State('awaiting response');
+
+  // [AuthorizationCodeGrant.getAuthorizationUrl] and either
+  // [AuthorizationCodeGrant.handleAuthorizationResponse] or
+  // [AuthorizationCodeGrant.handleAuthorizationCode] have been called.
+  static const finished = _State('finished');
+
+  final String _name;
+
+  const _State(this._name);
+
+  @override
+  String toString() => _name;
+}
diff --git a/pkgs/oauth2/lib/src/authorization_exception.dart b/pkgs/oauth2/lib/src/authorization_exception.dart
new file mode 100644
index 0000000..14a5a3c
--- /dev/null
+++ b/pkgs/oauth2/lib/src/authorization_exception.dart
@@ -0,0 +1,39 @@
+// Copyright (c) 2012, 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.
+
+/// An exception raised when OAuth2 authorization fails.
+class AuthorizationException implements Exception {
+  /// The name of the error.
+  ///
+  /// Possible names are enumerated in [the spec][].
+  ///
+  /// [the spec]: http://tools.ietf.org/html/draft-ietf-oauth-v2-31#section-5.2
+  final String error;
+
+  /// The description of the error, provided by the server.
+  ///
+  /// May be `null` if the server provided no description.
+  final String? description;
+
+  /// A URL for a page that describes the error in more detail, provided by the
+  /// server.
+  ///
+  /// May be `null` if the server provided no URL.
+  final Uri? uri;
+
+  /// Creates an AuthorizationException.
+  AuthorizationException(this.error, this.description, this.uri);
+
+  /// Provides a string description of the AuthorizationException.
+  @override
+  String toString() {
+    var header = 'OAuth authorization error ($error)';
+    if (description != null) {
+      header = '$header: $description';
+    } else if (uri != null) {
+      header = '$header: $uri';
+    }
+    return '$header.';
+  }
+}
diff --git a/pkgs/oauth2/lib/src/client.dart b/pkgs/oauth2/lib/src/client.dart
new file mode 100644
index 0000000..1dd2282
--- /dev/null
+++ b/pkgs/oauth2/lib/src/client.dart
@@ -0,0 +1,187 @@
+// Copyright (c) 2012, 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.
+
+import 'dart:async';
+
+import 'package:collection/collection.dart';
+import 'package:http/http.dart' as http;
+import 'package:http_parser/http_parser.dart';
+
+import 'authorization_exception.dart';
+import 'credentials.dart';
+import 'expiration_exception.dart';
+
+/// An OAuth2 client.
+///
+/// This acts as a drop-in replacement for an [http.Client], while sending
+/// OAuth2 authorization credentials along with each request.
+///
+/// The client also automatically refreshes its credentials if possible. When it
+/// makes a request, if its credentials are expired, it will first refresh them.
+/// This means that any request may throw an [AuthorizationException] if the
+/// refresh is not authorized for some reason, a [FormatException] if the
+/// authorization server provides ill-formatted responses, or an
+/// [ExpirationException] if the credentials are expired and can't be refreshed.
+///
+/// The client will also throw an [AuthorizationException] if the resource
+/// server returns a 401 response with a WWW-Authenticate header indicating that
+/// the current credentials are invalid.
+///
+/// If you already have a set of [Credentials], you can construct a [Client]
+/// directly. However, in order to first obtain the credentials, you must
+/// authorize. At the time of writing, the only authorization method this
+/// library supports is [AuthorizationCodeGrant].
+class Client extends http.BaseClient {
+  /// The client identifier for this client.
+  ///
+  /// The authorization server will issue each client a separate client
+  /// identifier and secret, which allows the server to tell which client is
+  /// accessing it. Some servers may also have an anonymous identifier/secret
+  /// pair that any client may use.
+  ///
+  /// This is usually global to the program using this library.
+  final String? identifier;
+
+  /// The client secret for this client.
+  ///
+  /// The authorization server will issue each client a separate client
+  /// identifier and secret, which allows the server to tell which client is
+  /// accessing it. Some servers may also have an anonymous identifier/secret
+  /// pair that any client may use.
+  ///
+  /// This is usually global to the program using this library.
+  ///
+  /// Note that clients whose source code or binary executable is readily
+  /// available may not be able to make sure the client secret is kept a secret.
+  /// This is fine; OAuth2 servers generally won't rely on knowing with
+  /// certainty that a client is who it claims to be.
+  final String? secret;
+
+  /// The credentials this client uses to prove to the resource server that it's
+  /// authorized.
+  ///
+  /// This may change from request to request as the credentials expire and the
+  /// client refreshes them automatically.
+  Credentials get credentials => _credentials;
+  Credentials _credentials;
+
+  /// Callback to be invoked whenever the credentials refreshed.
+  final CredentialsRefreshedCallback? _onCredentialsRefreshed;
+
+  /// Whether to use HTTP Basic authentication for authorizing the client.
+  final bool _basicAuth;
+
+  /// The underlying HTTP client.
+  http.Client? _httpClient;
+
+  /// Creates a new client from a pre-existing set of credentials.
+  ///
+  /// When authorizing a client for the first time, you should use
+  /// [AuthorizationCodeGrant] or [resourceOwnerPasswordGrant] instead of
+  /// constructing a [Client] directly.
+  ///
+  /// [httpClient] is the underlying client that this forwards requests to after
+  /// adding authorization credentials to them.
+  ///
+  /// Throws an [ArgumentError] if [secret] is passed without [identifier].
+  Client(this._credentials,
+      {this.identifier,
+      this.secret,
+      CredentialsRefreshedCallback? onCredentialsRefreshed,
+      bool basicAuth = true,
+      http.Client? httpClient})
+      : _basicAuth = basicAuth,
+        _onCredentialsRefreshed = onCredentialsRefreshed,
+        _httpClient = httpClient ?? http.Client() {
+    if (identifier == null && secret != null) {
+      throw ArgumentError('secret may not be passed without identifier.');
+    }
+  }
+
+  /// Sends an HTTP request with OAuth2 authorization credentials attached.
+  ///
+  /// This will also automatically refresh this client's [Credentials] before
+  /// sending the request if necessary.
+  @override
+  Future<http.StreamedResponse> send(http.BaseRequest request) async {
+    if (credentials.isExpired) {
+      if (!credentials.canRefresh) throw ExpirationException(credentials);
+      await refreshCredentials();
+    }
+
+    request.headers['authorization'] = 'Bearer ${credentials.accessToken}';
+    var response = await _httpClient!.send(request);
+
+    if (response.statusCode != 401) return response;
+    if (!response.headers.containsKey('www-authenticate')) return response;
+
+    List<AuthenticationChallenge> challenges;
+    try {
+      challenges = AuthenticationChallenge.parseHeader(
+          response.headers['www-authenticate']!);
+    } on FormatException {
+      return response;
+    }
+
+    var challenge = challenges
+        .firstWhereOrNull((challenge) => challenge.scheme == 'bearer');
+    if (challenge == null) return response;
+
+    var params = challenge.parameters;
+    if (!params.containsKey('error')) return response;
+
+    throw AuthorizationException(params['error']!, params['error_description'],
+        params['error_uri'] == null ? null : Uri.parse(params['error_uri']!));
+  }
+
+  /// A [Future] used to track whether [refreshCredentials] is running.
+  Future<Credentials>? _refreshingFuture;
+
+  /// Explicitly refreshes this client's credentials. Returns this client.
+  ///
+  /// This will throw a [StateError] if the [Credentials] can't be refreshed, an
+  /// [AuthorizationException] if refreshing the credentials fails, or a
+  /// [FormatException] if the authorization server returns invalid responses.
+  ///
+  /// You may request different scopes than the default by passing in
+  /// [newScopes]. These must be a subset of the scopes in the
+  /// [Credentials.scopes] field of [Client.credentials].
+  Future<Client> refreshCredentials([List<String>? newScopes]) async {
+    if (!credentials.canRefresh) {
+      var prefix = 'OAuth credentials';
+      if (credentials.isExpired) prefix = '$prefix have expired and';
+      throw StateError("$prefix can't be refreshed.");
+    }
+
+    // To make sure that only one refresh happens when credentials are expired
+    // we track it using the [_refreshingFuture]. And also make sure that the
+    // _onCredentialsRefreshed callback is only called once.
+    if (_refreshingFuture == null) {
+      try {
+        _refreshingFuture = credentials.refresh(
+          identifier: identifier,
+          secret: secret,
+          newScopes: newScopes,
+          basicAuth: _basicAuth,
+          httpClient: _httpClient,
+        );
+        _credentials = await _refreshingFuture!;
+        _onCredentialsRefreshed?.call(_credentials);
+      } finally {
+        _refreshingFuture = null;
+      }
+    } else {
+      await _refreshingFuture;
+    }
+
+    return this;
+  }
+
+  /// Closes this client and its underlying HTTP client.
+  @override
+  void close() {
+    _httpClient?.close();
+    _httpClient = null;
+  }
+}
diff --git a/pkgs/oauth2/lib/src/client_credentials_grant.dart b/pkgs/oauth2/lib/src/client_credentials_grant.dart
new file mode 100644
index 0000000..045d1a0
--- /dev/null
+++ b/pkgs/oauth2/lib/src/client_credentials_grant.dart
@@ -0,0 +1,79 @@
+// Copyright (c) 2012, 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.
+
+import 'dart:async';
+
+import 'package:http/http.dart' as http;
+import 'package:http_parser/http_parser.dart';
+
+import 'client.dart';
+import 'handle_access_token_response.dart';
+import 'utils.dart';
+
+/// Obtains credentials using a [client credentials grant](https://tools.ietf.org/html/rfc6749#section-1.3.4).
+///
+/// This mode of authorization uses the client's [identifier] and [secret]
+/// to obtain an authorization token from the authorization server, instead
+/// of sending a user through a dedicated flow.
+///
+/// The client [identifier] and [secret] are required, and are
+/// used to identify and authenticate your specific OAuth2 client. These are
+/// usually global to the program using this library.
+///
+/// The specific permissions being requested from the authorization server may
+/// be specified via [scopes]. The scope strings are specific to the
+/// authorization server and may be found in its documentation. Note that you
+/// may not be granted access to every scope you request; you may check the
+/// [Credentials.scopes] field of [Client.credentials] to see which scopes you
+/// were granted.
+///
+/// The scope strings will be separated by the provided [delimiter]. This
+/// defaults to `" "`, the OAuth2 standard, but some APIs (such as Facebook's)
+/// use non-standard delimiters.
+///
+/// By default, this follows the OAuth2 spec and requires the server's responses
+/// to be in JSON format. However, some servers return non-standard response
+/// formats, which can be parsed using the [getParameters] function.
+///
+/// This function is passed the `Content-Type` header of the response as well as
+/// its body as a UTF-8-decoded string. It should return a map in the same
+/// format as the [standard JSON response](https://tools.ietf.org/html/rfc6749#section-5.1)
+Future<Client> clientCredentialsGrant(
+    Uri authorizationEndpoint, String? identifier, String? secret,
+    {Iterable<String>? scopes,
+    bool basicAuth = true,
+    http.Client? httpClient,
+    String? delimiter,
+    Map<String, dynamic> Function(MediaType? contentType, String body)?
+        getParameters}) async {
+  delimiter ??= ' ';
+  var startTime = DateTime.now();
+
+  var body = {'grant_type': 'client_credentials'};
+
+  var headers = <String, String>{};
+
+  if (identifier != null) {
+    if (basicAuth) {
+      headers['Authorization'] = basicAuthHeader(identifier, secret!);
+    } else {
+      body['client_id'] = identifier;
+      if (secret != null) body['client_secret'] = secret;
+    }
+  }
+
+  if (scopes != null && scopes.isNotEmpty) {
+    body['scope'] = scopes.join(delimiter);
+  }
+
+  httpClient ??= http.Client();
+  var response = await httpClient.post(authorizationEndpoint,
+      headers: headers, body: body);
+
+  var credentials = handleAccessTokenResponse(response, authorizationEndpoint,
+      startTime, scopes?.toList() ?? [], delimiter,
+      getParameters: getParameters);
+  return Client(credentials,
+      identifier: identifier, secret: secret, httpClient: httpClient);
+}
diff --git a/pkgs/oauth2/lib/src/credentials.dart b/pkgs/oauth2/lib/src/credentials.dart
new file mode 100644
index 0000000..088b482
--- /dev/null
+++ b/pkgs/oauth2/lib/src/credentials.dart
@@ -0,0 +1,267 @@
+// Copyright (c) 2012, 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.
+
+import 'dart:async';
+import 'dart:collection';
+import 'dart:convert';
+
+import 'package:http/http.dart' as http;
+import 'package:http_parser/http_parser.dart';
+
+import 'handle_access_token_response.dart';
+import 'parameters.dart';
+import 'utils.dart';
+
+/// Type of the callback when credentials are refreshed.
+typedef CredentialsRefreshedCallback = void Function(Credentials);
+
+/// Credentials that prove that a client is allowed to access a resource on the
+/// resource owner's behalf.
+///
+/// These credentials are long-lasting and can be safely persisted across
+/// multiple runs of the program.
+///
+/// Many authorization servers will attach an expiration date to a set of
+/// credentials, along with a token that can be used to refresh the credentials
+/// once they've expired. The [http.Client] will automatically refresh its
+/// credentials when necessary. It's also possible to explicitly refresh them
+/// via [http.Client.refreshCredentials] or [Credentials.refresh].
+///
+/// Note that a given set of credentials can only be refreshed once, so be sure
+/// to save the refreshed credentials for future use.
+class Credentials {
+  /// A [String] used to separate scopes; defaults to `" "`.
+  String _delimiter;
+
+  /// The token that is sent to the resource server to prove the authorization
+  /// of a client.
+  final String accessToken;
+
+  /// The token that is sent to the authorization server to refresh the
+  /// credentials.
+  ///
+  /// This may be `null`, indicating that the credentials can't be refreshed.
+  final String? refreshToken;
+
+  /// The token that is received from the authorization server to enable
+  /// End-Users to be Authenticated, contains Claims, represented as a
+  /// JSON Web Token (JWT).
+  ///
+  /// This may be `null`, indicating that the 'openid' scope was not
+  /// requested (or not supported).
+  ///
+  /// [spec]: https://openid.net/specs/openid-connect-core-1_0.html#IDToken
+  final String? idToken;
+
+  /// The URL of the authorization server endpoint that's used to refresh the
+  /// credentials.
+  ///
+  /// This may be `null`, indicating that the credentials can't be refreshed.
+  final Uri? tokenEndpoint;
+
+  /// The specific permissions being requested from the authorization server.
+  ///
+  /// The scope strings are specific to the authorization server and may be
+  /// found in its documentation.
+  final List<String>? scopes;
+
+  /// The date at which these credentials will expire.
+  ///
+  /// This is likely to be a few seconds earlier than the server's idea of the
+  /// expiration date.
+  final DateTime? expiration;
+
+  /// The function used to parse parameters from a host's response.
+  final GetParameters _getParameters;
+
+  /// Whether or not these credentials have expired.
+  ///
+  /// Note that it's possible the credentials will expire shortly after this is
+  /// called. However, since the client's expiration date is kept a few seconds
+  /// earlier than the server's, there should be enough leeway to rely on this.
+  bool get isExpired {
+    var expiration = this.expiration;
+    return expiration != null && DateTime.now().isAfter(expiration);
+  }
+
+  /// Whether it's possible to refresh these credentials.
+  bool get canRefresh => refreshToken != null && tokenEndpoint != null;
+
+  /// Creates a new set of credentials.
+  ///
+  /// This class is usually not constructed directly; rather, it's accessed via
+  /// [Client.credentials] after a [Client] is created by
+  /// [AuthorizationCodeGrant]. Alternately, it may be loaded from a serialized
+  /// form via [Credentials.fromJson].
+  ///
+  /// The scope strings will be separated by the provided [delimiter]. This
+  /// defaults to `" "`, the OAuth2 standard, but some APIs (such as Facebook's)
+  /// use non-standard delimiters.
+  ///
+  /// By default, this follows the OAuth2 spec and requires the server's
+  /// responses to be in JSON format. However, some servers return non-standard
+  /// response formats, which can be parsed using the [getParameters] function.
+  ///
+  /// This function is passed the `Content-Type` header of the response as well
+  /// as its body as a UTF-8-decoded string. It should return a map in the same
+  /// format as the [standard JSON response][].
+  ///
+  /// [standard JSON response]: https://tools.ietf.org/html/rfc6749#section-5.1
+  Credentials(this.accessToken,
+      {this.refreshToken,
+      this.idToken,
+      this.tokenEndpoint,
+      Iterable<String>? scopes,
+      this.expiration,
+      String? delimiter,
+      Map<String, dynamic> Function(MediaType? mediaType, String body)?
+          getParameters})
+      : scopes = UnmodifiableListView(
+            // Explicitly type-annotate the list literal to work around
+            // sdk#24202.
+            scopes == null ? <String>[] : scopes.toList()),
+        _delimiter = delimiter ?? ' ',
+        _getParameters = getParameters ?? parseJsonParameters;
+
+  /// Loads a set of credentials from a JSON-serialized form.
+  ///
+  /// Throws a [FormatException] if the JSON is incorrectly formatted.
+  factory Credentials.fromJson(String json) {
+    void validate(bool condition, String message) {
+      if (condition) return;
+      throw FormatException('Failed to load credentials: $message.\n\n$json');
+    }
+
+    dynamic parsed;
+    try {
+      parsed = jsonDecode(json);
+    } on FormatException {
+      validate(false, 'invalid JSON');
+    }
+
+    validate(parsed is Map, 'was not a JSON map');
+
+    parsed = parsed as Map;
+    validate(parsed.containsKey('accessToken'),
+        'did not contain required field "accessToken"');
+    validate(
+      parsed['accessToken'] is String,
+      'required field "accessToken" was not a string, was '
+      '${parsed["accessToken"]}',
+    );
+
+    for (var stringField in ['refreshToken', 'idToken', 'tokenEndpoint']) {
+      var value = parsed[stringField];
+      validate(value == null || value is String,
+          'field "$stringField" was not a string, was "$value"');
+    }
+
+    var scopes = parsed['scopes'];
+    validate(scopes == null || scopes is List,
+        'field "scopes" was not a list, was "$scopes"');
+
+    var tokenEndpoint = parsed['tokenEndpoint'];
+    Uri? tokenEndpointUri;
+    if (tokenEndpoint != null) {
+      tokenEndpointUri = Uri.parse(tokenEndpoint as String);
+    }
+
+    var expiration = parsed['expiration'];
+    DateTime? expirationDateTime;
+    if (expiration != null) {
+      validate(expiration is int,
+          'field "expiration" was not an int, was "$expiration"');
+      expiration = expiration as int;
+      expirationDateTime = DateTime.fromMillisecondsSinceEpoch(expiration);
+    }
+
+    return Credentials(
+      parsed['accessToken'] as String,
+      refreshToken: parsed['refreshToken'] as String?,
+      idToken: parsed['idToken'] as String?,
+      tokenEndpoint: tokenEndpointUri,
+      scopes: (scopes as List).map((scope) => scope as String),
+      expiration: expirationDateTime,
+    );
+  }
+
+  /// Serializes a set of credentials to JSON.
+  ///
+  /// Nothing is guaranteed about the output except that it's valid JSON and
+  /// compatible with [Credentials.toJson].
+  String toJson() => jsonEncode({
+        'accessToken': accessToken,
+        'refreshToken': refreshToken,
+        'idToken': idToken,
+        'tokenEndpoint': tokenEndpoint?.toString(),
+        'scopes': scopes,
+        'expiration': expiration?.millisecondsSinceEpoch
+      });
+
+  /// Returns a new set of refreshed credentials.
+  ///
+  /// See [Client.identifier] and [Client.secret] for explanations of those
+  /// parameters.
+  ///
+  /// You may request different scopes than the default by passing in
+  /// [newScopes]. These must be a subset of [scopes].
+  ///
+  /// This throws an [ArgumentError] if [secret] is passed without [identifier],
+  /// a [StateError] if these credentials can't be refreshed, an
+  /// [AuthorizationException] if refreshing the credentials fails, or a
+  /// [FormatException] if the authorization server returns invalid responses.
+  Future<Credentials> refresh(
+      {String? identifier,
+      String? secret,
+      Iterable<String>? newScopes,
+      bool basicAuth = true,
+      http.Client? httpClient}) async {
+    var scopes = this.scopes;
+    if (newScopes != null) scopes = newScopes.toList();
+    scopes ??= [];
+    httpClient ??= http.Client();
+
+    if (identifier == null && secret != null) {
+      throw ArgumentError('secret may not be passed without identifier.');
+    }
+
+    var startTime = DateTime.now();
+    var tokenEndpoint = this.tokenEndpoint;
+    if (refreshToken == null) {
+      throw StateError("Can't refresh credentials without a refresh "
+          'token.');
+    } else if (tokenEndpoint == null) {
+      throw StateError("Can't refresh credentials without a token "
+          'endpoint.');
+    }
+
+    var headers = <String, String>{};
+
+    var body = {'grant_type': 'refresh_token', 'refresh_token': refreshToken};
+    if (scopes.isNotEmpty) body['scope'] = scopes.join(_delimiter);
+
+    if (basicAuth && secret != null) {
+      headers['Authorization'] = basicAuthHeader(identifier!, secret);
+    } else {
+      if (identifier != null) body['client_id'] = identifier;
+      if (secret != null) body['client_secret'] = secret;
+    }
+
+    var response =
+        await httpClient.post(tokenEndpoint, headers: headers, body: body);
+    var credentials = handleAccessTokenResponse(
+        response, tokenEndpoint, startTime, scopes, _delimiter,
+        getParameters: _getParameters);
+
+    // The authorization server may issue a new refresh token. If it doesn't,
+    // we should re-use the one we already have.
+    if (credentials.refreshToken != null) return credentials;
+    return Credentials(credentials.accessToken,
+        refreshToken: refreshToken,
+        idToken: credentials.idToken,
+        tokenEndpoint: credentials.tokenEndpoint,
+        scopes: credentials.scopes,
+        expiration: credentials.expiration);
+  }
+}
diff --git a/pkgs/oauth2/lib/src/expiration_exception.dart b/pkgs/oauth2/lib/src/expiration_exception.dart
new file mode 100644
index 0000000..d72fcf6
--- /dev/null
+++ b/pkgs/oauth2/lib/src/expiration_exception.dart
@@ -0,0 +1,19 @@
+// Copyright (c) 2012, 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.
+
+import 'credentials.dart';
+
+/// An exception raised when attempting to use expired OAuth2 credentials.
+class ExpirationException implements Exception {
+  /// The expired credentials.
+  final Credentials credentials;
+
+  /// Creates an ExpirationException.
+  ExpirationException(this.credentials);
+
+  /// Provides a string description of the ExpirationException.
+  @override
+  String toString() =>
+      "OAuth2 credentials have expired and can't be refreshed.";
+}
diff --git a/pkgs/oauth2/lib/src/handle_access_token_response.dart b/pkgs/oauth2/lib/src/handle_access_token_response.dart
new file mode 100644
index 0000000..f318e3b
--- /dev/null
+++ b/pkgs/oauth2/lib/src/handle_access_token_response.dart
@@ -0,0 +1,158 @@
+// Copyright (c) 2012, 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.
+
+import 'package:http/http.dart' as http;
+import 'package:http_parser/http_parser.dart';
+
+import 'authorization_exception.dart';
+import 'credentials.dart';
+import 'parameters.dart';
+
+/// The amount of time to add as a "grace period" for credential expiration.
+///
+/// This allows credential expiration checks to remain valid for a reasonable
+/// amount of time.
+const _expirationGrace = Duration(seconds: 10);
+
+/// Handles a response from the authorization server that contains an access
+/// token.
+///
+/// This response format is common across several different components of the
+/// OAuth2 flow.
+///
+/// By default, this follows the OAuth2 spec and requires the server's responses
+/// to be in JSON format. However, some servers return non-standard response
+/// formats, which can be parsed using the [getParameters] function.
+///
+/// This function is passed the `Content-Type` header of the response as well as
+/// its body as a UTF-8-decoded string. It should return a map in the same
+/// format as the [standard JSON response][].
+///
+/// [standard JSON response]: https://tools.ietf.org/html/rfc6749#section-5.1
+Credentials handleAccessTokenResponse(http.Response response, Uri tokenEndpoint,
+    DateTime startTime, List<String>? scopes, String delimiter,
+    {Map<String, dynamic> Function(MediaType? contentType, String body)?
+        getParameters}) {
+  getParameters ??= parseJsonParameters;
+
+  try {
+    if (response.statusCode != 200) {
+      _handleErrorResponse(response, tokenEndpoint, getParameters);
+    }
+
+    var contentTypeString = response.headers['content-type'];
+    if (contentTypeString == null) {
+      throw const FormatException('Missing Content-Type string.');
+    }
+
+    var parameters =
+        getParameters(MediaType.parse(contentTypeString), response.body);
+
+    for (var requiredParameter in ['access_token', 'token_type']) {
+      if (!parameters.containsKey(requiredParameter)) {
+        throw FormatException(
+            'did not contain required parameter "$requiredParameter"');
+      } else if (parameters[requiredParameter] is! String) {
+        throw FormatException(
+            'required parameter "$requiredParameter" was not a string, was '
+            '"${parameters[requiredParameter]}"');
+      }
+    }
+
+    // TODO(nweiz): support the "mac" token type
+    // (http://tools.ietf.org/html/draft-ietf-oauth-v2-http-mac-01)
+    if ((parameters['token_type'] as String).toLowerCase() != 'bearer') {
+      throw FormatException(
+          '"$tokenEndpoint": unknown token type "${parameters['token_type']}"');
+    }
+
+    var expiresIn = parameters['expires_in'];
+    if (expiresIn != null) {
+      if (expiresIn is String) {
+        try {
+          expiresIn = double.parse(expiresIn).toInt();
+        } on FormatException {
+          throw FormatException(
+            'parameter "expires_in" could not be parsed as in, was: '
+            '"$expiresIn"',
+          );
+        }
+      } else if (expiresIn is! int) {
+        throw FormatException(
+            'parameter "expires_in" was not an int, was: "$expiresIn"');
+      }
+    }
+
+    for (var name in ['refresh_token', 'id_token', 'scope']) {
+      var value = parameters[name];
+      if (value != null && value is! String) {
+        throw FormatException(
+            'parameter "$name" was not a string, was "$value"');
+      }
+    }
+
+    var scope = parameters['scope'] as String?;
+    if (scope != null) scopes = scope.split(delimiter);
+
+    var expiration = expiresIn == null
+        ? null
+        : startTime.add(Duration(seconds: expiresIn as int) - _expirationGrace);
+
+    return Credentials(
+      parameters['access_token'] as String,
+      refreshToken: parameters['refresh_token'] as String?,
+      idToken: parameters['id_token'] as String?,
+      tokenEndpoint: tokenEndpoint,
+      scopes: scopes,
+      expiration: expiration,
+    );
+  } on FormatException catch (e) {
+    throw FormatException('Invalid OAuth response for "$tokenEndpoint": '
+        '${e.message}.\n\n${response.body}');
+  }
+}
+
+/// Throws the appropriate exception for an error response from the
+/// authorization server.
+void _handleErrorResponse(
+    http.Response response, Uri tokenEndpoint, GetParameters getParameters) {
+  // OAuth2 mandates a 400 or 401 response code for access token error
+  // responses. If it's not a 400 reponse, the server is either broken or
+  // off-spec.
+  if (response.statusCode != 400 && response.statusCode != 401) {
+    var reason = '';
+    var reasonPhrase = response.reasonPhrase;
+    if (reasonPhrase != null && reasonPhrase.isNotEmpty) {
+      reason = ' $reasonPhrase';
+    }
+    throw FormatException('OAuth request for "$tokenEndpoint" failed '
+        'with status ${response.statusCode}$reason.\n\n${response.body}');
+  }
+
+  var contentTypeString = response.headers['content-type'];
+  var contentType =
+      contentTypeString == null ? null : MediaType.parse(contentTypeString);
+
+  var parameters = getParameters(contentType, response.body);
+
+  if (!parameters.containsKey('error')) {
+    throw const FormatException('did not contain required parameter "error"');
+  } else if (parameters['error'] is! String) {
+    throw FormatException('required parameter "error" was not a string, was '
+        '"${parameters["error"]}"');
+  }
+
+  for (var name in ['error_description', 'error_uri']) {
+    var value = parameters[name];
+
+    if (value != null && value is! String) {
+      throw FormatException('parameter "$name" was not a string, was "$value"');
+    }
+  }
+
+  var uriString = parameters['error_uri'] as String?;
+  var uri = uriString == null ? null : Uri.parse(uriString);
+  var description = parameters['error_description'] as String?;
+  throw AuthorizationException(parameters['error'] as String, description, uri);
+}
diff --git a/pkgs/oauth2/lib/src/parameters.dart b/pkgs/oauth2/lib/src/parameters.dart
new file mode 100644
index 0000000..ecc6559
--- /dev/null
+++ b/pkgs/oauth2/lib/src/parameters.dart
@@ -0,0 +1,33 @@
+// Copyright (c) 2018, 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.
+
+import 'dart:convert';
+
+import 'package:http_parser/http_parser.dart';
+
+/// The type of a callback that parses parameters from an HTTP response.
+typedef GetParameters = Map<String, dynamic> Function(
+    MediaType? contentType, String body);
+
+/// Parses parameters from a response with a JSON body, as per the
+/// [OAuth2 spec][].
+///
+/// [OAuth2 spec]: https://tools.ietf.org/html/rfc6749#section-5.1
+Map<String, dynamic> parseJsonParameters(MediaType? contentType, String body) {
+  // The spec requires a content-type of application/json, but some endpoints
+  // (e.g. Dropbox) serve it as text/javascript instead.
+  if (contentType == null ||
+      (contentType.mimeType != 'application/json' &&
+          contentType.mimeType != 'text/javascript')) {
+    throw FormatException(
+        'Content-Type was "$contentType", expected "application/json"');
+  }
+
+  var untypedParameters = jsonDecode(body);
+  if (untypedParameters is Map<String, dynamic>) {
+    return untypedParameters;
+  }
+
+  throw FormatException('Parameters must be a map, was "$untypedParameters"');
+}
diff --git a/pkgs/oauth2/lib/src/resource_owner_password_grant.dart b/pkgs/oauth2/lib/src/resource_owner_password_grant.dart
new file mode 100644
index 0000000..96fb503
--- /dev/null
+++ b/pkgs/oauth2/lib/src/resource_owner_password_grant.dart
@@ -0,0 +1,94 @@
+// Copyright (c) 2012, 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.
+
+import 'dart:async';
+
+import 'package:http/http.dart' as http;
+import 'package:http_parser/http_parser.dart';
+
+import 'client.dart';
+import 'credentials.dart';
+import 'handle_access_token_response.dart';
+import 'utils.dart';
+
+/// Obtains credentials using a [resource owner password grant](https://tools.ietf.org/html/rfc6749#section-1.3.3).
+///
+/// This mode of authorization uses the user's username and password to obtain
+/// an authentication token, which can then be stored. This is safer than
+/// storing the username and password directly, but it should be avoided if any
+/// other authorization method is available, since it requires the user to
+/// provide their username and password to a third party (you).
+///
+/// The client [identifier] and [secret] may be issued by the server, and are
+/// used to identify and authenticate your specific OAuth2 client. These are
+/// usually global to the program using this library.
+///
+/// The specific permissions being requested from the authorization server may
+/// be specified via [scopes]. The scope strings are specific to the
+/// authorization server and may be found in its documentation. Note that you
+/// may not be granted access to every scope you request; you may check the
+/// [Credentials.scopes] field of [Client.credentials] to see which scopes you
+/// were granted.
+///
+/// The scope strings will be separated by the provided [delimiter]. This
+/// defaults to `" "`, the OAuth2 standard, but some APIs (such as Facebook's)
+/// use non-standard delimiters.
+///
+/// By default, this follows the OAuth2 spec and requires the server's responses
+/// to be in JSON format. However, some servers return non-standard response
+/// formats, which can be parsed using the [getParameters] function.
+///
+/// This function is passed the `Content-Type` header of the response as well as
+/// its body as a UTF-8-decoded string. It should return a map in the same
+/// format as the [standard JSON response][].
+///
+/// [standard JSON response]: https://tools.ietf.org/html/rfc6749#section-5.1
+Future<Client> resourceOwnerPasswordGrant(
+    Uri authorizationEndpoint, String username, String password,
+    {String? identifier,
+    String? secret,
+    Iterable<String>? scopes,
+    bool basicAuth = true,
+    CredentialsRefreshedCallback? onCredentialsRefreshed,
+    http.Client? httpClient,
+    String? delimiter,
+    Map<String, dynamic> Function(MediaType? contentType, String body)?
+        getParameters}) async {
+  delimiter ??= ' ';
+  var startTime = DateTime.now();
+
+  var body = {
+    'grant_type': 'password',
+    'username': username,
+    'password': password
+  };
+
+  var headers = <String, String>{};
+
+  if (identifier != null) {
+    if (basicAuth) {
+      headers['Authorization'] = basicAuthHeader(identifier, secret!);
+    } else {
+      body['client_id'] = identifier;
+      if (secret != null) body['client_secret'] = secret;
+    }
+  }
+
+  if (scopes != null && scopes.isNotEmpty) {
+    body['scope'] = scopes.join(delimiter);
+  }
+
+  httpClient ??= http.Client();
+  var response = await httpClient.post(authorizationEndpoint,
+      headers: headers, body: body);
+
+  var credentials = handleAccessTokenResponse(
+      response, authorizationEndpoint, startTime, scopes?.toList(), delimiter,
+      getParameters: getParameters);
+  return Client(credentials,
+      identifier: identifier,
+      secret: secret,
+      httpClient: httpClient,
+      onCredentialsRefreshed: onCredentialsRefreshed);
+}
diff --git a/pkgs/oauth2/lib/src/utils.dart b/pkgs/oauth2/lib/src/utils.dart
new file mode 100644
index 0000000..2a22b9f
--- /dev/null
+++ b/pkgs/oauth2/lib/src/utils.dart
@@ -0,0 +1,15 @@
+// Copyright (c) 2012, 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.
+
+import 'dart:convert';
+
+/// Adds additional query parameters to [url], overwriting the original
+/// parameters if a name conflict occurs.
+Uri addQueryParameters(Uri url, Map<String, String> parameters) => url.replace(
+    queryParameters: Map.from(url.queryParameters)..addAll(parameters));
+
+String basicAuthHeader(String identifier, String secret) {
+  var userPass = '${Uri.encodeFull(identifier)}:${Uri.encodeFull(secret)}';
+  return 'Basic ${base64Encode(ascii.encode(userPass))}';
+}
diff --git a/pkgs/oauth2/pubspec.yaml b/pkgs/oauth2/pubspec.yaml
new file mode 100644
index 0000000..75ded18
--- /dev/null
+++ b/pkgs/oauth2/pubspec.yaml
@@ -0,0 +1,20 @@
+name: oauth2
+version: 2.0.4-wip
+description: >-
+  A client library for authenticating with a remote service via OAuth2 on
+  behalf of a user, and making authorized HTTP requests with the user's
+  OAuth2 credentials.
+repository: https://github.com/dart-lang/tools/tree/main/pkgs/oauth2
+  
+environment:
+  sdk: ^3.4.0
+
+dependencies:
+  collection: ^1.15.0
+  crypto: ^3.0.0
+  http: ^1.0.0
+  http_parser: ^4.0.0
+
+dev_dependencies:
+  dart_flutter_team_lints: ^3.0.0
+  test: ^1.16.0
diff --git a/pkgs/oauth2/test/authorization_code_grant_test.dart b/pkgs/oauth2/test/authorization_code_grant_test.dart
new file mode 100644
index 0000000..06e88af
--- /dev/null
+++ b/pkgs/oauth2/test/authorization_code_grant_test.dart
@@ -0,0 +1,391 @@
+// Copyright (c) 2012, 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.
+
+import 'dart:async';
+import 'dart:convert';
+
+import 'package:http/http.dart' as http;
+import 'package:oauth2/oauth2.dart' as oauth2;
+import 'package:test/test.dart';
+
+import 'utils.dart';
+
+final redirectUrl = Uri.parse('http://example.com/redirect');
+
+void main() {
+  late ExpectClient client;
+  late oauth2.AuthorizationCodeGrant grant;
+  setUp(() {
+    client = ExpectClient();
+    grant = oauth2.AuthorizationCodeGrant(
+        'identifier',
+        Uri.parse('https://example.com/authorization'),
+        Uri.parse('https://example.com/token'),
+        secret: 'secret',
+        httpClient: client);
+  });
+
+  group('.getAuthorizationUrl', () {
+    test('builds the correct URL', () {
+      expect(
+          grant.getAuthorizationUrl(redirectUrl).toString(),
+          allOf([
+            startsWith('https://example.com/authorization?response_type=code'),
+            contains('&client_id=identifier'),
+            contains('&redirect_uri=http%3A%2F%2Fexample.com%2Fredirect'),
+            matches(r'&code_challenge=[A-Za-z0-9\+\/\-\_]{43}'),
+            contains('&code_challenge_method=S256')
+          ]));
+    });
+
+    test('builds the correct URL with scopes', () {
+      var authorizationUrl = grant
+          .getAuthorizationUrl(redirectUrl, scopes: ['scope', 'other/scope']);
+      expect(
+          authorizationUrl.toString(),
+          allOf([
+            startsWith('https://example.com/authorization?response_type=code'),
+            contains('&client_id=identifier'),
+            contains('&redirect_uri=http%3A%2F%2Fexample.com%2Fredirect'),
+            matches(r'&code_challenge=[A-Za-z0-9\+\/\-\_]{43}'),
+            contains('&code_challenge_method=S256'),
+            contains('&scope=scope+other%2Fscope')
+          ]));
+    });
+
+    test('builds the correct URL with passed in code verifier', () {
+      const codeVerifier =
+          'it1shei7LooGoh3looxaa4sieveijeib2zecauz2oo8aebae5aehee0ahPirewoh'
+          '5Bo6Maexooqui3uL2si6ahweiv7shauc1shahxooveoB3aeyahsaiye0Egh3raix';
+      const expectedCodeChallenge =
+          'EjfFMv8TFPd3GuNxAn5COhlWBGpfZLimHett7ypJfJ0';
+      var grant = oauth2.AuthorizationCodeGrant(
+          'identifier',
+          Uri.parse('https://example.com/authorization'),
+          Uri.parse('https://example.com/token'),
+          secret: 'secret',
+          httpClient: client,
+          codeVerifier: codeVerifier);
+      expect(
+          grant.getAuthorizationUrl(redirectUrl).toString(),
+          allOf([
+            startsWith('https://example.com/authorization?response_type=code'),
+            contains('&client_id=identifier'),
+            contains('&redirect_uri=http%3A%2F%2Fexample.com%2Fredirect'),
+            contains('&code_challenge=$expectedCodeChallenge'),
+            contains('&code_challenge_method=S256')
+          ]));
+    });
+
+    test('separates scopes with the correct delimiter', () {
+      var grant = oauth2.AuthorizationCodeGrant(
+          'identifier',
+          Uri.parse('https://example.com/authorization'),
+          Uri.parse('https://example.com/token'),
+          secret: 'secret',
+          httpClient: client,
+          delimiter: '_');
+      var authorizationUrl = grant
+          .getAuthorizationUrl(redirectUrl, scopes: ['scope', 'other/scope']);
+      expect(
+          authorizationUrl.toString(),
+          allOf([
+            startsWith('https://example.com/authorization?response_type=code'),
+            contains('&client_id=identifier'),
+            contains('&redirect_uri=http%3A%2F%2Fexample.com%2Fredirect'),
+            matches(r'&code_challenge=[A-Za-z0-9\+\/\-\_]{43}'),
+            contains('&code_challenge_method=S256'),
+            contains('&scope=scope_other%2Fscope')
+          ]));
+    });
+
+    test('builds the correct URL with state', () {
+      var authorizationUrl =
+          grant.getAuthorizationUrl(redirectUrl, state: 'state');
+      expect(
+          authorizationUrl.toString(),
+          allOf([
+            startsWith('https://example.com/authorization?response_type=code'),
+            contains('&client_id=identifier'),
+            contains('&redirect_uri=http%3A%2F%2Fexample.com%2Fredirect'),
+            matches(r'&code_challenge=[A-Za-z0-9\+\/\-\_]{43}'),
+            contains('&code_challenge_method=S256'),
+            contains('&state=state')
+          ]));
+    });
+
+    test('merges with existing query parameters', () {
+      grant = oauth2.AuthorizationCodeGrant(
+          'identifier',
+          Uri.parse('https://example.com/authorization?query=value'),
+          Uri.parse('https://example.com/token'),
+          secret: 'secret',
+          httpClient: client);
+
+      var authorizationUrl = grant.getAuthorizationUrl(redirectUrl);
+      expect(
+          authorizationUrl.toString(),
+          allOf([
+            startsWith('https://example.com/authorization?query=value'),
+            contains('&response_type=code'),
+            contains('&client_id=identifier'),
+            contains('&redirect_uri=http%3A%2F%2Fexample.com%2Fredirect'),
+            matches(r'&code_challenge=[A-Za-z0-9\+\/\-\_]{43}'),
+            contains('&code_challenge_method=S256'),
+          ]));
+    });
+
+    test("can't be called twice", () {
+      grant.getAuthorizationUrl(redirectUrl);
+      expect(() => grant.getAuthorizationUrl(redirectUrl), throwsStateError);
+    });
+  });
+
+  group('.handleAuthorizationResponse', () {
+    test("can't be called before .getAuthorizationUrl", () {
+      expect(grant.handleAuthorizationResponse({}), throwsStateError);
+    });
+
+    test("can't be called twice", () {
+      grant.getAuthorizationUrl(redirectUrl);
+      expect(grant.handleAuthorizationResponse({'code': 'auth code'}),
+          throwsFormatException);
+      expect(grant.handleAuthorizationResponse({'code': 'auth code'}),
+          throwsStateError);
+    });
+
+    test('must have a state parameter if the authorization URL did', () {
+      grant.getAuthorizationUrl(redirectUrl, state: 'state');
+      expect(grant.handleAuthorizationResponse({'code': 'auth code'}),
+          throwsFormatException);
+    });
+
+    test('must have the same state parameter the authorization URL did', () {
+      grant.getAuthorizationUrl(redirectUrl, state: 'state');
+      expect(
+          grant.handleAuthorizationResponse(
+              {'code': 'auth code', 'state': 'other state'}),
+          throwsFormatException);
+    });
+
+    test('must have a code parameter', () {
+      grant.getAuthorizationUrl(redirectUrl);
+      expect(grant.handleAuthorizationResponse({}), throwsFormatException);
+    });
+
+    test('with an error parameter throws an AuthorizationException', () {
+      grant.getAuthorizationUrl(redirectUrl);
+      expect(grant.handleAuthorizationResponse({'error': 'invalid_request'}),
+          throwsA(isA<oauth2.AuthorizationException>()));
+    });
+
+    test('sends an authorization code request', () {
+      grant.getAuthorizationUrl(redirectUrl);
+      client.expectRequest((request) {
+        expect(request.method, equals('POST'));
+        expect(request.url.toString(), equals(grant.tokenEndpoint.toString()));
+        expect(
+            request.bodyFields,
+            allOf([
+              containsPair('grant_type', 'authorization_code'),
+              containsPair('code', 'auth code'),
+              containsPair('redirect_uri', redirectUrl.toString()),
+              containsPair(
+                  'code_verifier', matches(r'[A-Za-z0-9\-\.\_\~]{128}'))
+            ]));
+        expect(request.headers,
+            containsPair('Authorization', 'Basic aWRlbnRpZmllcjpzZWNyZXQ='));
+
+        return Future.value(http.Response(
+            jsonEncode({
+              'access_token': 'access token',
+              'token_type': 'bearer',
+            }),
+            200,
+            headers: {'content-type': 'application/json'}));
+      });
+
+      expect(
+          grant.handleAuthorizationResponse({'code': 'auth code'}).then(
+              (client) => client.credentials.accessToken),
+          completion(equals('access token')));
+    });
+  });
+
+  group('.handleAuthorizationCode', () {
+    test("can't be called before .getAuthorizationUrl", () {
+      expect(grant.handleAuthorizationCode('auth code'), throwsStateError);
+    });
+
+    test("can't be called twice", () {
+      grant.getAuthorizationUrl(redirectUrl);
+      expect(grant.handleAuthorizationCode('auth code'), throwsFormatException);
+      expect(grant.handleAuthorizationCode('auth code'), throwsStateError);
+    });
+
+    test('sends an authorization code request', () async {
+      grant.getAuthorizationUrl(redirectUrl);
+      client.expectRequest((request) {
+        expect(request.method, equals('POST'));
+        expect(request.url.toString(), equals(grant.tokenEndpoint.toString()));
+        expect(
+            request.bodyFields,
+            allOf([
+              containsPair('grant_type', 'authorization_code'),
+              containsPair('code', 'auth code'),
+              containsPair('redirect_uri', redirectUrl.toString()),
+              containsPair(
+                  'code_verifier', matches(r'[A-Za-z0-9\-\.\_\~]{128}'))
+            ]));
+        expect(request.headers,
+            containsPair('Authorization', 'Basic aWRlbnRpZmllcjpzZWNyZXQ='));
+
+        return Future.value(http.Response(
+            jsonEncode({
+              'access_token': 'access token',
+              'token_type': 'bearer',
+            }),
+            200,
+            headers: {'content-type': 'application/json'}));
+      });
+
+      expect(
+          await grant.handleAuthorizationCode('auth code'),
+          isA<oauth2.Client>().having((c) => c.credentials.accessToken,
+              'credentials.accessToken', 'access token'));
+    });
+  });
+
+  group('with basicAuth: false', () {
+    setUp(() {
+      client = ExpectClient();
+      grant = oauth2.AuthorizationCodeGrant(
+          'identifier',
+          Uri.parse('https://example.com/authorization'),
+          Uri.parse('https://example.com/token'),
+          secret: 'secret',
+          basicAuth: false,
+          httpClient: client);
+    });
+
+    test('.handleAuthorizationResponse sends an authorization code request',
+        () {
+      grant.getAuthorizationUrl(redirectUrl);
+      client.expectRequest((request) {
+        expect(request.method, equals('POST'));
+        expect(request.url.toString(), equals(grant.tokenEndpoint.toString()));
+        expect(
+            request.bodyFields,
+            allOf([
+              containsPair('grant_type', 'authorization_code'),
+              containsPair('code', 'auth code'),
+              containsPair('redirect_uri', redirectUrl.toString()),
+              containsPair(
+                  'code_verifier', matches(r'[A-Za-z0-9\-\.\_\~]{128}')),
+              containsPair('client_id', 'identifier'),
+              containsPair('client_secret', 'secret')
+            ]));
+
+        return Future.value(http.Response(
+            jsonEncode({
+              'access_token': 'access token',
+              'token_type': 'bearer',
+            }),
+            200,
+            headers: {'content-type': 'application/json'}));
+      });
+
+      expect(
+          grant.handleAuthorizationResponse({'code': 'auth code'}).then(
+              (client) => client.credentials.accessToken),
+          completion(equals('access token')));
+    });
+
+    test('.handleAuthorizationCode sends an authorization code request',
+        () async {
+      grant.getAuthorizationUrl(redirectUrl);
+      client.expectRequest((request) {
+        expect(request.method, equals('POST'));
+        expect(request.url.toString(), equals(grant.tokenEndpoint.toString()));
+        expect(
+            request.bodyFields,
+            allOf([
+              containsPair('grant_type', 'authorization_code'),
+              containsPair('code', 'auth code'),
+              containsPair('redirect_uri', redirectUrl.toString()),
+              containsPair(
+                  'code_verifier', matches(r'[A-Za-z0-9\-\.\_\~]{128}')),
+              containsPair('client_id', 'identifier'),
+              containsPair('client_secret', 'secret')
+            ]));
+
+        return Future.value(http.Response(
+            jsonEncode({
+              'access_token': 'access token',
+              'token_type': 'bearer',
+            }),
+            200,
+            headers: {'content-type': 'application/json'}));
+      });
+
+      expect(
+          await grant.handleAuthorizationCode('auth code'),
+          isA<oauth2.Client>().having((c) => c.credentials.accessToken,
+              'credentials.accessToken', 'access token'));
+    });
+  });
+
+  group('onCredentialsRefreshed', () {
+    test('is correctly propagated', () async {
+      var isCallbackInvoked = false;
+      var grant = oauth2.AuthorizationCodeGrant(
+          'identifier',
+          Uri.parse('https://example.com/authorization'),
+          Uri.parse('https://example.com/token'),
+          secret: 'secret',
+          basicAuth: false,
+          httpClient: client, onCredentialsRefreshed: (credentials) {
+        isCallbackInvoked = true;
+      });
+
+      grant.getAuthorizationUrl(redirectUrl);
+      client.expectRequest(
+        (request) => Future.value(
+          http.Response(
+            jsonEncode({
+              'access_token': 'access token',
+              'token_type': 'bearer',
+              'expires_in': -3600,
+              'refresh_token': 'refresh token',
+            }),
+            200,
+            headers: {'content-type': 'application/json'},
+          ),
+        ),
+      );
+
+      var oauth2Client = await grant.handleAuthorizationCode('auth code');
+
+      client.expectRequest(
+        (request) => Future.value(
+          http.Response(
+            jsonEncode({
+              'access_token': 'new access token',
+              'token_type': 'bearer',
+            }),
+            200,
+            headers: {'content-type': 'application/json'},
+          ),
+        ),
+      );
+
+      client.expectRequest(
+          (request) => Future.value(http.Response('good job', 200)));
+
+      await oauth2Client.read(Uri.parse('http://example.com/resource'));
+
+      expect(isCallbackInvoked, equals(true));
+    });
+  });
+}
diff --git a/pkgs/oauth2/test/client_credentials_grant_test.dart b/pkgs/oauth2/test/client_credentials_grant_test.dart
new file mode 100644
index 0000000..28de425
--- /dev/null
+++ b/pkgs/oauth2/test/client_credentials_grant_test.dart
@@ -0,0 +1,113 @@
+// Copyright (c) 2012, 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.
+
+@TestOn('vm')
+library;
+
+import 'dart:convert';
+
+import 'package:http/http.dart' as http;
+import 'package:oauth2/oauth2.dart' as oauth2;
+import 'package:test/test.dart';
+
+import 'utils.dart';
+
+final success = jsonEncode({
+  'access_token': '2YotnFZFEjr1zCsicMWpAA',
+  'token_type': 'bearer',
+  'expires_in': 3600,
+  'refresh_token': 'tGzv3JOkF0XG5Qx2TlKWIA',
+});
+
+String auth = 'Basic Y2xpZW50OnNlY3JldA==';
+Uri authEndpoint = Uri.parse('https://example.com');
+
+void main() {
+  late ExpectClient expectClient;
+
+  setUp(() => expectClient = ExpectClient());
+
+  group('basic', () {
+    test('builds correct request with client when using basic auth for client',
+        () async {
+      expectClient.expectRequest((request) async {
+        expect(auth, equals(request.headers['authorization']));
+        expect(request.bodyFields['grant_type'], equals('client_credentials'));
+        return http.Response(success, 200,
+            headers: {'content-type': 'application/json'});
+      });
+
+      var client = await oauth2.clientCredentialsGrant(
+          authEndpoint, 'client', 'secret',
+          httpClient: expectClient);
+
+      expect(client.credentials, isNotNull);
+      expect(client.credentials.accessToken, equals('2YotnFZFEjr1zCsicMWpAA'));
+    });
+
+    test('builds correct request when using query parameters for client',
+        () async {
+      expectClient.expectRequest((request) async {
+        expect(request.bodyFields['grant_type'], equals('client_credentials'));
+        expect(request.bodyFields['client_id'], equals('client'));
+        expect(request.bodyFields['client_secret'], equals('secret'));
+        return http.Response(success, 200,
+            headers: {'content-type': 'application/json'});
+      });
+
+      var client = await oauth2.clientCredentialsGrant(
+          authEndpoint, 'client', 'secret',
+          basicAuth: false, httpClient: expectClient);
+      expect(client.credentials, isNotNull);
+      expect(client.credentials.accessToken, equals('2YotnFZFEjr1zCsicMWpAA'));
+    });
+
+    test('builds correct request using scope', () async {
+      expectClient.expectRequest((request) async {
+        expect(auth, equals(request.headers['authorization']));
+        expect(request.bodyFields['grant_type'], equals('client_credentials'));
+        expect(request.bodyFields['scope'], equals('one two'));
+        return http.Response(success, 200,
+            headers: {'content-type': 'application/json'});
+      });
+
+      var client = await oauth2.clientCredentialsGrant(
+          authEndpoint, 'client', 'secret',
+          scopes: ['one', 'two'], httpClient: expectClient);
+      expect(client.credentials, isNotNull);
+      expect(client.credentials.accessToken, equals('2YotnFZFEjr1zCsicMWpAA'));
+    });
+
+    test('builds correct request using scope with custom delimiter', () async {
+      expectClient.expectRequest((request) async {
+        expect(request.bodyFields['grant_type'], equals('client_credentials'));
+        expect(request.bodyFields['scope'], equals('one,two'));
+        return http.Response(success, 200,
+            headers: {'content-type': 'application/json'});
+      });
+
+      await oauth2.clientCredentialsGrant(authEndpoint, 'client', 'secret',
+          scopes: ['one', 'two'], httpClient: expectClient, delimiter: ',');
+    });
+
+    test('merges with existing query parameters', () async {
+      var authEndpoint = Uri.parse('https://example.com?query=value');
+
+      expectClient.expectRequest((request) async {
+        expect(request.bodyFields['grant_type'], equals('client_credentials'));
+        expect(request.bodyFields['client_id'], equals('client'));
+        expect(request.bodyFields['client_secret'], equals('secret'));
+        expect(request.url.queryParameters['query'], equals('value'));
+        return http.Response(success, 200,
+            headers: {'content-type': 'application/json'});
+      });
+
+      var client = await oauth2.clientCredentialsGrant(
+          authEndpoint, 'client', 'secret',
+          basicAuth: false, httpClient: expectClient);
+      expect(client.credentials, isNotNull);
+      expect(client.credentials.accessToken, equals('2YotnFZFEjr1zCsicMWpAA'));
+    });
+  });
+}
diff --git a/pkgs/oauth2/test/client_test.dart b/pkgs/oauth2/test/client_test.dart
new file mode 100644
index 0000000..3c30d36
--- /dev/null
+++ b/pkgs/oauth2/test/client_test.dart
@@ -0,0 +1,287 @@
+// Copyright (c) 2012, 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.
+
+import 'dart:async';
+import 'dart:convert';
+
+import 'package:http/http.dart' as http;
+import 'package:oauth2/oauth2.dart' as oauth2;
+import 'package:test/test.dart';
+
+import 'utils.dart';
+
+final Uri requestUri = Uri.parse('http://example.com/resource');
+
+final Uri tokenEndpoint = Uri.parse('http://example.com/token');
+
+void main() {
+  late ExpectClient httpClient;
+
+  setUp(() => httpClient = ExpectClient());
+
+  group('with expired credentials', () {
+    test("that can't be refreshed throws an ExpirationException on send", () {
+      var expiration = DateTime.now().subtract(const Duration(hours: 1));
+      var credentials =
+          oauth2.Credentials('access token', expiration: expiration);
+      var client = oauth2.Client(credentials,
+          identifier: 'identifier', secret: 'secret', httpClient: httpClient);
+
+      expect(client.get(requestUri),
+          throwsA(const TypeMatcher<oauth2.ExpirationException>()));
+    });
+
+    test(
+        'that can be refreshed refreshes the credentials and sends the '
+        'request', () async {
+      var expiration = DateTime.now().subtract(const Duration(hours: 1));
+      var credentials = oauth2.Credentials('access token',
+          refreshToken: 'refresh token',
+          tokenEndpoint: tokenEndpoint,
+          expiration: expiration);
+      var client = oauth2.Client(credentials,
+          identifier: 'identifier', secret: 'secret', httpClient: httpClient);
+
+      httpClient.expectRequest((request) {
+        expect(request.method, equals('POST'));
+        expect(request.url.toString(), equals(tokenEndpoint.toString()));
+        return Future.value(http.Response(
+            jsonEncode(
+                {'access_token': 'new access token', 'token_type': 'bearer'}),
+            200,
+            headers: {'content-type': 'application/json'}));
+      });
+
+      httpClient.expectRequest((request) {
+        expect(request.method, equals('GET'));
+        expect(request.url.toString(), equals(requestUri.toString()));
+        expect(request.headers['authorization'],
+            equals('Bearer new access token'));
+
+        return Future.value(http.Response('good job', 200));
+      });
+
+      await client.read(requestUri);
+      expect(client.credentials.accessToken, equals('new access token'));
+    });
+
+    test(
+      'that can be refreshed refreshes only once if multiple requests are made',
+      () async {
+        var expiration = DateTime.now().subtract(const Duration(hours: 1));
+        var credentials = oauth2.Credentials('access token',
+            refreshToken: 'refresh token',
+            tokenEndpoint: tokenEndpoint,
+            expiration: expiration);
+        var client = oauth2.Client(credentials,
+            identifier: 'identifier', secret: 'secret', httpClient: httpClient);
+
+        httpClient.expectRequest((request) {
+          expect(request.method, equals('POST'));
+          expect(request.url.toString(), equals(tokenEndpoint.toString()));
+          return Future.value(http.Response(
+              jsonEncode(
+                  {'access_token': 'new access token', 'token_type': 'bearer'}),
+              200,
+              headers: {'content-type': 'application/json'}));
+        });
+
+        const numCalls = 2;
+
+        for (var i = 0; i < numCalls; i++) {
+          httpClient.expectRequest((request) {
+            expect(request.method, equals('GET'));
+            expect(request.url.toString(), equals(requestUri.toString()));
+            expect(request.headers['authorization'],
+                equals('Bearer new access token'));
+
+            return Future.value(http.Response('good job', 200));
+          });
+        }
+
+        await Future.wait(
+          List<Future<String>>.generate(
+              numCalls, (_) => client.read(requestUri)),
+        );
+
+        expect(client.credentials.accessToken, equals('new access token'));
+      },
+    );
+
+    test('that onCredentialsRefreshed is called', () async {
+      var callbackCalled = false;
+
+      var expiration = DateTime.now().subtract(const Duration(hours: 1));
+      var credentials = oauth2.Credentials('access token',
+          refreshToken: 'refresh token',
+          tokenEndpoint: tokenEndpoint,
+          expiration: expiration);
+      var client = oauth2.Client(credentials,
+          identifier: 'identifier',
+          secret: 'secret',
+          httpClient: httpClient, onCredentialsRefreshed: (credentials) {
+        callbackCalled = true;
+        expect(credentials.accessToken, equals('new access token'));
+      });
+
+      httpClient.expectRequest(
+        (request) => Future.value(
+          http.Response(
+            jsonEncode(
+              {'access_token': 'new access token', 'token_type': 'bearer'},
+            ),
+            200,
+            headers: {'content-type': 'application/json'},
+          ),
+        ),
+      );
+
+      httpClient.expectRequest(
+          (request) => Future.value(http.Response('good job', 200)));
+
+      await client.read(requestUri);
+      expect(callbackCalled, equals(true));
+    });
+  });
+
+  group('with valid credentials', () {
+    test('sends a request with bearer authorization', () {
+      var credentials = oauth2.Credentials('access token');
+      var client = oauth2.Client(credentials,
+          identifier: 'identifier', secret: 'secret', httpClient: httpClient);
+
+      httpClient.expectRequest((request) {
+        expect(request.method, equals('GET'));
+        expect(request.url.toString(), equals(requestUri.toString()));
+        expect(request.headers['authorization'], equals('Bearer access token'));
+
+        return Future.value(http.Response('good job', 200));
+      });
+
+      expect(client.read(requestUri), completion(equals('good job')));
+    });
+
+    test('can manually refresh the credentials', () async {
+      var credentials = oauth2.Credentials('access token',
+          refreshToken: 'refresh token', tokenEndpoint: tokenEndpoint);
+      var client = oauth2.Client(credentials,
+          identifier: 'identifier', secret: 'secret', httpClient: httpClient);
+
+      httpClient.expectRequest((request) {
+        expect(request.method, equals('POST'));
+        expect(request.url.toString(), equals(tokenEndpoint.toString()));
+        return Future.value(http.Response(
+            jsonEncode(
+                {'access_token': 'new access token', 'token_type': 'bearer'}),
+            200,
+            headers: {'content-type': 'application/json'}));
+      });
+
+      await client.refreshCredentials();
+      expect(client.credentials.accessToken, equals('new access token'));
+    });
+
+    test("without a refresh token can't manually refresh the credentials", () {
+      var credentials = oauth2.Credentials('access token');
+      var client = oauth2.Client(credentials,
+          identifier: 'identifier', secret: 'secret', httpClient: httpClient);
+
+      expect(client.refreshCredentials(), throwsA(isStateError));
+    });
+  });
+
+  group('with invalid credentials', () {
+    test('throws an AuthorizationException for a 401 response', () {
+      var credentials = oauth2.Credentials('access token');
+      var client = oauth2.Client(credentials,
+          identifier: 'identifier', secret: 'secret', httpClient: httpClient);
+
+      httpClient.expectRequest((request) {
+        expect(request.method, equals('GET'));
+        expect(request.url.toString(), equals(requestUri.toString()));
+        expect(request.headers['authorization'], equals('Bearer access token'));
+
+        var authenticate = 'Bearer error="invalid_token", error_description='
+            '"Something is terribly wrong."';
+        return Future.value(http.Response('bad job', 401,
+            headers: {'www-authenticate': authenticate}));
+      });
+
+      expect(client.read(requestUri),
+          throwsA(const TypeMatcher<oauth2.AuthorizationException>()));
+    });
+
+    test('passes through a 401 response without www-authenticate', () async {
+      var credentials = oauth2.Credentials('access token');
+      var client = oauth2.Client(credentials,
+          identifier: 'identifier', secret: 'secret', httpClient: httpClient);
+
+      httpClient.expectRequest((request) {
+        expect(request.method, equals('GET'));
+        expect(request.url.toString(), equals(requestUri.toString()));
+        expect(request.headers['authorization'], equals('Bearer access token'));
+
+        return Future.value(http.Response('bad job', 401));
+      });
+
+      expect((await client.get(requestUri)).statusCode, equals(401));
+    });
+
+    test('passes through a 401 response with invalid www-authenticate',
+        () async {
+      var credentials = oauth2.Credentials('access token');
+      var client = oauth2.Client(credentials,
+          identifier: 'identifier', secret: 'secret', httpClient: httpClient);
+
+      httpClient.expectRequest((request) {
+        expect(request.method, equals('GET'));
+        expect(request.url.toString(), equals(requestUri.toString()));
+        expect(request.headers['authorization'], equals('Bearer access token'));
+
+        var authenticate = 'Bearer error="invalid_token" error_description='
+            '"Something is terribly wrong."';
+        return Future.value(http.Response('bad job', 401,
+            headers: {'www-authenticate': authenticate}));
+      });
+
+      expect((await client.get(requestUri)).statusCode, equals(401));
+    });
+
+    test('passes through a 401 response with non-bearer www-authenticate',
+        () async {
+      var credentials = oauth2.Credentials('access token');
+      var client = oauth2.Client(credentials,
+          identifier: 'identifier', secret: 'secret', httpClient: httpClient);
+
+      httpClient.expectRequest((request) {
+        expect(request.method, equals('GET'));
+        expect(request.url.toString(), equals(requestUri.toString()));
+        expect(request.headers['authorization'], equals('Bearer access token'));
+
+        return Future.value(http.Response('bad job', 401,
+            headers: {'www-authenticate': 'Digest'}));
+      });
+
+      expect((await client.get(requestUri)).statusCode, equals(401));
+    });
+
+    test('passes through a 401 response with non-OAuth2 www-authenticate',
+        () async {
+      var credentials = oauth2.Credentials('access token');
+      var client = oauth2.Client(credentials,
+          identifier: 'identifier', secret: 'secret', httpClient: httpClient);
+
+      httpClient.expectRequest((request) {
+        expect(request.method, equals('GET'));
+        expect(request.url.toString(), equals(requestUri.toString()));
+        expect(request.headers['authorization'], equals('Bearer access token'));
+
+        return Future.value(http.Response('bad job', 401,
+            headers: {'www-authenticate': 'Bearer'}));
+      });
+
+      expect((await client.get(requestUri)).statusCode, equals(401));
+    });
+  });
+}
diff --git a/pkgs/oauth2/test/credentials_test.dart b/pkgs/oauth2/test/credentials_test.dart
new file mode 100644
index 0000000..d83bc7e
--- /dev/null
+++ b/pkgs/oauth2/test/credentials_test.dart
@@ -0,0 +1,331 @@
+// Copyright (c) 2012, 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.
+
+import 'dart:async';
+import 'dart:convert';
+
+import 'package:http/http.dart' as http;
+import 'package:oauth2/oauth2.dart' as oauth2;
+import 'package:test/test.dart';
+
+import 'utils.dart';
+
+final Uri tokenEndpoint = Uri.parse('http://example.com/token');
+
+void main() {
+  late ExpectClient httpClient;
+
+  setUp(() => httpClient = ExpectClient());
+
+  test('is not expired if no expiration exists', () {
+    var credentials = oauth2.Credentials('access token');
+    expect(credentials.isExpired, isFalse);
+  });
+
+  test('is not expired if the expiration is in the future', () {
+    var expiration = DateTime.now().add(const Duration(hours: 1));
+    var credentials =
+        oauth2.Credentials('access token', expiration: expiration);
+    expect(credentials.isExpired, isFalse);
+  });
+
+  test('is expired if the expiration is in the past', () {
+    var expiration = DateTime.now().subtract(const Duration(hours: 1));
+    var credentials =
+        oauth2.Credentials('access token', expiration: expiration);
+    expect(credentials.isExpired, isTrue);
+  });
+
+  test("can't refresh without a refresh token", () {
+    var credentials =
+        oauth2.Credentials('access token', tokenEndpoint: tokenEndpoint);
+    expect(credentials.canRefresh, false);
+
+    expect(
+        credentials.refresh(
+            identifier: 'identifier', secret: 'secret', httpClient: httpClient),
+        throwsStateError);
+  });
+
+  test("can't refresh without a token endpoint", () {
+    var credentials =
+        oauth2.Credentials('access token', refreshToken: 'refresh token');
+    expect(credentials.canRefresh, false);
+
+    expect(
+        credentials.refresh(
+            identifier: 'identifier', secret: 'secret', httpClient: httpClient),
+        throwsStateError);
+  });
+
+  test('can refresh with a refresh token and a token endpoint', () async {
+    var credentials = oauth2.Credentials('access token',
+        refreshToken: 'refresh token',
+        tokenEndpoint: tokenEndpoint,
+        scopes: ['scope1', 'scope2']);
+    expect(credentials.canRefresh, true);
+
+    httpClient.expectRequest((request) {
+      expect(request.method, equals('POST'));
+      expect(request.url.toString(), equals(tokenEndpoint.toString()));
+      expect(
+          request.bodyFields,
+          equals({
+            'grant_type': 'refresh_token',
+            'refresh_token': 'refresh token',
+            'scope': 'scope1 scope2'
+          }));
+      expect(
+          request.headers,
+          containsPair('Authorization',
+              'Basic aWQlQzMlQUJudCVDNCVBQmZpZXI6cyVDMyVBQmNyZXQ='));
+
+      return Future.value(http.Response(
+          jsonEncode({
+            'access_token': 'new access token',
+            'token_type': 'bearer',
+            'refresh_token': 'new refresh token'
+          }),
+          200,
+          headers: {'content-type': 'application/json'}));
+    });
+
+    credentials = await credentials.refresh(
+        identifier: 'idëntÄ«fier', secret: 'sëcret', httpClient: httpClient);
+    expect(credentials.accessToken, equals('new access token'));
+    expect(credentials.refreshToken, equals('new refresh token'));
+  });
+
+  test('sets proper scope string when using custom delimiter', () async {
+    var credentials = oauth2.Credentials('access token',
+        refreshToken: 'refresh token',
+        tokenEndpoint: tokenEndpoint,
+        scopes: ['scope1', 'scope2'],
+        delimiter: ',');
+    httpClient.expectRequest((http.Request request) {
+      expect(request.bodyFields['scope'], equals('scope1,scope2'));
+      return Future.value(http.Response(
+          jsonEncode({
+            'access_token': 'new access token',
+            'token_type': 'bearer',
+            'refresh_token': 'new refresh token'
+          }),
+          200,
+          headers: {'content-type': 'application/json'}));
+    });
+    await credentials.refresh(
+        identifier: 'idëntÄ«fier', secret: 'sëcret', httpClient: httpClient);
+  });
+
+  test('can refresh without a client secret', () async {
+    var credentials = oauth2.Credentials('access token',
+        refreshToken: 'refresh token',
+        tokenEndpoint: tokenEndpoint,
+        scopes: ['scope1', 'scope2']);
+    expect(credentials.canRefresh, true);
+
+    httpClient.expectRequest((request) {
+      expect(request.method, equals('POST'));
+      expect(request.url.toString(), equals(tokenEndpoint.toString()));
+      expect(
+          request.bodyFields,
+          equals({
+            'grant_type': 'refresh_token',
+            'refresh_token': 'refresh token',
+            'scope': 'scope1 scope2',
+            'client_id': 'identifier'
+          }));
+
+      return Future.value(http.Response(
+          jsonEncode({
+            'access_token': 'new access token',
+            'token_type': 'bearer',
+            'refresh_token': 'new refresh token'
+          }),
+          200,
+          headers: {'content-type': 'application/json'}));
+    });
+
+    credentials = await credentials.refresh(
+        identifier: 'identifier', httpClient: httpClient);
+    expect(credentials.accessToken, equals('new access token'));
+    expect(credentials.refreshToken, equals('new refresh token'));
+  });
+
+  test('can refresh without client authentication', () async {
+    var credentials = oauth2.Credentials('access token',
+        refreshToken: 'refresh token',
+        tokenEndpoint: tokenEndpoint,
+        scopes: ['scope1', 'scope2']);
+    expect(credentials.canRefresh, true);
+
+    httpClient.expectRequest((request) {
+      expect(request.method, equals('POST'));
+      expect(request.url.toString(), equals(tokenEndpoint.toString()));
+      expect(
+          request.bodyFields,
+          equals({
+            'grant_type': 'refresh_token',
+            'refresh_token': 'refresh token',
+            'scope': 'scope1 scope2'
+          }));
+
+      return Future.value(http.Response(
+          jsonEncode({
+            'access_token': 'new access token',
+            'token_type': 'bearer',
+            'refresh_token': 'new refresh token'
+          }),
+          200,
+          headers: {'content-type': 'application/json'}));
+    });
+
+    credentials = await credentials.refresh(httpClient: httpClient);
+    expect(credentials.accessToken, equals('new access token'));
+    expect(credentials.refreshToken, equals('new refresh token'));
+  });
+
+  test("uses the old refresh token if a new one isn't provided", () async {
+    var credentials = oauth2.Credentials('access token',
+        refreshToken: 'refresh token', tokenEndpoint: tokenEndpoint);
+    expect(credentials.canRefresh, true);
+
+    httpClient.expectRequest((request) {
+      expect(request.method, equals('POST'));
+      expect(request.url.toString(), equals(tokenEndpoint.toString()));
+      expect(
+          request.bodyFields,
+          equals({
+            'grant_type': 'refresh_token',
+            'refresh_token': 'refresh token'
+          }));
+      expect(
+          request.headers,
+          containsPair('Authorization',
+              'Basic aWQlQzMlQUJudCVDNCVBQmZpZXI6cyVDMyVBQmNyZXQ='));
+
+      return Future.value(http.Response(
+          jsonEncode(
+              {'access_token': 'new access token', 'token_type': 'bearer'}),
+          200,
+          headers: {'content-type': 'application/json'}));
+    });
+
+    credentials = await credentials.refresh(
+        identifier: 'idëntÄ«fier', secret: 'sëcret', httpClient: httpClient);
+    expect(credentials.accessToken, equals('new access token'));
+    expect(credentials.refreshToken, equals('refresh token'));
+  });
+
+  test('uses form-field authentication if basicAuth is false', () async {
+    var credentials = oauth2.Credentials('access token',
+        refreshToken: 'refresh token',
+        tokenEndpoint: tokenEndpoint,
+        scopes: ['scope1', 'scope2']);
+    expect(credentials.canRefresh, true);
+
+    httpClient.expectRequest((request) {
+      expect(request.method, equals('POST'));
+      expect(request.url.toString(), equals(tokenEndpoint.toString()));
+      expect(
+          request.bodyFields,
+          equals({
+            'grant_type': 'refresh_token',
+            'refresh_token': 'refresh token',
+            'scope': 'scope1 scope2',
+            'client_id': 'idëntÄ«fier',
+            'client_secret': 'sëcret'
+          }));
+
+      return Future.value(http.Response(
+          jsonEncode({
+            'access_token': 'new access token',
+            'token_type': 'bearer',
+            'refresh_token': 'new refresh token'
+          }),
+          200,
+          headers: {'content-type': 'application/json'}));
+    });
+
+    credentials = await credentials.refresh(
+        identifier: 'idëntÄ«fier',
+        secret: 'sëcret',
+        basicAuth: false,
+        httpClient: httpClient);
+    expect(credentials.accessToken, equals('new access token'));
+    expect(credentials.refreshToken, equals('new refresh token'));
+  });
+
+  group('fromJson', () {
+    oauth2.Credentials fromMap(Map<String, dynamic> map) =>
+        oauth2.Credentials.fromJson(jsonEncode(map));
+
+    test('should load the same credentials from toJson', () {
+      // Round the expiration down to milliseconds since epoch, since that's
+      // what the credentials file stores. Otherwise sub-millisecond time gets
+      // in the way.
+      var expiration = DateTime.now().subtract(const Duration(hours: 1));
+      expiration = DateTime.fromMillisecondsSinceEpoch(
+          expiration.millisecondsSinceEpoch);
+
+      var credentials = oauth2.Credentials('access token',
+          refreshToken: 'refresh token',
+          idToken: 'id token',
+          tokenEndpoint: tokenEndpoint,
+          scopes: ['scope1', 'scope2'],
+          expiration: expiration);
+      var reloaded = oauth2.Credentials.fromJson(credentials.toJson());
+
+      expect(reloaded.accessToken, equals(credentials.accessToken));
+      expect(reloaded.refreshToken, equals(credentials.refreshToken));
+      expect(reloaded.idToken, equals(credentials.idToken));
+      expect(reloaded.tokenEndpoint.toString(),
+          equals(credentials.tokenEndpoint.toString()));
+      expect(reloaded.scopes, equals(credentials.scopes));
+      expect(reloaded.expiration, equals(credentials.expiration));
+    });
+
+    test('should throw a FormatException for invalid JSON', () {
+      expect(
+          () => oauth2.Credentials.fromJson('foo bar'), throwsFormatException);
+    });
+
+    test("should throw a FormatException for JSON that's not a map", () {
+      expect(() => oauth2.Credentials.fromJson('null'), throwsFormatException);
+    });
+
+    test('should throw a FormatException if there is no accessToken', () {
+      expect(() => fromMap({}), throwsFormatException);
+    });
+
+    test('should throw a FormatException if accessToken is not a string', () {
+      expect(() => fromMap({'accessToken': 12}), throwsFormatException);
+    });
+
+    test('should throw a FormatException if refreshToken is not a string', () {
+      expect(() => fromMap({'accessToken': 'foo', 'refreshToken': 12}),
+          throwsFormatException);
+    });
+
+    test('should throw a FormatException if idToken is not a string', () {
+      expect(() => fromMap({'accessToken': 'foo', 'idToken': 12}),
+          throwsFormatException);
+    });
+
+    test('should throw a FormatException if tokenEndpoint is not a string', () {
+      expect(() => fromMap({'accessToken': 'foo', 'tokenEndpoint': 12}),
+          throwsFormatException);
+    });
+
+    test('should throw a FormatException if scopes is not a list', () {
+      expect(() => fromMap({'accessToken': 'foo', 'scopes': 12}),
+          throwsFormatException);
+    });
+
+    test('should throw a FormatException if expiration is not an int', () {
+      expect(() => fromMap({'accessToken': 'foo', 'expiration': '12'}),
+          throwsFormatException);
+    });
+  });
+}
diff --git a/pkgs/oauth2/test/handle_access_token_response_test.dart b/pkgs/oauth2/test/handle_access_token_response_test.dart
new file mode 100644
index 0000000..4d7b519
--- /dev/null
+++ b/pkgs/oauth2/test/handle_access_token_response_test.dart
@@ -0,0 +1,301 @@
+// Copyright (c) 2012, 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.
+
+import 'dart:convert';
+
+import 'package:http/http.dart' as http;
+import 'package:oauth2/oauth2.dart' as oauth2;
+import 'package:oauth2/src/handle_access_token_response.dart';
+import 'package:oauth2/src/parameters.dart';
+import 'package:test/test.dart';
+
+import 'utils.dart';
+
+final Uri tokenEndpoint = Uri.parse('https://example.com/token');
+
+final DateTime startTime = DateTime.now();
+
+oauth2.Credentials handle(http.Response response,
+        {GetParameters? getParameters}) =>
+    handleAccessTokenResponse(
+        response, tokenEndpoint, startTime, ['scope'], ' ',
+        getParameters: getParameters);
+
+void main() {
+  group('an error response', () {
+    oauth2.Credentials handleError(
+            {String body = '{"error": "invalid_request"}',
+            int statusCode = 400,
+            Map<String, String> headers = const {
+              'content-type': 'application/json'
+            }}) =>
+        handle(http.Response(body, statusCode, headers: headers));
+
+    test('causes an AuthorizationException', () {
+      expect(handleError, throwsAuthorizationException);
+    });
+
+    test('with a 401 code causes an AuthorizationException', () {
+      expect(() => handleError(statusCode: 401), throwsAuthorizationException);
+    });
+
+    test('with an unexpected code causes a FormatException', () {
+      expect(() => handleError(statusCode: 500), throwsFormatException);
+    });
+
+    test('with no content-type causes a FormatException', () {
+      expect(() => handleError(headers: {}), throwsFormatException);
+    });
+
+    test('with a non-JSON content-type causes a FormatException', () {
+      expect(() => handleError(headers: {'content-type': 'text/plain'}),
+          throwsFormatException);
+    });
+
+    test('with a non-JSON, non-plain content-type causes a FormatException',
+        () {
+      expect(() => handleError(headers: {'content-type': 'image/png'}),
+          throwsFormatException);
+    });
+
+    test(
+        'with a JSON content-type and charset causes an '
+        'AuthorizationException', () {
+      expect(
+          () => handleError(
+              headers: {'content-type': 'application/json; charset=UTF-8'}),
+          throwsAuthorizationException);
+    });
+
+    test('with invalid JSON causes a FormatException', () {
+      expect(() => handleError(body: 'not json'), throwsFormatException);
+    });
+
+    test('with a non-string error causes a FormatException', () {
+      expect(() => handleError(body: '{"error": 12}'), throwsFormatException);
+    });
+
+    test('with a non-string error_description causes a FormatException', () {
+      expect(
+          () => handleError(
+              body: jsonEncode(
+                  {'error': 'invalid_request', 'error_description': 12})),
+          throwsFormatException);
+    });
+
+    test('with a non-string error_uri causes a FormatException', () {
+      expect(
+          () => handleError(
+              body: jsonEncode({'error': 'invalid_request', 'error_uri': 12})),
+          throwsFormatException);
+    });
+
+    test('with a string error_description causes a AuthorizationException', () {
+      expect(
+          () => handleError(
+                  body: jsonEncode({
+                'error': 'invalid_request',
+                'error_description': 'description'
+              })),
+          throwsAuthorizationException);
+    });
+
+    test('with a string error_uri causes a AuthorizationException', () {
+      expect(
+          () => handleError(
+                  body: jsonEncode({
+                'error': 'invalid_request',
+                'error_uri': 'http://example.com/error'
+              })),
+          throwsAuthorizationException);
+    });
+  });
+
+  group('a success response', () {
+    oauth2.Credentials handleSuccess(
+        {String contentType = 'application/json',
+        Object? accessToken = 'access token',
+        Object? tokenType = 'bearer',
+        Object? expiresIn,
+        Object? refreshToken,
+        Object? scope}) {
+      return handle(http.Response(
+          jsonEncode({
+            'access_token': accessToken,
+            'token_type': tokenType,
+            'expires_in': expiresIn,
+            'refresh_token': refreshToken,
+            'scope': scope
+          }),
+          200,
+          headers: {'content-type': contentType}));
+    }
+
+    test('returns the correct credentials', () {
+      var credentials = handleSuccess();
+      expect(credentials.accessToken, equals('access token'));
+      expect(credentials.tokenEndpoint.toString(),
+          equals(tokenEndpoint.toString()));
+    });
+
+    test('with no content-type causes a FormatException', () {
+      expect(() => handleSuccess(contentType: ''), throwsFormatException);
+    });
+
+    test('with a non-JSON content-type causes a FormatException', () {
+      expect(() => handleSuccess(contentType: 'text/plain'),
+          throwsFormatException);
+    });
+
+    test(
+        'with a JSON content-type and charset returns the correct '
+        'credentials', () {
+      var credentials =
+          handleSuccess(contentType: 'application/json; charset=UTF-8');
+      expect(credentials.accessToken, equals('access token'));
+    });
+
+    test('with a JavScript content-type returns the correct credentials', () {
+      var credentials = handleSuccess(contentType: 'text/javascript');
+      expect(credentials.accessToken, equals('access token'));
+    });
+
+    test('with custom getParameters() returns the correct credentials', () {
+      var body = '_${jsonEncode({
+            'token_type': 'bearer',
+            'access_token': 'access token'
+          })}';
+      var credentials = handle(
+        http.Response(body, 200, headers: {'content-type': 'text/plain'}),
+        getParameters: (contentType, body) =>
+            jsonDecode(body.substring(1)) as Map<String, dynamic>,
+      );
+      expect(credentials.accessToken, equals('access token'));
+      expect(credentials.tokenEndpoint.toString(),
+          equals(tokenEndpoint.toString()));
+    });
+
+    test('throws a FormatException if custom getParameters rejects response',
+        () {
+      var response = http.Response(
+          jsonEncode({
+            'access_token': 'access token',
+            'token_type': 'bearer',
+            'expires_in': 24,
+            'refresh_token': 'refresh token',
+            'scope': 'scope',
+          }),
+          200,
+          headers: {'content-type': 'foo/bar'});
+
+      expect(
+          () => handle(response,
+              getParameters: (contentType, body) => throw FormatException(
+                  'unsupported content-type: $contentType')),
+          throwsFormatException);
+    });
+
+    test('with a null access token throws a FormatException', () {
+      expect(() => handleSuccess(accessToken: null), throwsFormatException);
+    });
+
+    test('with a non-string access token throws a FormatException', () {
+      expect(() => handleSuccess(accessToken: 12), throwsFormatException);
+    });
+
+    test('with a null token type throws a FormatException', () {
+      expect(() => handleSuccess(tokenType: null), throwsFormatException);
+    });
+
+    test('with a non-string token type throws a FormatException', () {
+      expect(() => handleSuccess(tokenType: 12), throwsFormatException);
+    });
+
+    test('with a non-"bearer" token type throws a FormatException', () {
+      expect(() => handleSuccess(tokenType: 'mac'), throwsFormatException);
+    });
+
+    test('with a non-int expires-in throws a FormatException', () {
+      expect(() => handleSuccess(expiresIn: 'whenever'), throwsFormatException);
+    });
+
+    test(
+        'with expires-in sets the expiration to ten seconds earlier than the '
+        'server says', () {
+      var credentials = handleSuccess(expiresIn: 100);
+      expect(credentials.expiration?.millisecondsSinceEpoch,
+          startTime.millisecondsSinceEpoch + 90 * 1000);
+    });
+
+    test('with expires-in encoded as string', () {
+      var credentials = handleSuccess(expiresIn: '110');
+      expect(credentials.expiration?.millisecondsSinceEpoch,
+          startTime.millisecondsSinceEpoch + 100 * 1000);
+    });
+
+    test('with a non-string refresh token throws a FormatException', () {
+      expect(() => handleSuccess(refreshToken: 12), throwsFormatException);
+    });
+
+    test('with a refresh token sets the refresh token', () {
+      var credentials = handleSuccess(refreshToken: 'refresh me');
+      expect(credentials.refreshToken, equals('refresh me'));
+    });
+
+    test('with a non-string scope throws a FormatException', () {
+      expect(() => handleSuccess(scope: 12), throwsFormatException);
+    });
+
+    test('with a scope sets the scopes', () {
+      var credentials = handleSuccess(scope: 'scope1 scope2');
+      expect(credentials.scopes, equals(['scope1', 'scope2']));
+    });
+
+    test('with a custom scope delimiter sets the scopes', () {
+      var response = http.Response(
+          jsonEncode({
+            'access_token': 'access token',
+            'token_type': 'bearer',
+            'expires_in': null,
+            'refresh_token': null,
+            'scope': 'scope1,scope2'
+          }),
+          200,
+          headers: {'content-type': 'application/json'});
+      var credentials = handleAccessTokenResponse(
+          response, tokenEndpoint, startTime, ['scope'], ',');
+      expect(credentials.scopes, equals(['scope1', 'scope2']));
+    });
+  });
+
+  group('a success response with a id_token', () {
+    oauth2.Credentials handleSuccess(
+        {String contentType = 'application/json',
+        Object? accessToken = 'access token',
+        Object? tokenType = 'bearer',
+        Object? expiresIn,
+        Object? idToken = 'decode me',
+        Object? scope}) {
+      return handle(http.Response(
+          jsonEncode({
+            'access_token': accessToken,
+            'token_type': tokenType,
+            'expires_in': expiresIn,
+            'id_token': idToken,
+            'scope': scope
+          }),
+          200,
+          headers: {'content-type': contentType}));
+    }
+
+    test('with a non-string id token throws a FormatException', () {
+      expect(() => handleSuccess(idToken: 12), throwsFormatException);
+    });
+
+    test('with a id token sets the id token', () {
+      var credentials = handleSuccess(idToken: 'decode me');
+      expect(credentials.idToken, equals('decode me'));
+    });
+  });
+}
diff --git a/pkgs/oauth2/test/resource_owner_password_grant_test.dart b/pkgs/oauth2/test/resource_owner_password_grant_test.dart
new file mode 100644
index 0000000..7a5d9b5
--- /dev/null
+++ b/pkgs/oauth2/test/resource_owner_password_grant_test.dart
@@ -0,0 +1,168 @@
+// Copyright (c) 2012, 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.
+
+@TestOn('vm')
+library;
+
+import 'dart:async';
+import 'dart:convert';
+
+import 'package:http/http.dart' as http;
+import 'package:oauth2/oauth2.dart' as oauth2;
+import 'package:test/test.dart';
+
+import 'utils.dart';
+
+final success = jsonEncode({
+  'access_token': '2YotnFZFEjr1zCsicMWpAA',
+  'token_type': 'bearer',
+  'expires_in': 3600,
+  'refresh_token': 'tGzv3JOkF0XG5Qx2TlKWIA',
+});
+
+String auth = 'Basic Y2xpZW50OnNlY3JldA==';
+Uri authEndpoint = Uri.parse('https://example.com');
+
+void main() {
+  late ExpectClient expectClient;
+
+  setUp(() => expectClient = ExpectClient());
+
+  group('basic', () {
+    test('builds correct request with client when using basic auth for client',
+        () async {
+      expectClient.expectRequest((request) async {
+        expect(auth, equals(request.headers['authorization']));
+        expect(request.bodyFields['grant_type'], equals('password'));
+        expect(request.bodyFields['username'], equals('username'));
+        expect(request.bodyFields['password'], equals('userpass'));
+        return http.Response(success, 200,
+            headers: {'content-type': 'application/json'});
+      });
+
+      var client = await oauth2.resourceOwnerPasswordGrant(
+          authEndpoint, 'username', 'userpass',
+          identifier: 'client', secret: 'secret', httpClient: expectClient);
+
+      expect(client.credentials, isNotNull);
+      expect(client.credentials.accessToken, equals('2YotnFZFEjr1zCsicMWpAA'));
+    });
+
+    test('passes the onCredentialsRefreshed callback to the client', () async {
+      expectClient.expectRequest((request) async {
+        return http.Response(
+            jsonEncode({
+              'access_token': '2YotnFZFEjr1zCsicMWpAA',
+              'token_type': 'bearer',
+              'expires_in': -3600,
+              'refresh_token': 'tGzv3JOkF0XG5Qx2TlKWIA',
+            }),
+            200,
+            headers: {'content-type': 'application/json'});
+      });
+
+      var isCallbackInvoked = false;
+
+      var client = await oauth2.resourceOwnerPasswordGrant(
+          authEndpoint, 'username', 'userpass',
+          identifier: 'client', secret: 'secret', httpClient: expectClient,
+          onCredentialsRefreshed: (oauth2.Credentials credentials) {
+        isCallbackInvoked = true;
+      });
+
+      expectClient.expectRequest((request) {
+        return Future.value(http.Response(
+            jsonEncode(
+                {'access_token': 'new access token', 'token_type': 'bearer'}),
+            200,
+            headers: {'content-type': 'application/json'}));
+      });
+
+      expectClient.expectRequest((request) {
+        return Future.value(http.Response('good job', 200));
+      });
+
+      await client.read(Uri.parse('http://example.com/resource'));
+      expect(isCallbackInvoked, equals(true));
+    });
+
+    test('builds correct request when using query parameters for client',
+        () async {
+      expectClient.expectRequest((request) async {
+        expect(request.bodyFields['grant_type'], equals('password'));
+        expect(request.bodyFields['client_id'], equals('client'));
+        expect(request.bodyFields['client_secret'], equals('secret'));
+        expect(request.bodyFields['username'], equals('username'));
+        expect(request.bodyFields['password'], equals('userpass'));
+        return http.Response(success, 200,
+            headers: {'content-type': 'application/json'});
+      });
+
+      var client = await oauth2.resourceOwnerPasswordGrant(
+          authEndpoint, 'username', 'userpass',
+          identifier: 'client',
+          secret: 'secret',
+          basicAuth: false,
+          httpClient: expectClient);
+      expect(client.credentials, isNotNull);
+      expect(client.credentials.accessToken, equals('2YotnFZFEjr1zCsicMWpAA'));
+    });
+
+    test('builds correct request using scope', () async {
+      expectClient.expectRequest((request) async {
+        expect(request.bodyFields['grant_type'], equals('password'));
+        expect(request.bodyFields['username'], equals('username'));
+        expect(request.bodyFields['password'], equals('userpass'));
+        expect(request.bodyFields['scope'], equals('one two'));
+        return http.Response(success, 200,
+            headers: {'content-type': 'application/json'});
+      });
+
+      var client = await oauth2.resourceOwnerPasswordGrant(
+          authEndpoint, 'username', 'userpass',
+          scopes: ['one', 'two'], httpClient: expectClient);
+      expect(client.credentials, isNotNull);
+      expect(client.credentials.accessToken, equals('2YotnFZFEjr1zCsicMWpAA'));
+    });
+
+    test('builds correct request using scope with custom delimiter', () async {
+      expectClient.expectRequest((request) async {
+        expect(request.bodyFields['grant_type'], equals('password'));
+        expect(request.bodyFields['username'], equals('username'));
+        expect(request.bodyFields['password'], equals('userpass'));
+        expect(request.bodyFields['scope'], equals('one,two'));
+        return http.Response(success, 200,
+            headers: {'content-type': 'application/json'});
+      });
+
+      await oauth2.resourceOwnerPasswordGrant(
+          authEndpoint, 'username', 'userpass',
+          scopes: ['one', 'two'], httpClient: expectClient, delimiter: ',');
+    });
+
+    test('merges with existing query parameters', () async {
+      var authEndpoint = Uri.parse('https://example.com?query=value');
+
+      expectClient.expectRequest((request) async {
+        expect(request.bodyFields['grant_type'], equals('password'));
+        expect(request.bodyFields['client_id'], equals('client'));
+        expect(request.bodyFields['client_secret'], equals('secret'));
+        expect(request.bodyFields['username'], equals('username'));
+        expect(request.bodyFields['password'], equals('userpass'));
+        expect(request.url.queryParameters['query'], equals('value'));
+        return http.Response(success, 200,
+            headers: {'content-type': 'application/json'});
+      });
+
+      var client = await oauth2.resourceOwnerPasswordGrant(
+          authEndpoint, 'username', 'userpass',
+          identifier: 'client',
+          secret: 'secret',
+          basicAuth: false,
+          httpClient: expectClient);
+      expect(client.credentials, isNotNull);
+      expect(client.credentials.accessToken, equals('2YotnFZFEjr1zCsicMWpAA'));
+    });
+  });
+}
diff --git a/pkgs/oauth2/test/utils.dart b/pkgs/oauth2/test/utils.dart
new file mode 100644
index 0000000..4f3b747
--- /dev/null
+++ b/pkgs/oauth2/test/utils.dart
@@ -0,0 +1,49 @@
+// Copyright (c) 2012, 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.
+
+import 'dart:async';
+import 'dart:collection' show Queue;
+
+import 'package:http/http.dart' as http;
+import 'package:http/testing.dart';
+import 'package:oauth2/oauth2.dart' as oauth2;
+import 'package:test/test.dart';
+
+class ExpectClient extends MockClient {
+  final Queue<MockClientHandler> _handlers;
+
+  ExpectClient._(super.fn) : _handlers = Queue<MockClientHandler>();
+
+  factory ExpectClient() {
+    late ExpectClient client;
+    client = ExpectClient._((request) => client._handleRequest(request));
+    return client;
+  }
+
+  void expectRequest(MockClientHandler fn) {
+    var completer = Completer<void>();
+    expect(completer.future, completes);
+
+    _handlers.add((request) {
+      completer.complete(null);
+      return fn(request);
+    });
+  }
+
+  Future<http.Response> _handleRequest(http.Request request) {
+    if (_handlers.isEmpty) {
+      return Future.value(http.Response('not found', 404));
+    } else {
+      return _handlers.removeFirst()(request);
+    }
+  }
+}
+
+/// A matcher for functions that throw AuthorizationException.
+final Matcher throwsAuthorizationException =
+    throwsA(const TypeMatcher<oauth2.AuthorizationException>());
+
+/// A matcher for functions that throw ExpirationException.
+final Matcher throwsExpirationException =
+    throwsA(const TypeMatcher<oauth2.ExpirationException>());
diff --git a/pkgs/source_map_stack_trace/.gitignore b/pkgs/source_map_stack_trace/.gitignore
new file mode 100644
index 0000000..f73b2f9
--- /dev/null
+++ b/pkgs/source_map_stack_trace/.gitignore
@@ -0,0 +1,4 @@
+.dart_tool/
+.packages
+.pub/
+pubspec.lock
diff --git a/pkgs/source_map_stack_trace/.test_config b/pkgs/source_map_stack_trace/.test_config
new file mode 100644
index 0000000..531426a
--- /dev/null
+++ b/pkgs/source_map_stack_trace/.test_config
@@ -0,0 +1,5 @@
+{
+  "test_package": {
+    "platforms": ["vm"]
+  }
+}
\ No newline at end of file
diff --git a/pkgs/source_map_stack_trace/AUTHORS b/pkgs/source_map_stack_trace/AUTHORS
new file mode 100644
index 0000000..e8063a8
--- /dev/null
+++ b/pkgs/source_map_stack_trace/AUTHORS
@@ -0,0 +1,6 @@
+# Below is a list of people and organizations that have contributed
+# to the project. Names should be added to the list like so:
+#
+#   Name/Organization <email address>
+
+Google Inc.
diff --git a/pkgs/source_map_stack_trace/CHANGELOG.md b/pkgs/source_map_stack_trace/CHANGELOG.md
new file mode 100644
index 0000000..00c66d9
--- /dev/null
+++ b/pkgs/source_map_stack_trace/CHANGELOG.md
@@ -0,0 +1,82 @@
+## 2.1.3-wip
+
+## 2.1.2
+
+* Require Dart 3.3.0
+* Move to `dart-lang/tools` monorepo.
+
+## 2.1.1
+
+* Populate the pubspec `repository` field.
+
+## 2.1.0
+
+* Stable release for null safety.
+* Require Dart 2.12
+
+## 2.0.0
+
+### Breaking Changes
+
+* Removed dependency on `package_resolver` and changed the apis to accept a
+  `Map<String, Uri>` which maps package names to the base uri to resolve the
+  `package:` uris for those packages.
+* The `sdkRoot` argument must be an `Uri`. Use `Uri.parse` for use
+  cases previously passing a `String`.
+* The deprecated `packageRoot` argument has been removed.
+
+## 1.1.5
+
+* Set max SDK version to `<3.0.0`.
+
+## 1.1.4
+
+* Support source maps that depend on the uri of the location to resolve spans
+  correctly.
+
+## 1.1.3
+
+* Add a missing dependency on `path`.
+
+## 1.1.2
+
+* Fix a typo in the previous fix.
+
+## 1.1.1
+
+* Don't crash if the `SyncPackageResolver` has no package information at all.
+
+## 1.1.0
+
+* `mapStackTrace()` now uses a `SyncPackageResolver` object from the
+  [`package_resolver` package][package_resolver] to recreate `package:` URIs.
+
+* **Deprecation**: the `packageRoot` parameter to `mapStackTrace` is deprecated
+  in favor of the `packageInfo` parameter described above. It will be removed in
+  a future release.
+
+[package_resolver]: https://pub.dartlang.org/packages/package_resolver
+
+## 1.0.5
+
+* Add compatibility for member names that include named arguments.
+
+## 1.0.4
+
+* Add compatibility for Dart 1.10-style name munging.
+
+## 1.0.3
+
+* Prefer "dart:" URLs to "package:" URLs.
+
+## 1.0.2
+
+* Fix an off-by-one bug that was causing line numbers to be slightly off.
+
+## 1.0.1
+
+* Don't crash when mapping stack chains.
+
+## 1.0.0
+
+* Initial release.
diff --git a/pkgs/source_map_stack_trace/LICENSE b/pkgs/source_map_stack_trace/LICENSE
new file mode 100644
index 0000000..633672a
--- /dev/null
+++ b/pkgs/source_map_stack_trace/LICENSE
@@ -0,0 +1,27 @@
+Copyright 2015, the Dart project authors.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+    * Redistributions of source code must retain the above copyright
+      notice, this list of conditions and the following disclaimer.
+    * Redistributions in binary form must reproduce the above
+      copyright notice, this list of conditions and the following
+      disclaimer in the documentation and/or other materials provided
+      with the distribution.
+    * Neither the name of Google LLC nor the names of its
+      contributors may be used to endorse or promote products derived
+      from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
diff --git a/pkgs/source_map_stack_trace/README.md b/pkgs/source_map_stack_trace/README.md
new file mode 100644
index 0000000..9b11612
--- /dev/null
+++ b/pkgs/source_map_stack_trace/README.md
@@ -0,0 +1,50 @@
+[![Dart CI](https://github.com/dart-lang/tools/actions/workflows/source_map_stack_trace.yml/badge.svg)](https://github.com/dart-lang/tools/actions/workflows/source_map_stack_trace.yml)
+[![pub package](https://img.shields.io/pub/v/source_map_stack_trace.svg)](https://pub.dev/packages/source_map_stack_trace)
+[![package publisher](https://img.shields.io/pub/publisher/source_map_stack_trace.svg)](https://pub.dev/packages/source_map_stack_trace/publisher)
+
+`source_map_stack_trace` is a package for converting stack traces generated by
+dart2js-compiled JavaScript code into readable native Dart stack traces using
+source maps. For example:
+
+```dart
+import 'package:source_map_stack_trace/source_map_stack_trace.dart';
+
+void main() {
+  var jsTrace = // Get a StackTrace generated by dart2js.
+  var mapping = // Get a source map mapping the JS to the Dart source.
+
+  // Convert jsTrace to refer to the Dart source instead.
+  var dartTrace = mapStackTrace(jsTrace, sourceMap);
+  print(dartTrace);
+}
+```
+
+This can convert the following JavaScript trace:
+
+```
+expect_async_test.dart.browser_test.dart.js 2636:15   dart.wrapException
+expect_async_test.dart.browser_test.dart.js 14661:15  main__closure16.call$0
+expect_async_test.dart.browser_test.dart.js 18237:26  Declarer_test__closure.call$1
+expect_async_test.dart.browser_test.dart.js 17905:23  StackZoneSpecification_registerUnaryCallback__closure.call$0
+expect_async_test.dart.browser_test.dart.js 17876:16  StackZoneSpecification._stack_zone_specification$_run$2
+expect_async_test.dart.browser_test.dart.js 17899:26  StackZoneSpecification_registerUnaryCallback_closure.call$1
+expect_async_test.dart.browser_test.dart.js 6115:16   _rootRunUnary
+expect_async_test.dart.browser_test.dart.js 8576:39   _CustomZone.runUnary$2
+expect_async_test.dart.browser_test.dart.js 7135:57   _Future__propagateToListeners_handleValueCallback.call$0
+expect_async_test.dart.browser_test.dart.js 7031:147  dart._Future.static._Future__propagateToListeners
+```
+
+to:
+
+```
+dart:_internal/compiler/js_lib/js_helper.dart 1210:1          wrapException
+test/frontend/expect_async_test.dart 24:5                     main.<fn>.<fn>
+package:test/src/backend/declarer.dart 45:48                  Declarer.test.<fn>.<fn>
+package:stack_trace/src/stack_zone_specification.dart 134:30  StackZoneSpecification.registerUnaryCallback.<fn>.<fn>
+package:stack_trace/src/stack_zone_specification.dart 210:7   StackZoneSpecification._run
+package:stack_trace/src/stack_zone_specification.dart 135:5   StackZoneSpecification.registerUnaryCallback.<fn>
+dart:async/zone.dart 904:14                                   _rootRunUnary
+dart:async/zone.dart 806:3                                    _CustomZone.runUnary
+dart:async/future_impl.dart 486:13                            _Future._propagateToListeners.handleValueCallback
+dart:async/future_impl.dart 567:32                            _Future._propagateToListeners
+```
diff --git a/pkgs/source_map_stack_trace/analysis_options.yaml b/pkgs/source_map_stack_trace/analysis_options.yaml
new file mode 100644
index 0000000..5ee158a
--- /dev/null
+++ b/pkgs/source_map_stack_trace/analysis_options.yaml
@@ -0,0 +1,7 @@
+# https://dart.dev/tools/analysis#the-analysis-options-file
+include: package:dart_flutter_team_lints/analysis_options.yaml
+
+analyzer:
+  language:
+    strict-casts: true
+    strict-raw-types: true
diff --git a/pkgs/source_map_stack_trace/lib/source_map_stack_trace.dart b/pkgs/source_map_stack_trace/lib/source_map_stack_trace.dart
new file mode 100644
index 0000000..a3925cd
--- /dev/null
+++ b/pkgs/source_map_stack_trace/lib/source_map_stack_trace.dart
@@ -0,0 +1,104 @@
+// Copyright (c) 2015, 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.
+
+import 'package:path/path.dart' as p;
+import 'package:source_maps/source_maps.dart';
+import 'package:stack_trace/stack_trace.dart';
+
+/// Convert [stackTrace], a stack trace generated by dart2js-compiled
+/// JavaScript, to a native-looking stack trace using [sourceMap].
+///
+/// [minified] indicates whether or not the dart2js code was minified. If it
+/// hasn't, this tries to clean up the stack frame member names.
+///
+/// The [packageMap] maps package names to the base uri used to resolve the
+/// `package:` uris for those packages. It is used to  it's used to reconstruct
+/// `package:` URIs for stack frames that come from packages.
+///
+/// [sdkRoot] is the URI surfaced in the stack traces for SDK libraries.
+/// If it's passed, stack frames from the SDK will have `dart:` URLs.
+StackTrace mapStackTrace(Mapping sourceMap, StackTrace stackTrace,
+    {bool minified = false, Map<String, Uri>? packageMap, Uri? sdkRoot}) {
+  if (stackTrace is Chain) {
+    return Chain(stackTrace.traces.map((trace) {
+      return Trace.from(mapStackTrace(sourceMap, trace,
+          minified: minified, packageMap: packageMap, sdkRoot: sdkRoot));
+    }));
+  }
+
+  var sdkLib = sdkRoot == null ? null : '$sdkRoot/lib';
+
+  var trace = Trace.from(stackTrace);
+  return Trace(trace.frames.map((frame) {
+    var line = frame.line;
+    // If there's no line information, there's no way to translate this frame.
+    // We could return it as-is, but these lines are usually not useful anyways.
+    if (line == null) return null;
+
+    // If there's no column, try using the first column of the line.
+    var column = frame.column ?? 0;
+
+    // Subtract 1 because stack traces use 1-indexed lines and columns and
+    // source maps uses 0-indexed.
+    var span =
+        sourceMap.spanFor(line - 1, column - 1, uri: frame.uri.toString());
+
+    // If we can't find a source span, ignore the frame. It's probably something
+    // internal that the user doesn't care about.
+    if (span == null) return null;
+
+    var sourceUrl = span.sourceUrl.toString();
+    if (sdkLib != null && p.url.isWithin(sdkLib, sourceUrl)) {
+      sourceUrl = 'dart:${p.url.relative(sourceUrl, from: sdkLib)}';
+    } else if (packageMap != null) {
+      for (var package in packageMap.keys) {
+        var packageUrl = packageMap[package].toString();
+        if (!p.url.isWithin(packageUrl, sourceUrl)) continue;
+
+        sourceUrl =
+            'package:$package/${p.url.relative(sourceUrl, from: packageUrl)}';
+        break;
+      }
+    }
+
+    return Frame(
+        Uri.parse(sourceUrl),
+        span.start.line + 1,
+        span.start.column + 1,
+        // If the dart2js output is minified, there's no use trying to prettify
+        // its member names. Use the span's identifier if available, otherwise
+        // use the minified member name.
+        minified
+            ? (span.isIdentifier ? span.text : frame.member)
+            : _prettifyMember(frame.member!));
+  }).whereType<Frame>());
+}
+
+/// Reformats a JS member name to make it look more Dart-like.
+String _prettifyMember(String member) {
+  return member
+      // Get rid of the noise that Firefox sometimes adds.
+      .replaceAll(RegExp(r'/?<$'), '')
+      // Get rid of arity indicators and named arguments.
+      .replaceAll(RegExp(r'\$\d+(\$[a-zA-Z_0-9]+)*$'), '')
+      // Convert closures to <fn>.
+      .replaceAllMapped(
+          RegExp(r'(_+)closure\d*\.call$'),
+          // The number of underscores before "closure" indicates how nested it
+          // is.
+          (match) => '.<fn>' * match[1]!.length)
+      // Get rid of explicitly-generated calls.
+      .replaceAll(RegExp(r'\.call$'), '')
+      // Get rid of the top-level method prefix.
+      .replaceAll(RegExp(r'^dart\.'), '')
+      // Get rid of library namespaces.
+      .replaceAll(RegExp(r'[a-zA-Z_0-9]+\$'), '')
+      // Get rid of the static method prefix. The class name also exists in the
+      // invocation, so we're not getting rid of any information.
+      .replaceAll(RegExp(r'^[a-zA-Z_0-9]+.(static|dart).'), '')
+      // Convert underscores after identifiers to dots. This runs the risk of
+      // incorrectly converting members that contain underscores, but those are
+      // contrary to the style guide anyway.
+      .replaceAllMapped(RegExp(r'([a-zA-Z0-9]+)_'), (match) => '${match[1]!}.');
+}
diff --git a/pkgs/source_map_stack_trace/pubspec.yaml b/pkgs/source_map_stack_trace/pubspec.yaml
new file mode 100644
index 0000000..d4b8c3a
--- /dev/null
+++ b/pkgs/source_map_stack_trace/pubspec.yaml
@@ -0,0 +1,17 @@
+name: source_map_stack_trace
+version: 2.1.3-wip
+description: A package for applying source maps to stack traces.
+repository: https://github.com/dart-lang/tools/tree/main/pkgs/source_map_stack_trace
+
+environment:
+  sdk: ^3.3.0
+
+dependencies:
+  path: ^1.8.0
+  source_maps: ^0.10.10
+  stack_trace: ^1.10.0
+
+dev_dependencies:
+  dart_flutter_team_lints: ^3.0.0
+  source_span: ^1.8.0
+  test: ^1.16.0
diff --git a/pkgs/source_map_stack_trace/test/source_map_stack_trace_test.dart b/pkgs/source_map_stack_trace/test/source_map_stack_trace_test.dart
new file mode 100644
index 0000000..dd4d710
--- /dev/null
+++ b/pkgs/source_map_stack_trace/test/source_map_stack_trace_test.dart
@@ -0,0 +1,264 @@
+// Copyright (c) 2015, 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.
+
+import 'package:path/path.dart' as p;
+import 'package:source_map_stack_trace/source_map_stack_trace.dart';
+import 'package:source_maps/source_maps.dart';
+import 'package:source_span/source_span.dart';
+import 'package:stack_trace/stack_trace.dart';
+import 'package:test/test.dart';
+
+/// A simple [Mapping] for tests that don't need anything special.
+final _simpleMapping = parseJson((SourceMapBuilder()
+      ..addSpan(
+          SourceMapSpan.identifier(
+              SourceLocation(1, line: 1, column: 3, sourceUrl: 'foo.dart'),
+              'qux'),
+          SourceSpan(SourceLocation(8, line: 5, column: 0),
+              SourceLocation(18, line: 15, column: 0), '\n' * 10)))
+    .build('foo.dart.js.map'));
+
+final _packageMap = {
+  'bar': Uri.parse('packages/bar'),
+  'foo': Uri.parse('packages/foo'),
+};
+
+void main() {
+  test('maps a JS line and column to a Dart line and span', () {
+    var trace = Trace.parse('foo.dart.js 10:11  foo');
+    var frame = _mapTrace(_simpleMapping, trace).frames.first;
+    expect(frame.uri, equals(Uri.parse('foo.dart')));
+
+    // These are +1 because stack_trace is 1-based whereas source_span is
+    // 0-basd.
+    expect(frame.line, equals(2));
+    expect(frame.column, equals(4));
+  });
+
+  test('ignores JS frames without line info', () {
+    var trace = Trace.parse('''
+foo.dart.js 10:11  foo
+foo.dart.js        bar
+foo.dart.js 10:11  baz
+''');
+    var frames = _mapTrace(_simpleMapping, trace).frames;
+
+    expect(frames.length, equals(2));
+    expect(frames.first.member, equals('foo'));
+    expect(frames.last.member, equals('baz'));
+  });
+
+  test('ignores JS frames without corresponding spans', () {
+    var trace = Trace.parse('''
+foo.dart.js 10:11  foo
+foo.dart.js 1:1   bar
+foo.dart.js 10:11  baz
+''');
+
+    var frames = _mapTrace(_simpleMapping, trace).frames;
+
+    expect(frames.length, equals(2));
+    expect(frames.first.member, equals('foo'));
+    expect(frames.last.member, equals('baz'));
+  });
+
+  test('include frames from JS files not covered by the source map bundle', () {
+    var trace = Trace.parse('''
+foo.dart.js 10:11  foo
+jquery.js 10:1  foo
+bar.dart.js 10:11  foo
+''');
+    var builder = SourceMapBuilder()
+      ..addSpan(
+          SourceMapSpan.identifier(
+              SourceLocation(1,
+                  line: 1, column: 3, sourceUrl: 'packages/foo/foo.dart'),
+              'qux'),
+          SourceSpan(SourceLocation(8, line: 5, column: 0),
+              SourceLocation(12, line: 9, column: 1), '\n' * 4));
+    var sourceMapJson1 = builder.build('foo.dart.js.map');
+    sourceMapJson1['file'] = 'foo.dart.js';
+
+    builder = SourceMapBuilder()
+      ..addSpan(
+          SourceMapSpan.identifier(
+              SourceLocation(1,
+                  line: 1, column: 3, sourceUrl: 'packages/bar/bar.dart'),
+              'qux'),
+          SourceSpan(SourceLocation(8, line: 5, column: 0),
+              SourceLocation(12, line: 9, column: 1), '\n' * 4));
+    var sourceMapJson2 = builder.build('bar.dart.js.map');
+    sourceMapJson2['file'] = 'bar.dart.js';
+
+    var bundle = [sourceMapJson1, sourceMapJson2];
+    var mapping = parseJsonExtended(bundle);
+    var frames = _mapTrace(mapping, trace, packageMap: _packageMap).frames;
+
+    expect(frames.length, equals(3));
+
+    var frame = frames[0];
+    expect(frame.uri, equals(Uri.parse('package:foo/foo.dart')));
+    expect(frame.line, equals(2));
+    expect(frame.column, equals(4));
+
+    frame = frames[1];
+    expect(p.basename(frame.uri.toString()), equals('jquery.js'));
+    expect(frame.line, equals(10));
+
+    frame = frames[2];
+    expect(frame.uri, equals(Uri.parse('package:bar/bar.dart')));
+    expect(frame.line, equals(2));
+    expect(frame.column, equals(4));
+  });
+
+  test('falls back to column 0 for unlisted column', () {
+    var trace = Trace.parse('foo.dart.js 10  foo');
+    var builder = SourceMapBuilder()
+      ..addSpan(
+          SourceMapSpan.identifier(
+              SourceLocation(1, line: 1, column: 3, sourceUrl: 'foo.dart'),
+              'qux'),
+          SourceSpan(SourceLocation(8, line: 5, column: 0),
+              SourceLocation(12, line: 9, column: 1), '\n' * 4));
+
+    var mapping = parseJson(builder.build('foo.dart.js.map'));
+    var frame = _mapTrace(mapping, trace).frames.first;
+    expect(frame.uri, equals(Uri.parse('foo.dart')));
+    expect(frame.line, equals(2));
+    expect(frame.column, equals(4));
+  });
+
+  test('uses package: URIs for frames within a packageResolver.packageMap URL',
+      () {
+    var trace = Trace.parse('foo.dart.js 10  foo');
+    var builder = SourceMapBuilder()
+      ..addSpan(
+          SourceMapSpan.identifier(
+              SourceLocation(1,
+                  line: 1, column: 3, sourceUrl: 'packages/foo/foo.dart'),
+              'qux'),
+          SourceSpan(SourceLocation(8, line: 5, column: 0),
+              SourceLocation(12, line: 9, column: 1), '\n' * 4));
+
+    var mapping = parseJson(builder.build('foo.dart.js.map'));
+    var mappedTrace = _mapTrace(mapping, trace, packageMap: _packageMap);
+    var frame = mappedTrace.frames.first;
+    expect(frame.uri, equals(Uri.parse('package:foo/foo.dart')));
+    expect(frame.line, equals(2));
+    expect(frame.column, equals(4));
+  });
+
+  test('uses dart: URIs for frames within sdkRoot', () {
+    var trace = Trace.parse('foo.dart.js 10  foo');
+    var builder = SourceMapBuilder()
+      ..addSpan(
+          SourceMapSpan.identifier(
+              SourceLocation(1,
+                  line: 1, column: 3, sourceUrl: 'sdk/lib/async/foo.dart'),
+              'qux'),
+          SourceSpan(SourceLocation(8, line: 5, column: 0),
+              SourceLocation(12, line: 9, column: 1), '\n' * 4));
+
+    var mapping = parseJson(builder.build('foo.dart.js.map'));
+    var frame =
+        _mapTrace(mapping, trace, sdkRoot: Uri.parse('sdk/')).frames.first;
+    expect(frame.uri, equals(Uri.parse('dart:async/foo.dart')));
+    expect(frame.line, equals(2));
+    expect(frame.column, equals(4));
+  });
+
+  test('converts a stack chain', () {
+    var trace = Chain([
+      Trace.parse('foo.dart.js 10:11  foo'),
+      Trace.parse('foo.dart.js 10:11  bar')
+    ]);
+    var traces = _mapChain(_simpleMapping, trace).traces;
+
+    var frame = traces.first.frames.single;
+    expect(frame.uri, equals(Uri.parse('foo.dart')));
+    expect(frame.member, equals('foo'));
+    expect(frame.line, equals(2));
+    expect(frame.column, equals(4));
+
+    frame = traces.last.frames.single;
+    expect(frame.uri, equals(Uri.parse('foo.dart')));
+    expect(frame.member, equals('bar'));
+    expect(frame.line, equals(2));
+    expect(frame.column, equals(4));
+  });
+
+  group('cleans up', () {
+    test('Firefox junk', () {
+      expect(_prettify('foo/<'), equals('foo'));
+      expect(_prettify('foo<'), equals('foo'));
+    });
+
+    test('arity indicators', () {
+      expect(_prettify(r'foo$1'), equals('foo'));
+      expect(_prettify(r'foo$1234'), equals('foo'));
+    });
+
+    test('named arguments', () {
+      expect(_prettify(r'foo$1$bar'), equals('foo'));
+      expect(_prettify(r'foo$123$bar$bang$qux'), equals('foo'));
+    });
+
+    test('closures', () {
+      expect(_prettify('foo_closure.call'), equals('foo.<fn>'));
+    });
+
+    test('nested closures', () {
+      expect(_prettify('foo__closure.call'), equals('foo.<fn>.<fn>'));
+      expect(
+          _prettify('foo____closure.call'), equals('foo.<fn>.<fn>.<fn>.<fn>'));
+    });
+
+    test('.call', () {
+      expect(_prettify('foo.call'), equals('foo'));
+    });
+
+    test('top-level functions', () {
+      expect(_prettify('dart.foo'), equals('foo'));
+    });
+
+    test('library namespaces', () {
+      expect(_prettify(r'my_library$foo'), equals('foo'));
+    });
+
+    test('static methods', () {
+      expect(_prettify(r'Foo.static.foo'), equals('foo'));
+    });
+
+    test('instance methods', () {
+      expect(_prettify(r'Foo_bar__baz'), equals('Foo.bar._baz'));
+    });
+
+    test('lots of stuff', () {
+      expect(_prettify(r'lib$Foo.static.lib$Foo_closure.call$0/<'),
+          equals('Foo.<fn>'));
+    });
+  });
+}
+
+/// Like [mapStackTrace], but is guaranteed to return a [Trace] so it can be
+/// inspected.
+Trace _mapTrace(Mapping sourceMap, StackTrace stackTrace,
+    {bool minified = false, Map<String, Uri>? packageMap, Uri? sdkRoot}) {
+  return Trace.from(mapStackTrace(sourceMap, stackTrace,
+      minified: minified, packageMap: packageMap, sdkRoot: sdkRoot));
+}
+
+/// Like [mapStackTrace], but is guaranteed to return a [Chain] so it can be
+/// inspected.
+Chain _mapChain(Mapping sourceMap, StackTrace stackTrace,
+    {bool minified = false, Map<String, Uri>? packageMap, Uri? sdkRoot}) {
+  return Chain.forTrace(mapStackTrace(sourceMap, stackTrace,
+      minified: minified, packageMap: packageMap, sdkRoot: sdkRoot));
+}
+
+/// Runs the mapper's prettification logic on [member] and returns the result.
+String? _prettify(String member) {
+  var trace = Trace([Frame(Uri.parse('foo.dart.js'), 10, 11, member)]);
+  return _mapTrace(_simpleMapping, trace).frames.first.member;
+}
diff --git a/pkgs/unified_analytics/.gitignore b/pkgs/unified_analytics/.gitignore
new file mode 100644
index 0000000..9377e38
--- /dev/null
+++ b/pkgs/unified_analytics/.gitignore
@@ -0,0 +1,14 @@
+# Files and directories created by pub.
+.dart_tool/
+.packages
+
+# Conventional directory for build outputs.
+build/
+
+# Omit committing pubspec.lock for library packages; see
+# https://dart.dev/guides/libraries/private-files#pubspeclock.
+pubspec.lock
+
+.vscode/
+coverage/
+*.DS_Store
diff --git a/pkgs/unified_analytics/CHANGELOG.md b/pkgs/unified_analytics/CHANGELOG.md
new file mode 100644
index 0000000..86d0110
--- /dev/null
+++ b/pkgs/unified_analytics/CHANGELOG.md
@@ -0,0 +1,173 @@
+## 6.1.4
+
+- Fix formatting and remove dependency on `package:intl`.
+- Remove direct usage of `package:path` in favor of `package:file`.
+- Added `androidAppId` and `iosBundleId` to the `Event.devtoolsEvent` constructor.
+
+## 6.1.3
+
+- Require Dart 3.4.
+- Added `isWasm` parameter to the `Event.devtoolsEvent` constructor.
+- Added an optional parameter `data` to the `Event.exception` constructor.
+
+## 6.1.2
+
+- Avoid opening large telemetry log files to prevent out of memory errors.
+
+## 6.1.1
+
+- Fixed bug where calling `Analytics.send` could result in a `FileSystemException` when unable to write to a log file.
+
+## 6.1.0
+
+- Added new event constructor `Event.devtoolsEvent` for the single devtools event with a new enum value `DashEvent.devtoolsEvent`
+
+## 6.0.0
+
+- Consolidate `Session` functionality into `UserProperty` to prevent race condition crash where session logic crashed before initializing `UserProperty`
+- Get rid of `late` variables throughout implementation class, `AnalyticsImpl`
+- Any error events (`Event.analyticsException`) encountered within package will be sent when invoking `Analytics.close`; replacing `ErrorHandler` functionality
+- Exposing new method for `FakeAnalytics.sendPendingErrorEvents` to send error events on command
+- Added `Event.fromJson` static method to generate instance of `Event` from JSON
+- Remove unused parameters `measurementId` and `apiSecret` from the `Analytics.test` constructor
+- Remove `Analytics.test` factory constructor in favor of `Analytics.fake` static method to return a `FakeAnalytics` instance
+- Remove `FakeAnalytics` default constructor in favor of `Analytics.fake`
+
+## 5.8.8
+
+- [Bug fix](https://github.com/dart-lang/tools/issues/252) rewrite the other call site for the session file
+
+## 5.8.7
+
+- [Bug fix](https://github.com/dart-lang/tools/issues/252) to rewrite the `last_ping` key into the session json file
+
+## 5.8.6
+
+- Refactored session handler class to use the last modified timestamp as the last ping value to prevent writing to file with each send
+- Bumping intl package to 0.19.0 to fix version solving issue with flutter_tools
+
+## 5.8.5
+
+- Fix late initialization error for `Analytics.userProperty` [bug](https://github.com/dart-lang/tools/issues/238)
+
+## 5.8.4
+
+- Exporting all enums from [`enums.dart`](https://github.com/dart-lang/tools/blob/main/pkgs/unified_analytics/lib/src/enums.dart) through `lib/testing.dart`
+
+## 5.8.3
+
+- [Fix bug](https://github.com/flutter/flutter/issues/143792) when parsing session json file
+
+## 5.8.2
+
+- Added new event `Event.analyticsException` to track internal errors for this package
+- Redirecting the `Analytics.test` factory to return an instance of `FakeAnalytics`
+- Exposing new helper function that can be used to parse the Dart SDK version
+
+## 5.8.1
+
+- Refactor logic for `okToSend` and `shouldShowMessage`
+- Check devtools config file for legacy opt out status
+
+## 5.8.0
+
+- Fix template string for consent message
+- Add `enabledFeatures` to constructor to collect features enabled for each dash tool
+
+## 5.7.0
+
+- Added the `Event.commandUsageValues` constructor
+
+## 5.6.0
+
+- Added the `Event.timing` constructor
+
+## 5.5.0
+
+- Edit to the `Event.flutterCommandResult` constructor to add `commandHasTerminal`
+- Added timeout for `Analytics.setTelemetry` to prevent the clients from hanging
+- Added the `Event.appleUsageEvent` constructor
+- Added the `Event.exception` constructor
+
+## 5.4.0
+
+- Added the `Event.codeSizeAnalysis` constructor
+
+## 5.3.0
+
+- User property "host_os_version" added to provide detail version information about the host
+- User property "locale" added to provide language related information
+- User property "client_ide" (optional) added to provide the IDE used by the Dash tool using this package, if applicable
+- Added the `Event.flutterCommandResult` constructor
+
+## 5.2.0
+
+- Added the `Event.hotRunnerInfo` constructor
+
+## 5.1.0
+
+- Added the `Event.flutterBuildInfo` constructor
+
+## 5.0.0
+
+- Update to the latest version of `package:dart_flutter_team_lints`
+- Using internal futures list to store send events
+- Added the `Event.doctorValidatorResult` constructor
+
+## 4.0.1
+
+- Adding constant for the NoOpAnalytics instance client ID to enable clients to reference it in tests
+
+## 4.0.0
+
+- Enhanced `LogFileStats` data to include information about flutter channel counts and tool counts
+- Added new method to suppress telemetry collection temporarily for current invocation via `analytics.suppressTelemetry()`
+- Added `SurveyHandler` feature to `Analytics` instance to fetch available surveys from remote endpoint to display to users along with functionality to dismiss them
+- Surveys will be disabled for any users that have been opted out
+- Shipping `FakeAnalytics` for clients of this tool that need to ensure workflows are sending events in tests
+- Adding getter to `Analytics` instance to fetch the client ID being sent to GA4
+
+## 3.0.0
+
+- Allow latest package versions for `file` and `http`
+- Introducing new `Event` class that will standardize what event data can be sent with each event
+- Deprecating the `sendEvent` method in favor of the `send` method
+
+## 2.0.0
+
+- Refactoring `dateStamp` utility function to be defined in `utils.dart` instead of having static methods in `Initializer` and `ConfigHandler`
+- Remove the `pddFlag` now that the revisions to the PDD have been finalized to persist data in the log file and session json file
+- Opting out will now delete the contents of the CLIENT ID, session json, and log files; opting back in will regenerate them as events send
+- `enableAsserts` parameter added to constructors for `Analytics` to check body of POST request for Google Analytics 4 limitations
+- Now checking if write permissions are enabled for user's home directory, if not allowed, `NoOpAnalytics` returned by `Analytics` factory constructor
+
+## 1.1.0
+
+- Added a `okToSend` getter so that clients can easily and accurately check the state of the consent mechanism.
+- Initialize the config file with user opted out if user was opted out in legacy Flutter and Dart analytics
+
+## 1.0.1
+
+- Error handling on the `analytics.sendEvent(...)` method to silently error out and return a `500` http status code to let tools using this package know Google Analytics did not receive the event (all successful requests will have a status code of `2xx` provided by Google Analytics)
+
+## 1.0.0
+
+- Error handling functionality added to prevent malformed session json data from causing a crash
+- Creating a new analytics constructor to point to a test instance of Google Analytics for developers
+- Align supported tool list with PDD
+- Exposing a new instance method that will need to be invoked when a client has successfully shown the consent message to the user `clientShowedMessage()`
+- Adding and incrementing a tool's version will automatically use the current consent message version instead of incrementing by 1
+- Default constructor has disabled the usage of local log file and session json file until revisions have landed to the privacy document
+
+## 0.1.2
+
+- Implemented fake Google Analytics Client for `Analytics.test(...)` constructor; marked with visible for testing annotation
+
+## 0.1.1
+
+- Bumping intl package to 0.18.0 to fix version solving issue with flutter_tools
+- LogFileStats includes more information about how many events are persisted and total count of how many times each event was sent
+
+## 0.1.0
+
+- Initial version
diff --git a/pkgs/unified_analytics/LICENSE b/pkgs/unified_analytics/LICENSE
new file mode 100644
index 0000000..ac90031
--- /dev/null
+++ b/pkgs/unified_analytics/LICENSE
@@ -0,0 +1,27 @@
+Copyright 2023, the Dart project authors.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+    * Redistributions of source code must retain the above copyright
+      notice, this list of conditions and the following disclaimer.
+    * Redistributions in binary form must reproduce the above
+      copyright notice, this list of conditions and the following
+      disclaimer in the documentation and/or other materials provided
+      with the distribution.
+    * Neither the name of Google LLC nor the names of its
+      contributors may be used to endorse or promote products derived
+      from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
\ No newline at end of file
diff --git a/pkgs/unified_analytics/README.md b/pkgs/unified_analytics/README.md
new file mode 100644
index 0000000..4263cfb
--- /dev/null
+++ b/pkgs/unified_analytics/README.md
@@ -0,0 +1,17 @@
+[![package:unified_analytics](https://github.com/dart-lang/tools/actions/workflows/unified_analytics.yml/badge.svg)](https://github.com/dart-lang/tools/actions/workflows/unified_analytics.yml)
+[![pub package](https://img.shields.io/pub/v/unified_analytics.svg)](https://pub.dev/packages/unified_analytics)
+[![package publisher](https://img.shields.io/pub/publisher/unified_analytics.svg)](https://pub.dev/packages/unified_analytics/publisher)
+
+## What's this?
+
+This package is intended to be used on Dart and Flutter related
+tooling only. It provides APIs to send events to Google Analytics using the
+Measurement Protocol.
+
+This is not intended to be general purpose or consumed by the community. It is
+responsible for toggling analytics collection for related tooling on each
+developer's machine.
+
+## Using this package
+
+Refer to the [usage guide](USAGE_GUIDE.md).
diff --git a/pkgs/unified_analytics/USAGE_GUIDE.md b/pkgs/unified_analytics/USAGE_GUIDE.md
new file mode 100644
index 0000000..ef5bbea
--- /dev/null
+++ b/pkgs/unified_analytics/USAGE_GUIDE.md
@@ -0,0 +1,202 @@
+This package is intended to be used on Dart and Flutter related tooling only.
+It provides APIs to send events to Google Analytics using the Measurement Protocol.
+
+## Usage
+
+To get started using this package, import at the entrypoint dart file and
+initialize with the required parameters.
+
+The example file shows an end-to-end usage guide for using this package and
+can be referred to here [unified_analytics_example.dart](example/unified_analytics_example.dart).
+
+**IMPORTANT**: It is best practice to close the http client connection when finished
+sending events, otherwise, you may notice that the dart process hangs on exit. The example below
+shows how to handle closing the connection via `analytics.close()` method.
+
+[Link to documentation for http client's close method](https://pub.dev/documentation/http/latest/http/Client-class.html)
+
+
+## Opting In and Out of Analytics Collection
+
+It will be important for each tool to expose a trivial method to
+disabling or enabling analytics collection. Based on how the user interacts
+with the tool, this can be done through the CLI, IDE, etc. The tool will
+then pass a boolean to an API exposed by the package as shown below.
+
+```dart
+// Begin by initializing the class
+final Analytics analytics = Analytics(...);
+
+// The boolean below simulates the user deciding to opt-out
+// of Analytics collection
+final bool status = false;
+
+// Call the method to pass the boolean
+analytics.setTelemetry(status);
+```
+
+## Displaying Consent Message to Users
+
+When a user first uses any tool with this package enabled, the tool using
+this package will need to ensure that the user has seen the consent message.
+The tool using this package should check with the `Analytics` instance
+by invoking the `shouldShowMessage` getter. When this getter returns
+`true`, this means that the user has not been enrolled into analytics
+collection yet. It is at this point that the tool using this package will
+invoke the `getConsentMessage` getter to return a string to share with the
+user (each tool will have their own method of displaying the message
+through cli stdout, popup modal, etc.). Once the message has been shown,
+the tool using this package will need to confirm to the `Analytics` instance
+that it has shown the message; it is at this point that the user has
+officially been onboarded to analytics collection.
+
+
+
+```dart
+// Begin by initializing the class near the entrypoint
+final Analytics analytics = Analytics(...);
+
+// This conditional should always run; the first time it is run, this
+// will return true since the consent message has never been shown
+if (analytics.shouldShowMessage) {
+  
+  // Simulates displaying the message, this will vary from
+  // client to client; ie. stdout, popup in IDE, etc.
+  print(analytics.getConsentMessage);
+
+  // After receiving confirmation that the message has been
+  // displayed, invoking the below method will successfully
+  // onboard the tool into the config file and allow for
+  // events to be sent on the next creation of the analytics
+  // instance
+  analytics.clientShowedMessage();
+}
+```
+
+## Checking User Opt-In Status
+
+Some tools may need to know if the user has opted in for Analytics
+collection in order to enable additional functionality. The example below
+shows how to check the status.
+
+```dart
+// Begin by initializing the class
+final Analytics analytics = Analytics(...);
+
+// This getter will return a boolean showing the status;
+// print statement used for trivial usage example
+print('This user's status: ${analytics.telemetryEnabled}');  // true if opted-in
+```
+
+## Checking for New Versions of Consent Message
+
+In the event that the package consent messaging needs has been updated, an
+API has been exposed on an instance of `Analytics` that will notify the tool
+using this package whether to display the message again.
+
+```dart
+// Begin by initializing the class
+//
+// This is assuming that the tool has already been onboarded
+// and that the user has already seen the previous version of
+// the consent message
+final Analytics analytics = Analytics(...);
+
+
+// Much like the first example, if there is a new version of
+// the tools message that needs to be shown, use the same work
+// workflow
+if (analytics.shouldShowMessage) {
+  
+  // Simulates displaying the message, this will vary from
+  // client to client; ie. stdout, popup in IDE, etc.
+  print(analytics.getConsentMessage);
+
+  // After receiving confirmation that the message has been
+  // displayed, invoking the below method will successfully
+  // onboard the tool into the config file and allow for
+  // events to be sent on the next creation of the analytics
+  // instance
+  analytics.clientShowedMessage();
+}
+```
+
+It is important to note events will not be sent if there is a new version of
+the consent message.
+
+## Developing Within `package:unified_analytics`
+
+### Adding new data classes
+
+#### User properties
+In Google Analytics, new data fields can be collected as user properties 
+or events. 
+
+User properties are key-value pairs that can be used to segment users. For example, 
+the Flutter channel used. To request that a new user property 
+be added, file an issue [using this template](https://github.com/dart-lang/tools/issues/new?template=unified_analytics_user_property.yml). 
+
+To add a new user property, add a new property to the `UserProperty` class 
+in the [`user_property.dart` file](./lib/src/user_property.dart). 
+
+#### Events
+Events are actions that the user, or tool, performs. In Google Analytics, 
+events can have associated data. This event data is stored 
+in key-value pairs. 
+
+To request new events, or event data, file an issue 
+[using this template](https://github.com/dart-lang/tools/issues/new?template=unified_analytics_event.yml).
+
+To add a new event, create a new field in the `DashEvent` enum (if necessary) in
+the [`enums.dart` file](./lib/src/enums.dart). 
+
+Then, add event data, create a new constructor for the `Event` class 
+in the [`event.dart` file](./lib/src/event.dart).
+
+
+### Testing event collection
+
+When contributing to this package, if the developer needs to verify that
+events have been sent, the developer should the use development constructor
+so that the events being sent are not going into the production instance.
+
+```dart
+final Analytics analytics = Analytics.development(...);
+```
+
+Reach out to maintainers to get access to the test Google Analytics endpoint.
+
+## Advanced Usage: Querying Locally Persisted Logs
+
+This package enables  tools to persist the events that have been sent
+to Google Analytics for logging by default. This can be very helpful if
+tools would like to understand the user's activity level across all
+related tooling. For example, if querying the locally persisted logs
+shows that the user has not been active for N number of days, a tool that
+works within an IDE can prompt the user with a survey to understand why their
+level of activity has dropped.
+
+The snippet below shows how to invoke the query and a sample response.
+
+```dart
+// Begin by initializing the class
+final Analytics analytics = Analytics(...);
+
+// Printing the query results returns json formatted
+// string to view; data can also be accessed through
+// [LogFileStats] getters
+print(analytics.logFileStats());
+```
+Refer to the `LogFileStats` instance [variables](lib/src/log_handler.dart) for details on the result.
+
+Explanation of the each key above
+
+- startDateTime: the earliest event that was sent
+- minsFromStartDateTime: the number of minutes elapsed since the earliest message
+- endDateTime: the latest, most recent event that was sent
+- minsFromEndDateTime: the number of minutes elapsed since the latest message
+- sessionCount: count of sessions; sessions have a minimum time of 30 minutes
+- flutterChannelCount: count of flutter channels (can be 0 if developer is a Dart dev only)
+- toolCount: count of the Dart and Flutter tools sending analytics
+- recordCount: count of the total number of events in the log file
+- eventCount: counts each unique event and how many times they occurred in the log file
\ No newline at end of file
diff --git a/pkgs/unified_analytics/analysis_options.yaml b/pkgs/unified_analytics/analysis_options.yaml
new file mode 100644
index 0000000..746ad64
--- /dev/null
+++ b/pkgs/unified_analytics/analysis_options.yaml
@@ -0,0 +1,10 @@
+# This file configures the static analysis results for your project (errors,
+# warnings, and lints).
+
+include: package:dart_flutter_team_lints/analysis_options.yaml
+
+linter:
+  rules:
+    - avoid_catches_without_on_clauses
+    - prefer_final_in_for_each
+    - prefer_final_locals
diff --git a/pkgs/unified_analytics/coverage_runner.sh b/pkgs/unified_analytics/coverage_runner.sh
new file mode 100755
index 0000000..4043614
--- /dev/null
+++ b/pkgs/unified_analytics/coverage_runner.sh
@@ -0,0 +1,11 @@
+#!/bin/sh
+
+# Generate `coverage/lcov.info` file
+flutter test --coverage
+
+# Generate HTML report
+# Note: on macOS you need to have lcov installed on your system (`brew install lcov`) to use this:
+genhtml coverage/lcov.info -o coverage/html
+
+# Open the report
+open coverage/html/index.html
diff --git a/pkgs/unified_analytics/example/sample_rate.dart b/pkgs/unified_analytics/example/sample_rate.dart
new file mode 100644
index 0000000..51b0cdb
--- /dev/null
+++ b/pkgs/unified_analytics/example/sample_rate.dart
@@ -0,0 +1,90 @@
+// Copyright (c) 2023, 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.
+
+import 'package:unified_analytics/src/utils.dart';
+
+/// The purpose of this example file is to demonstrate the sampling
+/// rate functionality from the survey handler.
+///
+/// It defines a `remoteUniqueId` that subs in for a real survey's unique
+/// ID that is hosted in the remote json file.
+///
+/// Begin the simulation by setting the `testSampleRate` and `iterations`
+/// variables, where `iterations` simulates real users and `testSampleRate`
+/// represents a fraction of how many people should be sampled.
+///
+/// In this example, we have set the `testSampleRate` to `0.3`, meaning we want
+/// sample 30% of users, and `iterations` to `10,000`, which simulates `10,000`
+/// users.
+///
+/// Running the script with predefined seed of `123` will
+/// generate the below `stdout`
+/// ```
+/// Test sample rate = 0.3
+/// Number of iterations = 10000
+/// ---
+///
+/// Count of iterations sampled (successes) = 3046
+/// Actual sample rate = 0.3046
+/// ---
+///
+/// Runtime = 8ms
+/// ```
+///
+/// The actual results yielded 3,046 people selected for a rate
+/// of `30.46%` which is about the `30%` defined in `testSampleRate`.
+void main() {
+  // Seed has been set to replicate results
+  //
+  // Test with your own seed and alter other parameters
+  // as needed
+  final uuidGenerator = Uuid(123);
+
+  // Randomly generate an ID that will simulate being used for
+  // a given survey
+  final remoteUniqueId = uuidGenerator.generateV4();
+
+  // Define a sampling rate that we would like to test
+  //
+  // Setting 0.3 means any generated doubles less than or
+  // equal to 0.3 results in a survey getting delievered
+  const testSampleRate = 0.3;
+
+  // Define how many iterations to run, each iteration can
+  // be thought of as a developer using a dash tool
+  const iterations = 10000;
+
+  // Initializing a counter that will count the number of
+  // iterations that were below the sampling rate
+  var count = 0;
+
+  final start = DateTime.now();
+  for (var i = 0; i < iterations; i++) {
+    // Each newly generated ID is simulating a unique
+    // developer's CLIENT ID that is persisted on their disk
+    final clientId = uuidGenerator.generateV4();
+
+    // Generate a double that will be compared against the sampleRate
+    final generatedDouble = sampleRate(remoteUniqueId, clientId);
+
+    // Count successes if the generated double is less than our
+    // testing sample rate
+    if (generatedDouble <= testSampleRate) {
+      count++;
+    }
+  }
+  final end = DateTime.now();
+
+  print('''
+Test sample rate = $testSampleRate
+Number of iterations = $iterations
+---
+
+Count of iterations sampled (successes) = $count
+Actual sample rate = ${(count / iterations).toStringAsFixed(4)}
+---
+
+Runtime = ${end.difference(start).inMilliseconds}ms
+''');
+}
diff --git a/pkgs/unified_analytics/example/serving_surveys.dart b/pkgs/unified_analytics/example/serving_surveys.dart
new file mode 100644
index 0000000..d56339e
--- /dev/null
+++ b/pkgs/unified_analytics/example/serving_surveys.dart
@@ -0,0 +1,165 @@
+// Copyright (c) 2023, 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.
+
+import 'package:clock/clock.dart';
+import 'package:file/file.dart';
+import 'package:file/memory.dart';
+
+import 'package:unified_analytics/src/constants.dart';
+import 'package:unified_analytics/src/enums.dart';
+import 'package:unified_analytics/src/survey_handler.dart';
+import 'package:unified_analytics/unified_analytics.dart';
+
+/// This example code is intended to only be used as guidance for
+/// clients using this package. Clients using this package should avoid
+/// the use of the [Analytics.fake] static method.
+///
+/// It was used in this example file so that the real [FileSystem] was swapped
+/// out for a [MemoryFileSystem] so that repeated runs of this script yield
+/// the same results.
+void main() async {
+  late final MemoryFileSystem fs;
+  late final Analytics analytics;
+  late final Directory home;
+  // We need to initialize with a fake clock since the surveys have
+  // a period of time they are valid for
+  await withClock(Clock.fixed(DateTime(2023, 3, 3, 12, 0)), () async {
+    // Use a memory file system to repeatedly run this example
+    // file with the test instance
+    fs = MemoryFileSystem(style: FileSystemStyle.posix);
+    home = fs.directory('home');
+    home.createSync();
+
+    // The purpose of `initialAnalytics` is so that the tool is able to
+    // send events after its first run; this instance won't be used below
+    //
+    // ignore: invalid_use_of_visible_for_testing_member
+    final initialAnalytics = Analytics.fake(
+      tool: DashTool.flutterTool,
+      homeDirectory: home,
+      dartVersion: 'dartVersion',
+      fs: fs,
+      platform: DevicePlatform.macos,
+    );
+    // The below command allows `DashTool.flutterTool` to send telemetry
+    initialAnalytics.clientShowedMessage();
+
+    // ignore: invalid_use_of_visible_for_testing_member
+    analytics = Analytics.fake(
+        tool: DashTool.flutterTool,
+        homeDirectory: home,
+        dartVersion: 'dartVersion',
+        fs: fs,
+        platform: DevicePlatform.macos,
+        surveyHandler: FakeSurveyHandler.fromList(
+          dismissedSurveyFile: home
+              .childDirectory(kDartToolDirectoryName)
+              .childFile(kDismissedSurveyFileName),
+          initializedSurveys: [
+            Survey(
+              uniqueId: 'uniqueId',
+              startDate: DateTime(2023, 1, 1),
+              endDate: DateTime(2023, 5, 31),
+              description: 'description',
+              snoozeForMinutes: 10,
+              samplingRate: 1.0,
+              excludeDashToolList: [],
+              conditionList: [],
+              buttonList: [
+                SurveyButton(
+                  buttonText: 'View Survey',
+                  action: 'accept',
+                  promptRemainsVisible: false,
+                  url: 'http://example.com',
+                ),
+                SurveyButton(
+                  buttonText: 'More Info',
+                  action: 'snooze',
+                  promptRemainsVisible: true,
+                  url: 'http://example2.com',
+                ),
+                SurveyButton(
+                  buttonText: 'Dismiss Survey',
+                  action: 'dismiss',
+                  promptRemainsVisible: false,
+                )
+              ],
+            ),
+          ],
+        ));
+  });
+
+  // Each client of this package will be able to fetch all of
+  // the available surveys with the below method
+  //
+  // Sample rate will be applied automatically; it also won't
+  // fetch any surveys in the snooze period or if they have
+  // been dismissed
+  final surveyList = await analytics.fetchAvailableSurveys();
+  assert(surveyList.length == 1);
+
+  // Grab the first and only survey to simulate displaying it to a user
+  final survey = surveyList.first;
+  print('Simulating displaying the survey with a print below:');
+  print('Survey id: ${survey.uniqueId}\n');
+
+  // Immediately after displaying the survey, the method below
+  // should be run so that no other clients using this tool will show
+  // it at the same time
+  //
+  // It will "snoozed" when the below is run as well as reported to
+  // Google Analytics 4 that this survey was shown
+  analytics.surveyShown(survey);
+
+  // Get the file where this is persisted to show it getting updated
+  final persistedSurveyFile = home
+      .childDirectory(kDartToolDirectoryName)
+      .childFile(kDismissedSurveyFileName);
+  print('The contents of the json file '
+      'after invoking `analytics.surveyShown(survey);`');
+  print('${persistedSurveyFile.readAsStringSync()}\n');
+
+  // Change the index below to decide which button to simulate pressing
+  //
+  // 0 - accept
+  // 1 - snooze
+  // 2 - dismiss
+  final selectedButtonIndex = 1;
+  assert([0, 1, 2].contains(selectedButtonIndex));
+
+  // Get the survey button by index that will need to be passed along with
+  // the survey to simulate an interaction with the survey
+  final selectedSurveyButton = survey.buttonList[selectedButtonIndex];
+  print('The simulated button pressed was: '
+      '"${selectedSurveyButton.buttonText}" '
+      '(action = ${selectedSurveyButton.action})\n');
+
+  // The below method will handle whatever action the button
+  analytics.surveyInteracted(
+    survey: survey,
+    surveyButton: selectedSurveyButton,
+  );
+
+  // Conditional to check if there is a URl to route to
+  if (selectedSurveyButton.url != null) {
+    print('***This button also has a survey URL link '
+        'to route to at "${selectedSurveyButton.url}"***\n');
+  }
+
+  // Conditional to check what simulating a popup to stay up
+  if (selectedSurveyButton.promptRemainsVisible) {
+    print('***This button has its promptRemainsVisible field set to `true` '
+        'so this simulates what seeing a pop up again would look like***\n');
+  }
+
+  print('The contents of the json file '
+      'after invoking '
+      '`analytics.surveyInteracted(survey: survey, '
+      'surveyButton: selectedSurveyButton);`');
+  print('${persistedSurveyFile.readAsStringSync()}\n');
+
+  // Demonstrating that the survey doesn't get returned again
+  print('Attempting to fetch surveys again will result in an empty list');
+  print(await analytics.fetchAvailableSurveys());
+}
diff --git a/pkgs/unified_analytics/example/unified_analytics_example.dart b/pkgs/unified_analytics/example/unified_analytics_example.dart
new file mode 100644
index 0000000..e0ddaff
--- /dev/null
+++ b/pkgs/unified_analytics/example/unified_analytics_example.dart
@@ -0,0 +1,65 @@
+// Copyright (c) 2023, 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.
+
+import 'package:unified_analytics/unified_analytics.dart';
+
+// Globally instantiate the analytics class at the entry
+// point of the tool
+//
+// Development constructor used here so we don't push
+// to production when running
+final Analytics analytics = Analytics.development(
+  tool: DashTool.flutterTool,
+  flutterChannel: 'ey-test-channel',
+  flutterVersion: 'Flutter 3.6.0-7.0.pre.47',
+  clientIde: 'VSCode',
+  dartVersion: 'Dart 2.19.0',
+  // This can be set to true while testing to validate
+  // against GA4 usage limitations (character limits, etc.)
+  enableAsserts: false,
+  enabledFeatures: 'feature-1,feature-2',
+);
+
+// Timing a process and sending the event
+void main() async {
+  final start = DateTime.now();
+
+  // Each client using this package will have it's own
+  // method to show the message but the below is a trivial
+  // example of how to properly initialize the analytics instance
+  if (analytics.shouldShowMessage) {
+    // Simulates displaying the message, this will vary from
+    // client to client; ie. stdout, popup in IDE, etc.
+    print(analytics.getConsentMessage);
+
+    // After receiving confirmation that the message has been
+    // displayed, invoking the below method will successfully
+    // onboard the tool into the config file and allow for
+    // events to be sent on the next creation of the analytics
+    // instance
+    //
+    // The rest of the example below assumes that the tool has
+    // already been onboarded in a previous run
+    analytics.clientShowedMessage();
+  }
+
+  print('Current user ${analytics.clientId} '
+      'is opted in: ${analytics.telemetryEnabled}');
+
+  // Example of long running process
+  await Future<void>.delayed(const Duration(milliseconds: 100));
+
+  // Calculate the metric to send
+  final runTime = DateTime.now().difference(start).inMilliseconds;
+
+  // Create the event that will be sent for the hot reload time
+  // as an example
+  final hotReloadEvent = Event.hotReloadTime(timeMs: runTime);
+
+  // Make a call to the [Analytics] api to send the data
+  analytics.send(hotReloadEvent);
+
+  // Close the client connection on exit
+  await analytics.close();
+}
diff --git a/pkgs/unified_analytics/lib/src/analytics.dart b/pkgs/unified_analytics/lib/src/analytics.dart
new file mode 100644
index 0000000..cc8b4bc
--- /dev/null
+++ b/pkgs/unified_analytics/lib/src/analytics.dart
@@ -0,0 +1,857 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:io' as io;
+
+import 'package:file/file.dart';
+import 'package:file/local.dart';
+import 'package:file/memory.dart';
+import 'package:http/http.dart';
+import 'package:meta/meta.dart';
+
+import 'asserts.dart';
+import 'config_handler.dart';
+import 'constants.dart';
+import 'enums.dart';
+import 'event.dart';
+import 'ga_client.dart';
+import 'initializer.dart';
+import 'log_handler.dart';
+import 'survey_handler.dart';
+import 'user_property.dart';
+import 'utils.dart';
+
+abstract class Analytics {
+  /// The default factory constructor that will return an implementation
+  /// of the [Analytics] abstract class using the [LocalFileSystem].
+  ///
+  /// If [enableAsserts] is set to `true`, then asserts for GA4 limitations
+  /// will be enabled.
+  ///
+  /// [flutterChannel] and [flutterVersion] are nullable in case the client
+  /// using this package is unable to resolve those values.
+  ///
+  /// An optional parameter [clientIde] is also available for dart and flutter
+  /// tooling that are running from IDEs can be resolved. Such as "VSCode"
+  /// running the flutter-tool.
+  ///
+  /// [enabledFeatures] is also an optional field that can be added to collect
+  /// any features that are enabled for a user. For example,
+  /// "enable-linux-desktop,cli-animations" are two features that can be enabled
+  /// for the flutter-tool.
+  factory Analytics({
+    required DashTool tool,
+    required String dartVersion,
+    String? flutterChannel,
+    String? flutterVersion,
+    String? clientIde,
+    String? enabledFeatures,
+    bool enableAsserts = false,
+  }) {
+    // Create the instance of the file system so clients don't need
+    // resolve on their own
+    const FileSystem fs = LocalFileSystem();
+
+    // Ensure that the home directory has permissions enabled to write
+    final homeDirectory = getHomeDirectory(fs);
+    if (homeDirectory == null ||
+        !checkDirectoryForWritePermissions(homeDirectory)) {
+      return const NoOpAnalytics();
+    }
+
+    // Resolve the OS using dart:io
+    final DevicePlatform platform;
+    if (io.Platform.operatingSystem == 'linux') {
+      platform = DevicePlatform.linux;
+    } else if (io.Platform.operatingSystem == 'macos') {
+      platform = DevicePlatform.macos;
+    } else {
+      platform = DevicePlatform.windows;
+    }
+
+    // Create the instance of the GA Client which will create
+    // an [http.Client] to send requests
+    final gaClient = GAClient(
+      measurementId: kGoogleAnalyticsMeasurementId,
+      apiSecret: kGoogleAnalyticsApiSecret,
+    );
+
+    final firstRun = runInitialization(homeDirectory: homeDirectory);
+
+    return AnalyticsImpl(
+      tool: tool,
+      homeDirectory: homeDirectory,
+      flutterChannel: flutterChannel,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      platform: platform,
+      toolsMessageVersion: kToolsMessageVersion,
+      fs: fs,
+      gaClient: gaClient,
+      surveyHandler: SurveyHandler(
+        dismissedSurveyFile: homeDirectory
+            .childDirectory(kDartToolDirectoryName)
+            .childFile(kDismissedSurveyFileName),
+      ),
+      enableAsserts: enableAsserts,
+      clientIde: clientIde,
+      enabledFeatures: enabledFeatures,
+      firstRun: firstRun,
+    );
+  }
+
+  /// Factory constructor to return the [AnalyticsImpl] class with
+  /// Google Analytics credentials that point to a test instance and
+  /// not the production instance where live data will be sent.
+  ///
+  /// By default, [enableAsserts] is set to `true` to check against
+  /// GA4 limitations.
+  ///
+  /// [flutterChannel] and [flutterVersion] are nullable in case the client
+  /// using this package is unable to resolve those values.
+  factory Analytics.development({
+    required DashTool tool,
+    required String dartVersion,
+    String? flutterChannel,
+    String? flutterVersion,
+    String? clientIde,
+    String? enabledFeatures,
+    bool enableAsserts = true,
+  }) {
+    // Create the instance of the file system so clients don't need
+    // resolve on their own
+    const FileSystem fs = LocalFileSystem();
+
+    // Ensure that the home directory has permissions enabled to write
+    final homeDirectory = getHomeDirectory(fs);
+    if (homeDirectory == null) {
+      throw Exception('Unable to determine the home directory, '
+          'ensure it is available in the environment');
+    }
+    if (!checkDirectoryForWritePermissions(homeDirectory)) {
+      throw Exception('Permissions error on the home directory!');
+    }
+
+    // Resolve the OS using dart:io
+    final DevicePlatform platform;
+    if (io.Platform.operatingSystem == 'linux') {
+      platform = DevicePlatform.linux;
+    } else if (io.Platform.operatingSystem == 'macos') {
+      platform = DevicePlatform.macos;
+    } else {
+      platform = DevicePlatform.windows;
+    }
+
+    // Credentials defined below for the test Google Analytics instance
+    const kTestMeasurementId = 'G-N1NXG28J5B';
+    const kTestApiSecret = '4yT8__oER3Cd84dtx6r-_A';
+
+    // Create the instance of the GA Client which will create
+    // an [http.Client] to send requests
+    final gaClient = GAClient(
+      measurementId: kTestMeasurementId,
+      apiSecret: kTestApiSecret,
+    );
+
+    final firstRun = runInitialization(homeDirectory: homeDirectory);
+
+    return AnalyticsImpl(
+      tool: tool,
+      homeDirectory: homeDirectory,
+      flutterChannel: flutterChannel,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      platform: platform,
+      toolsMessageVersion: kToolsMessageVersion,
+      fs: fs,
+      gaClient: gaClient,
+      surveyHandler: SurveyHandler(
+        dismissedSurveyFile: homeDirectory
+            .childDirectory(kDartToolDirectoryName)
+            .childFile(kDismissedSurveyFileName),
+      ),
+      enableAsserts: enableAsserts,
+      clientIde: clientIde,
+      enabledFeatures: enabledFeatures,
+      firstRun: firstRun,
+    );
+  }
+
+  /// The shared identifier for Flutter and Dart related tooling using
+  /// package:unified_analytics.
+  String get clientId;
+
+  /// Retrieves the consent message to prompt users with on first
+  /// run or when the message has been updated.
+  String get getConsentMessage;
+
+  /// Returns true if it is OK to send an analytics message. Do not cache,
+  /// as this depends on factors that can change, such as the configuration
+  /// file contents.
+  bool get okToSend;
+
+  /// Returns a map object with all of the tools that have been parsed
+  /// out of the configuration file.
+  Map<String, ToolInfo> get parsedTools;
+
+  /// Boolean that lets the client know if they should display the message.
+  bool get shouldShowMessage;
+
+  /// Boolean indicating whether or not telemetry is enabled.
+  bool get telemetryEnabled;
+
+  /// Returns a map representation of the [UserProperty] for the [Analytics]
+  /// instance.
+  ///
+  /// This is what will get sent to Google Analytics with every request.
+  Map<String, Map<String, Object?>> get userPropertyMap;
+
+  /// Method to be invoked by the client using this package to confirm
+  /// that the client has shown the message and that it can be added to
+  /// the config file and start sending events the next time it starts up.
+  void clientShowedMessage();
+
+  /// Call this method when the tool using this package is closed.
+  ///
+  /// Prevents the tool from hanging when if there are still requests
+  /// that need to be sent off.
+  ///
+  /// Providing [delayDuration] in milliseconds will allow the instance
+  /// to wait the provided time before closing the http connection. Keeping
+  /// the connection open for some time will allow any pending events that
+  /// are waiting to be sent to the Google Analytics server. Default value
+  /// of 250 ms applied.
+  Future<void> close({int delayDuration = kDelayDuration});
+
+  /// Method to fetch surveys from the endpoint [kContextualSurveyUrl].
+  ///
+  /// Any survey that is returned by this method has already passed
+  /// the survey conditions specified in the remote survey metadata file.
+  ///
+  /// If the method returns an empty list, then there are no surveys to be
+  /// shared with the user.
+  Future<List<Survey>> fetchAvailableSurveys();
+
+  /// Query the persisted event data stored on the user's machine.
+  ///
+  /// Returns null if there are no persisted logs.
+  LogFileStats? logFileStats();
+
+  /// Send preconfigured events using specific named constructors
+  /// on the [Event] class.
+  ///
+  /// Example
+  /// ```dart
+  /// analytics.send(Event.memory(periodSec: 123));
+  /// ```
+  void send(Event event);
+
+  /// Pass a boolean to either enable or disable telemetry and make
+  /// the necessary changes in the persisted configuration file.
+  ///
+  /// Setting the telemetry status will also send an event to GA
+  /// indicating the latest status of the telemetry from [reportingBool].
+  Future<void> setTelemetry(bool reportingBool);
+
+  /// Calling this will result in telemetry collection being suppressed for
+  /// the current invocation.
+  ///
+  /// If you would like to permanently disable telemetry
+  /// collection use:
+  ///
+  /// ```dart
+  /// analytics.setTelemetry(false)
+  /// ```
+  void suppressTelemetry();
+
+  /// Method to run after interacting with a [Survey] instance.
+  ///
+  /// Pass a [Survey] instance which can be retrieved from
+  /// [Analytics.fetchAvailableSurveys].
+  ///
+  /// [surveyButton] is the button that was interacted with by the user.
+  void surveyInteracted({
+    required Survey survey,
+    required SurveyButton surveyButton,
+  });
+
+  /// Method to be called after a survey has been shown to the user.
+  ///
+  /// Calling this will snooze the survey so it won't be shown immediately.
+  ///
+  /// The snooze period is defined by the [Survey.snoozeForMinutes] field.
+  void surveyShown(Survey survey);
+
+  /// Returns an instance of [FakeAnalytics] which can be used in tests to check
+  /// for certain [Event] instances within [FakeAnalytics.sentEvents].
+  @visibleForTesting
+  static FakeAnalytics fake({
+    required DashTool tool,
+    required Directory homeDirectory,
+    required String dartVersion,
+    required MemoryFileSystem fs,
+    String? flutterChannel,
+    String? flutterVersion,
+    String? clientIde,
+    String? enabledFeatures,
+    SurveyHandler? surveyHandler,
+    GAClient? gaClient,
+    DevicePlatform platform = DevicePlatform.linux,
+    int toolsMessageVersion = kToolsMessageVersion,
+    String toolsMessage = kToolsMessage,
+    bool enableAsserts = true,
+  }) {
+    final firstRun = runInitialization(homeDirectory: homeDirectory);
+
+    return FakeAnalytics._(
+      tool: tool,
+      homeDirectory: homeDirectory,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      platform: platform,
+      fs: fs,
+      surveyHandler: surveyHandler ??
+          FakeSurveyHandler.fromList(
+            dismissedSurveyFile: homeDirectory
+                .childDirectory(kDartToolDirectoryName)
+                .childFile(kDismissedSurveyFileName),
+            initializedSurveys: [],
+          ),
+      gaClient: gaClient ?? const FakeGAClient(),
+      clientIde: clientIde,
+      enabledFeatures: enabledFeatures,
+      firstRun: firstRun,
+      enableAsserts: enableAsserts,
+    );
+  }
+}
+
+class AnalyticsImpl implements Analytics {
+  final DashTool tool;
+  final FileSystem fs;
+  final int toolsMessageVersion;
+  final ConfigHandler _configHandler;
+  final GAClient _gaClient;
+  final SurveyHandler _surveyHandler;
+  final File _clientIdFile;
+  final UserProperty _userProperty;
+  final LogHandler _logHandler;
+
+  /// Tells the client if they need to show a message to the
+  /// user; this will return true if it is the first time the
+  /// package is being used for a developer or if the consent
+  /// message has been updated by the package.
+  bool _showMessage = false;
+
+  /// When set to `true`, various assert statements will be enabled
+  /// to ensure usage of this class is within GA4 limitations.
+  final bool _enableAsserts;
+
+  /// Telemetry suppression flag that is set via [Analytics.suppressTelemetry].
+  bool _telemetrySuppressed = false;
+
+  /// Indicates if this is the first run for a given tool.
+  bool _firstRun = false;
+
+  /// The list of futures that will contain all of the send events
+  /// from the [GAClient].
+  final _futures = <Future<Response>>[];
+
+  /// Internal value for the client id which will be lazily loaded.
+  String? _clientId;
+
+  /// Internal collection of [Event]s that have been sent
+  /// for errors encountered within package:unified_analytics.
+  ///
+  /// Stores each of the events that have been sent to GA4 so that the
+  /// same error doesn't get sent twice.
+  final Set<Event> _sentErrorEvents = {};
+
+  AnalyticsImpl({
+    required this.tool,
+    required Directory homeDirectory,
+    required String? flutterChannel,
+    required String? flutterVersion,
+    required String? clientIde,
+    required String? enabledFeatures,
+    required String dartVersion,
+    required DevicePlatform platform,
+    required this.toolsMessageVersion,
+    required this.fs,
+    required GAClient gaClient,
+    required SurveyHandler surveyHandler,
+    required bool enableAsserts,
+    required bool firstRun,
+  })  : _gaClient = gaClient,
+        _surveyHandler = surveyHandler,
+        _enableAsserts = enableAsserts,
+        _clientIdFile = homeDirectory
+            .childDirectory(kDartToolDirectoryName)
+            .childFile(kClientIdFileName),
+        _userProperty = UserProperty(
+          sessionFile: homeDirectory
+              .childDirectory(kDartToolDirectoryName)
+              .childFile(kSessionFileName),
+          flutterChannel: flutterChannel,
+          host: platform.label,
+          flutterVersion: flutterVersion,
+          dartVersion: dartVersion,
+          tool: tool.label,
+          // We truncate this to a maximum of 36 characters since this can
+          // a very long string for some operating systems
+          hostOsVersion:
+              truncateStringToLength(io.Platform.operatingSystemVersion, 36),
+          locale: io.Platform.localeName,
+          clientIde: clientIde,
+          enabledFeatures: enabledFeatures,
+        ),
+        _configHandler = ConfigHandler(
+          homeDirectory: homeDirectory,
+          configFile: homeDirectory
+              .childDirectory(kDartToolDirectoryName)
+              .childFile(kConfigFileName),
+        ),
+        _logHandler = LogHandler(
+          logFile: homeDirectory
+              .childDirectory(kDartToolDirectoryName)
+              .childFile(kLogFileName),
+        ) {
+    // This initializer class will let the instance know
+    // if it was the first run; if it is, nothing will be sent
+    // on the first run
+    if (firstRun) {
+      _showMessage = true;
+      _firstRun = true;
+    } else {
+      _showMessage = false;
+      _firstRun = false;
+    }
+
+    // Check if the tool has already been onboarded, and if it
+    // has, check if the latest message version is greater to
+    // prompt the client to show a message
+    //
+    // If the tool has not been added to the config file, then
+    // we will show the message as well
+    final currentVersion =
+        _configHandler.parsedTools[tool.label]?.versionNumber ?? -1;
+    if (currentVersion < toolsMessageVersion) {
+      _showMessage = true;
+
+      // If the message version has been updated, it will be considered
+      // as if it was a first run and any events attempting to get sent
+      // will be blocked
+      _firstRun = true;
+    }
+  }
+
+  @override
+  String get clientId {
+    if (!_clientIdFile.existsSync()) {
+      createClientIdFile(clientIdFile: _clientIdFile);
+    }
+    _clientId ??= _clientIdFile.readAsStringSync();
+
+    return _clientId!;
+  }
+
+  @override
+  String get getConsentMessage {
+    // The command to swap in the consent message
+    final commandString =
+        tool == DashTool.flutterTool || tool == DashTool.devtools
+            ? 'flutter'
+            : 'dart';
+
+    return kToolsMessage
+        .replaceAll('{{ toolDescription }}', tool.description)
+        .replaceAll('{{ toolName }}', commandString);
+  }
+
+  /// Checking the [telemetryEnabled] boolean reflects what the
+  /// config file reflects.
+  ///
+  /// Checking the [_showMessage] boolean indicates if the consent
+  /// message has been shown for the user, this boolean is set to `true`
+  /// when the tool using this package invokes the [clientShowedMessage]
+  /// method.
+  ///
+  /// If the user has suppressed telemetry [_telemetrySuppressed] will
+  /// return `true` to prevent events from being sent for current invocation.
+  ///
+  /// Checking if it is the first time a tool is running with this package
+  /// as indicated by [_firstRun].
+  @override
+  bool get okToSend =>
+      telemetryEnabled && !_showMessage && !_telemetrySuppressed && !_firstRun;
+
+  @override
+  Map<String, ToolInfo> get parsedTools => _configHandler.parsedTools;
+
+  @override
+  bool get shouldShowMessage => _showMessage;
+
+  @override
+  bool get telemetryEnabled => _configHandler.telemetryEnabled;
+
+  @override
+  Map<String, Map<String, Object?>> get userPropertyMap =>
+      _userProperty.preparePayload();
+
+  @override
+  void clientShowedMessage() {
+    // Check the tool needs to be added to the config file
+    if (!_configHandler.parsedTools.containsKey(tool.label)) {
+      _configHandler.addTool(
+        tool: tool.label,
+        versionNumber: toolsMessageVersion,
+      );
+    }
+
+    // When the tool already exists but the consent message version
+    // has been updated
+    if (_configHandler.parsedTools[tool.label]!.versionNumber <
+        toolsMessageVersion) {
+      _configHandler.incrementToolVersion(
+        tool: tool.label,
+        newVersionNumber: toolsMessageVersion,
+      );
+    }
+    _showMessage = false;
+  }
+
+  @override
+  Future<void> close({int delayDuration = kDelayDuration}) async {
+    // Collect any errors encountered and send
+    _sendPendingErrorEvents();
+
+    await Future.wait(_futures).timeout(
+      Duration(milliseconds: delayDuration),
+      onTimeout: () => [],
+    );
+    _gaClient.close();
+  }
+
+  @override
+  Future<List<Survey>> fetchAvailableSurveys() async {
+    final surveysToShow = <Survey>[];
+    if (!okToSend) return surveysToShow;
+
+    final logFileStats = _logHandler.logFileStats();
+
+    // Call for surveys that have already been dismissed from
+    // persisted survey ids on disk
+    final persistedSurveyMap = _surveyHandler.fetchPersistedSurveys();
+
+    for (final survey in await _surveyHandler.fetchSurveyList()) {
+      // If the survey has listed the tool running this package in the exclude
+      // list, it will not be returned
+      if (survey.excludeDashToolList.contains(tool)) continue;
+
+      // Apply the survey's sample rate; if the generated value from
+      // the client id and survey's uniqueId are less, it will not get
+      // sent to the user
+      if (survey.samplingRate < sampleRate(clientId, survey.uniqueId)) {
+        continue;
+      }
+
+      // If the survey has been permanently dismissed or has temporarily
+      // been snoozed, skip it
+      if (surveySnoozedOrDismissed(survey, persistedSurveyMap)) continue;
+
+      // Counter to check each survey condition, if all are met, then
+      // this integer will be equal to the number of conditions in
+      // [Survey.conditionList]
+      var conditionsMet = 0;
+      if (logFileStats != null) {
+        for (final condition in survey.conditionList) {
+          // Retrieve the value from the [LogFileStats] with
+          // the label provided in the condtion
+          final logFileStatsValue =
+              logFileStats.getValueByString(condition.field);
+
+          if (logFileStatsValue == null) continue;
+
+          switch (condition.operatorString) {
+            case '>=':
+              if (logFileStatsValue >= condition.value) conditionsMet++;
+            case '<=':
+              if (logFileStatsValue <= condition.value) conditionsMet++;
+            case '>':
+              if (logFileStatsValue > condition.value) conditionsMet++;
+            case '<':
+              if (logFileStatsValue < condition.value) conditionsMet++;
+            case '==':
+              if (logFileStatsValue == condition.value) conditionsMet++;
+            case '!=':
+              if (logFileStatsValue != condition.value) conditionsMet++;
+          }
+        }
+      }
+
+      if (conditionsMet == survey.conditionList.length) {
+        surveysToShow.add(survey);
+      }
+    }
+
+    return surveysToShow;
+  }
+
+  @override
+  LogFileStats? logFileStats() => _logHandler.logFileStats();
+
+  @override
+  void send(Event event) {
+    if (!okToSend) return;
+
+    // Construct the body of the request
+    final body = generateRequestBody(
+      clientId: clientId,
+      eventName: event.eventName,
+      eventData: event.eventData,
+      userProperty: _userProperty,
+    );
+
+    if (_enableAsserts) checkBody(body);
+
+    _logHandler.save(data: body);
+
+    final gaClientFuture = _gaClient.sendData(body);
+    _futures.add(gaClientFuture);
+    gaClientFuture.whenComplete(() => _futures.remove(gaClientFuture));
+  }
+
+  @override
+  Future<void> setTelemetry(bool reportingBool) {
+    _configHandler.setTelemetry(reportingBool);
+
+    // Creation of the [Event] for opting out
+    final collectionEvent =
+        Event.analyticsCollectionEnabled(status: reportingBool);
+
+    // The body of the request that will be sent to GA4
+    final Map<String, Object?> body;
+
+    if (reportingBool) {
+      // Recreate the session and client id file; no need to
+      // recreate the log file since it will only receives events
+      // to persist from events sent
+      createClientIdFile(clientIdFile: _clientIdFile);
+      createSessionFile(sessionFile: _userProperty.sessionFile);
+
+      // Reread the client ID string so an empty string is not being
+      // sent to GA4 since the persisted files are cleared when a user
+      // decides to opt out of telemetry collection
+      _clientId = _clientIdFile.readAsStringSync();
+
+      // We must construct the body at this point after we have read in the
+      // new client id string that was generated
+      body = generateRequestBody(
+        clientId: clientId,
+        eventName: collectionEvent.eventName,
+        eventData: collectionEvent.eventData,
+        userProperty: _userProperty,
+      );
+
+      _logHandler.save(data: body);
+    } else {
+      // Construct the body of the request to signal
+      // telemetry status toggling
+      body = generateRequestBody(
+        clientId: clientId,
+        eventName: collectionEvent.eventName,
+        eventData: collectionEvent.eventData,
+        userProperty: _userProperty,
+      );
+
+      // For opted out users, data in the persisted files is cleared
+      _userProperty.sessionFile.writeAsStringSync('');
+      _logHandler.logFile.writeAsStringSync('');
+      _clientIdFile.writeAsStringSync('');
+
+      _clientId = '';
+    }
+
+    // Pass to the google analytics client to send with a
+    // timeout incase http clients hang
+    return _gaClient.sendData(body).timeout(
+          const Duration(milliseconds: kDelayDuration),
+          onTimeout: () => Response('', 200),
+        );
+  }
+
+  @override
+  void suppressTelemetry() => _telemetrySuppressed = true;
+
+  @override
+  void surveyInteracted({
+    required Survey survey,
+    required SurveyButton surveyButton,
+  }) {
+    // Any action, except for 'snooze' will permanently dismiss a given survey
+    final permanentlyDismissed = surveyButton.action == 'snooze' ? false : true;
+    _surveyHandler.dismiss(survey, permanentlyDismissed);
+    send(Event.surveyAction(
+      surveyId: survey.uniqueId,
+      status: surveyButton.action,
+    ));
+  }
+
+  @override
+  void surveyShown(Survey survey) {
+    _surveyHandler.dismiss(survey, false);
+    send(Event.surveyShown(surveyId: survey.uniqueId));
+  }
+
+  /// Send any pending error events, useful for tests to avoid closing
+  /// the connection.
+  ///
+  /// In the main implementation, [AnalyticsImpl], error events are only
+  /// sent on exit when [close] is invoked. This helper method can instead
+  /// have those error events sent immediately to help with tests that check
+  /// [FakeAnalytics.sentEvents].
+  void _sendPendingErrorEvents() {
+    // Collect any errors encountered and send
+    final errorEvents = {..._userProperty.errorSet, ..._logHandler.errorSet};
+    errorEvents
+        .where((event) =>
+            event.eventName == DashEvent.analyticsException &&
+            !_sentErrorEvents.contains(event))
+        .forEach(send);
+
+    // Ensure the same event doesn't get sent again
+    _sentErrorEvents.addAll(errorEvents);
+
+    // Clear error sets
+    _userProperty.errorSet.clear();
+    _logHandler.errorSet.clear();
+  }
+}
+
+/// This fake instance of [Analytics] is intended to be used by clients of
+/// this package for testing purposes. It exposes a list [sentEvents] that
+/// keeps track of all events that have been sent.
+///
+/// This is useful for confirming that events are being sent for a given
+/// workflow. Invoking the [send] method on this instance will not make any
+/// network requests to Google Analytics.
+class FakeAnalytics extends AnalyticsImpl {
+  /// Use this list to check for events that have been emitted when
+  /// invoking the send method
+  final List<Event> sentEvents = [];
+
+  /// Class to use when you want to see which events were sent
+  FakeAnalytics._({
+    required super.tool,
+    required super.homeDirectory,
+    required super.dartVersion,
+    required super.platform,
+    required super.fs,
+    required super.surveyHandler,
+    required super.firstRun,
+    super.flutterChannel,
+    super.flutterVersion,
+    super.clientIde,
+    super.enabledFeatures,
+    super.toolsMessageVersion = kToolsMessageVersion,
+    super.gaClient = const FakeGAClient(),
+    super.enableAsserts = true,
+  });
+
+  /// Getter to reference the private [UserProperty].
+  UserProperty get userProperty => _userProperty;
+
+  @override
+  void send(Event event) {
+    if (!okToSend) return;
+
+    // Construct the body of the request
+    final body = generateRequestBody(
+      clientId: clientId,
+      eventName: event.eventName,
+      eventData: event.eventData,
+      userProperty: _userProperty,
+    );
+
+    if (_enableAsserts) checkBody(body);
+
+    _logHandler.save(data: body);
+
+    // Using this list to validate that events are being sent
+    // for internal methods in the `Analytics` instance
+    sentEvents.add(event);
+  }
+
+  /// Public instance method to invoke private method that sends any
+  /// pending error events.
+  ///
+  /// If this is never invoked, any pending error events will be sent
+  /// when invoking the [close] method.
+  void sendPendingErrorEvents() => _sendPendingErrorEvents();
+}
+
+/// An implementation that will never send events.
+///
+/// This is for clients that opt to either not send analytics, or will migrate
+/// to use [AnalyticsImpl] at a later time.
+class NoOpAnalytics implements Analytics {
+  /// The hard-coded client ID value for each NoOp instance.
+  static String get staticClientId => 'xxxx-xxxx';
+
+  @override
+  final String getConsentMessage = '';
+
+  @override
+  final bool okToSend = false;
+
+  @override
+  final Map<String, ToolInfo> parsedTools = const <String, ToolInfo>{};
+
+  @override
+  final bool shouldShowMessage = false;
+
+  @override
+  final bool telemetryEnabled = false;
+
+  @override
+  final Map<String, Map<String, Object?>> userPropertyMap =
+      const <String, Map<String, Object?>>{};
+
+  const NoOpAnalytics();
+
+  @override
+  String get clientId => staticClientId;
+
+  @override
+  void clientShowedMessage() {}
+
+  @override
+  Future<void> close({int delayDuration = kDelayDuration}) async {}
+
+  @override
+  Future<List<Survey>> fetchAvailableSurveys() async => const <Survey>[];
+
+  @override
+  LogFileStats? logFileStats() => null;
+
+  @override
+  Future<Response>? send(Event event) => null;
+
+  @override
+  Future<void> setTelemetry(bool reportingBool) async {}
+
+  @override
+  void suppressTelemetry() {}
+
+  @override
+  void surveyInteracted({
+    required Survey survey,
+    required SurveyButton surveyButton,
+  }) {}
+
+  @override
+  void surveyShown(Survey survey) {}
+}
diff --git a/pkgs/unified_analytics/lib/src/asserts.dart b/pkgs/unified_analytics/lib/src/asserts.dart
new file mode 100644
index 0000000..199f4ee
--- /dev/null
+++ b/pkgs/unified_analytics/lib/src/asserts.dart
@@ -0,0 +1,172 @@
+// Copyright (c) 2023, 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.
+
+/// Matches only alphabetic characters.
+final RegExp alphabeticPattern = RegExp(r'^[A-Za-z]+$');
+
+/// Matches strings that contain alphanumeric characters and underscores.
+final RegExp alphaNumericPattern = RegExp(r'^[A-Za-z0-9_]+$');
+
+/// Checks that the body of the request being sent to
+/// GA4 is within the limitations.
+///
+/// Limitations can be found:
+/// https://developers.google.com/analytics/devguides/collection/protocol/ga4/sending-events?client_type=gtag#limitations
+void checkBody(Map<String, Object?> body) {
+  // Ensure we have the correct top level keys
+  if (!body.keys.contains('client_id')) {
+    throw AnalyticsException('client_id missing from top level keys');
+  }
+  if (!body.keys.contains('events')) {
+    throw AnalyticsException('events missing from top level keys');
+  }
+  if (!body.keys.contains('user_properties')) {
+    throw AnalyticsException('user_properties missing from top level keys');
+  }
+
+  final events = body['events'] as List;
+  final userProperties = body['user_properties'] as Map<String, Object?>;
+
+  // GA4 Limitation:
+  // Requests can have a maximum of 25 events
+  if (events.length > 25) {
+    throw AnalyticsException('25 is the max number of events');
+  }
+
+  // Checks for each event object
+  for (final eventMap in events.cast<Map<String, Object?>>()) {
+    final eventName = eventMap['name'] as String;
+
+    // GA4 Limitation:
+    // Event names must be 40 characters or fewer, may only contain
+    // alpha-numeric characters and underscores, and must start
+    // with an alphabetic character
+    if (eventName.length > 40) {
+      throw AnalyticsException(
+        'Limit event names to 40 chars or less\n'
+        'Event name: "$eventName" is too long',
+      );
+    }
+    if (!alphaNumericPattern.hasMatch(eventName)) {
+      throw AnalyticsException(
+        'Event name can only have alphanumeric chars and underscores\n'
+        'Event name: "$eventName" contains invalid characters',
+      );
+    }
+    if (!alphabeticPattern.hasMatch(eventName[0])) {
+      throw AnalyticsException(
+        'Event name first char must be alphabetic char\n'
+        'Event name: "$eventName" must begin with a valid character',
+      );
+    }
+
+    final eventParams = eventMap['params'] as Map<String, Object?>;
+
+    // GA4 Limitation:
+    // Events can have a maximum of 25 parameters
+    if (eventParams.length > 25) {
+      throw AnalyticsException(
+        'Limit params for each event to less than 25\n'
+        'Event: "$eventName" has too many parameters',
+      );
+    }
+
+    // Loop through each of the event parameters
+    for (final entry in eventParams.entries) {
+      final key = entry.key;
+      final value = entry.value;
+
+      // GA4 Limitation:
+      // Ensure that each value for the event params is one
+      // of the following types:
+      // `String`, `int`, `double`, or `bool`
+      if (!(value is String ||
+          value is int ||
+          value is double ||
+          value is bool)) {
+        throw AnalyticsException(
+          'Values for event params have to be String, int, double, or bool\n'
+          'Value for "$key" is not a valid type for event: "$eventName"',
+        );
+      }
+
+      // GA4 Limitation:
+      // Parameter names (including item parameters) must be 40 characters
+      // or fewer, may only contain alpha-numeric characters and underscores,
+      // and must start with an alphabetic character
+      if (key.length > 40) {
+        throw AnalyticsException(
+          'Limit event param names to 40 chars or less\n'
+          'The key: "$key" under the event: "$eventName" is too long',
+        );
+      }
+      if (!alphaNumericPattern.hasMatch(key)) {
+        throw AnalyticsException(
+          'Event param name can only have alphanumeric chars and underscores\n'
+          'The key: "$key" under the event: "$eventName" contains '
+          'invalid characters',
+        );
+      }
+      if (!alphabeticPattern.hasMatch(key[0])) {
+        throw AnalyticsException(
+          'Event param name first char must be alphabetic char\n'
+          'The key: "$key" under the event: "$eventName" must begin '
+          'in a valid character',
+        );
+      }
+
+      // GA4 Limitation:
+      // Parameter values (including item parameter values) must be 100
+      // characters or fewer
+      if (value.runtimeType == String) {
+        value as String;
+        if (value.length > 100) {
+          throw AnalyticsException(
+            'Limit characters in event param value to 100 chars or less\n'
+            'Value for "$key" is too long, value="$value"',
+          );
+        }
+      }
+    }
+  }
+
+  // GA4 Limitation:
+  // Events can have a maximum of 25 user properties
+  if (userProperties.length > 25) {
+    throw AnalyticsException('Limit user properties to 25 or less');
+  }
+
+  // Checks for each user property item
+  for (final entry in userProperties.entries) {
+    final key = entry.key;
+    final value = entry.value as Map<String, Object?>;
+
+    // GA4 Limitation:
+    // User property names must be 24 characters or fewer
+    if (key.length > 24) {
+      throw AnalyticsException('Limit user property names to 24 chars or less\n'
+          'The user property key: "$key" is too long');
+    }
+
+    // GA4 Limitation:
+    // User property values must be 36 characters or fewer
+    final userPropValue = value['value'];
+    if (userPropValue is String && userPropValue.length > 36) {
+      throw AnalyticsException(
+        'Limit user property values to 36 chars or less\n'
+        'For the user property key "$key", the value "${value['value']}" '
+        'is too long',
+      );
+    }
+  }
+}
+
+class AnalyticsException implements Exception {
+  final String message;
+
+  AnalyticsException(this.message);
+
+  @override
+  String toString() => 'AnalyticsException: $message';
+}
diff --git a/pkgs/unified_analytics/lib/src/config_handler.dart b/pkgs/unified_analytics/lib/src/config_handler.dart
new file mode 100644
index 0000000..8db4660
--- /dev/null
+++ b/pkgs/unified_analytics/lib/src/config_handler.dart
@@ -0,0 +1,224 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:convert';
+
+import 'package:clock/clock.dart';
+import 'package:convert/convert.dart';
+import 'package:file/file.dart';
+
+import 'initializer.dart';
+import 'utils.dart';
+
+/// The regex pattern used to parse the disable analytics line.
+const String telemetryFlagPattern = r'^reporting=([0|1]) *$';
+
+/// The regex pattern used to parse the tools info
+/// from the configuration file.
+///
+/// Example:
+/// ```text
+/// flutter-tool=2022-10-26,1
+/// devtools=2022-11-26,1
+/// ```
+const String toolPattern =
+    r'^([A-Za-z0-9]+[A-Za-z0-9_-]*)=([0-9]{4}-[0-9]{2}-[0-9]{2}),([0-9]+)$';
+
+class ConfigHandler {
+  /// Regex pattern implementation for matching a line in the config file.
+  static RegExp telemetryFlagRegex =
+      RegExp(telemetryFlagPattern, multiLine: true);
+  static RegExp toolRegex = RegExp(toolPattern, multiLine: true);
+
+  final Directory homeDirectory;
+  final File configFile;
+
+  final Map<String, ToolInfo> parsedTools = <String, ToolInfo>{};
+
+  DateTime configFileLastModified;
+
+  /// Reporting enabled unless specified by user
+  bool _telemetryEnabled = true;
+
+  ConfigHandler({
+    required this.homeDirectory,
+    required this.configFile,
+  }) : configFileLastModified = configFile.lastModifiedSync() {
+    // Call the method to parse the contents of the config file when
+    // this class is initialized
+    parseConfig();
+  }
+
+  /// Returns the telemetry state from the config file.
+  ///
+  /// Method will reparse the config file if it detects that the
+  /// last modified datetime is different from what was parsed when
+  /// the class was initialized.
+  bool get telemetryEnabled {
+    if (configFileLastModified.isBefore(configFile.lastModifiedSync())) {
+      parseConfig();
+      configFileLastModified = configFile.lastModifiedSync();
+    }
+
+    return _telemetryEnabled;
+  }
+
+  /// Responsibe for the creation of the configuration line
+  /// for the tool being passed in by the user and adding a
+  /// [ToolInfo] object.
+  void addTool({
+    required String tool,
+    required int versionNumber,
+  }) {
+    // Create the new instance of [ToolInfo] to be added
+    // to the [parsedTools] map
+    parsedTools[tool] = ToolInfo(
+      lastRun: clock.now(),
+      versionNumber: versionNumber,
+    );
+
+    // New string to be appended to the bottom of the configuration file
+    // with a newline character for new tools to be added
+    var newTool = '$tool=$dateStamp,$versionNumber\n';
+    if (!configFile.readAsStringSync().endsWith('\n')) {
+      newTool = '\n$newTool';
+    }
+    configFile.writeAsStringSync(newTool, mode: FileMode.append);
+    configFileLastModified = configFile.lastModifiedSync();
+  }
+
+  /// Will increment the version number and update the date
+  /// in the config file for the provided tool name while
+  /// also incrementing the version number in [ToolInfo].
+  void incrementToolVersion({
+    required String tool,
+    required int newVersionNumber,
+  }) {
+    if (!parsedTools.containsKey(tool)) {
+      return;
+    }
+
+    // Read in the config file contents and use a regex pattern to
+    // match the line for the current tool (ie. flutter-tools=2023-01-05,1)
+    final configString = configFile.readAsStringSync();
+    final pattern = '^($tool)=([0-9]{4}-[0-9]{2}-[0-9]{2}),([0-9]+)\$';
+
+    final regex = RegExp(pattern, multiLine: true);
+    final matches = regex.allMatches(configString);
+
+    // If there isn't exactly one match for the given tool, that suggests the
+    // file has been altered and needs to be reset
+    if (matches.length != 1) {
+      resetConfig();
+      return;
+    }
+
+    // Construct the new tool line for the config line and replace it
+    // in the original config string to prep for writing back out
+    final newToolString = '$tool=$dateStamp,$newVersionNumber';
+    final newConfigString = configString.replaceAll(regex, newToolString);
+    configFile.writeAsStringSync(newConfigString);
+
+    final toolInfo = parsedTools[tool];
+    if (toolInfo == null) {
+      return;
+    }
+
+    // Update the [ToolInfo] object for the current tool
+    toolInfo.lastRun = clock.now();
+    toolInfo.versionNumber = newVersionNumber;
+  }
+
+  /// Method responsible for reading in the config file stored on
+  /// user's machine and parsing out the following: all the tools that
+  /// have been logged in the file, the dates they were last run, and
+  /// determining if telemetry is enabled by parsing the file.
+  void parseConfig() {
+    // Begin with the assumption that telemetry is always enabled
+    _telemetryEnabled = true;
+
+    // Read the configuration file as a string and run the two regex patterns
+    // on it to get information around which tools have been parsed and whether
+    // or not telemetry has been disabled by the user
+    final configString = configFile.readAsStringSync();
+
+    // Collect the tools logged in the configuration file
+    toolRegex.allMatches(configString).forEach((RegExpMatch element) {
+      // Extract the information relevant for the [ToolInfo] class
+      final tool = element.group(1) as String;
+      final lastRun = DateTime.parse(element.group(2) as String);
+      final versionNumber = int.parse(element.group(3) as String);
+
+      // Initialize an instance of the [ToolInfo] class to store
+      // in the [parsedTools] map object
+      parsedTools[tool] = ToolInfo(
+        lastRun: lastRun,
+        versionNumber: versionNumber,
+      );
+    });
+
+    // Check for lines signaling that the user has disabled analytics,
+    // if multiple lines are found, the more conservative value will be used
+    telemetryFlagRegex.allMatches(configString).forEach((RegExpMatch element) {
+      // Conditional for recording telemetry as being disabled
+      if (element.group(1) == '0') {
+        _telemetryEnabled = false;
+      }
+    });
+  }
+
+  /// This will reset the configuration file and clear the
+  /// [parsedTools] map and trigger parsing the config again.
+  void resetConfig() {
+    createConfigFile(
+      configFile: configFile,
+      homeDirectory: homeDirectory,
+    );
+    parsedTools.clear();
+    parseConfig();
+  }
+
+  /// Disables the reporting capabilities if [reportingBool] is set to `false`.
+  Future<void> setTelemetry(bool reportingBool) async {
+    final flag = reportingBool ? '1' : '0';
+    final configString = await configFile.readAsString();
+
+    final matches = telemetryFlagRegex.allMatches(configString);
+
+    // If there isn't exactly one match for the reporting flag, that suggests
+    // the file has been altered and needs to be reset
+    if (matches.length != 1) {
+      resetConfig();
+      return;
+    }
+
+    final newTelemetryString = 'reporting=$flag';
+
+    final newConfigString =
+        configString.replaceAll(telemetryFlagRegex, newTelemetryString);
+
+    await configFile.writeAsString(newConfigString);
+    configFileLastModified = configFile.lastModifiedSync();
+
+    _telemetryEnabled = reportingBool;
+  }
+}
+
+class ToolInfo {
+  DateTime lastRun;
+  int versionNumber;
+
+  ToolInfo({
+    required this.lastRun,
+    required this.versionNumber,
+  });
+
+  @override
+  String toString() {
+    return json.encode(<String, Object?>{
+      'lastRun': FixedDateTimeFormatter('YYYY-MM-DD').encode(lastRun),
+      'versionNumber': versionNumber,
+    });
+  }
+}
diff --git a/pkgs/unified_analytics/lib/src/constants.dart b/pkgs/unified_analytics/lib/src/constants.dart
new file mode 100644
index 0000000..fde9c21
--- /dev/null
+++ b/pkgs/unified_analytics/lib/src/constants.dart
@@ -0,0 +1,119 @@
+// Copyright (c) 2023, 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.
+
+/// URL endpoint for sending Google Analytics Events.
+const String kAnalyticsUrl = 'https://www.google-analytics.com/mp/collect';
+
+/// Name for the text file that will contain the user's randomly generated
+/// client id.
+const String kClientIdFileName = 'CLIENT_ID';
+
+/// Name for the file where telemetry status and tools data will be stored.
+const String kConfigFileName = 'dart-flutter-telemetry.config';
+
+/// The string that will provide the boilerplate for the configuration file
+/// stored on the user's machine.
+const String kConfigString = '''
+# INTRODUCTION
+#
+# This is the Flutter and Dart telemetry reporting
+# configuration file.
+#
+# Lines starting with a #" are documentation that
+# the tools maintain automatically.
+#
+# All other lines are configuration lines. They have
+# the form "name=value". If multiple lines contain
+# the same configuration name with different values,
+# the parser will default to a conservative value. 
+
+# DISABLING TELEMETRY REPORTING
+#
+# To disable telemetry reporting, set "reporting" to
+# the value "0" and to enable, set to "1":
+reporting=1
+
+# NOTIFICATIONS
+#
+# Each tool records when it last informed the user about
+# analytics reporting and the privacy policy.
+#
+# The following tools have so far read this file:
+#
+#   dart-tools (Dart CLI developer tool)
+#   devtools (DevTools debugging and performance tools)
+#   flutter-tools (Flutter CLI developer tool)
+#
+# For each one, the file may contain a configuration line
+# where the name is the code in the list above, e.g. "dart-tool",
+# and the value is a date in the form YYYY-MM-DD, a comma, and
+# a number representing the version of the message that was
+# displayed.''';
+
+/// Link to contextual survey metadata file.
+const String kContextualSurveyUrl =
+    'https://storage.googleapis.com/flutter-uxr/surveys/contextual-survey-metadata.json';
+
+/// Name of the directory where all of the files necessary for this package
+/// will be located.
+const String kDartToolDirectoryName = '.dart-tool';
+
+/// The default time to wait before closing the http connection to allow for
+/// pending events to be sent.
+const int kDelayDuration = 250;
+
+/// Name of the file where we persist dismissed survey ids.
+const String kDismissedSurveyFileName =
+    'dart-flutter-telemetry-dismissed-surveys.json';
+
+/// The API secret associated with the GA4 instance's Measurement Protocol.
+const String kGoogleAnalyticsApiSecret = 'Ka1jc8tZSzWc_GXMWHfPHA';
+
+/// The measurement ID related to the GA4 instance.
+///
+/// Serves as an identifier for a web data stream.
+const String kGoogleAnalyticsMeasurementId = 'G-04BXPVBCWJ';
+
+/// How many data records to store in the log file.
+const int kLogFileLength = 2500;
+
+/// The maximum allowed size of the telemetry log file.
+///
+/// 25 MiB.
+const int kMaxLogFileSize = 25 * (1 << 20);
+
+/// Filename for the log file to persist sent events on user's machine.
+const String kLogFileName = 'dart-flutter-telemetry.log';
+
+/// The current version of the package, should be in line with pubspec version.
+const String kPackageVersion = '6.1.4';
+
+/// The minimum length for a session.
+const int kSessionDurationMinutes = 30;
+
+/// Name for the json file where the session details will be stored.
+const String kSessionFileName = 'dart-flutter-telemetry-session.json';
+
+/// The message that should be shown to the user.
+const String kToolsMessage = '''
+The {{ toolDescription }} uses Google Analytics to report usage and diagnostic
+data along with package dependencies, and crash reporting to send basic crash
+reports. This data is used to help improve the Dart platform, Flutter framework,
+and related tools.
+
+Telemetry is not sent on the very first run. To disable reporting of telemetry,
+run this terminal command:
+
+    {{ toolName }} --disable-analytics
+
+If you opt out of telemetry, an opt-out event will be sent, and then no further
+information will be sent. This data is collected in accordance with the Google
+Privacy Policy (https://policies.google.com/privacy).
+''';
+
+/// The version number for the message below.
+///
+/// If the message below is altered, the version should be incremented so that
+/// users can be prompted with the updated messaging.
+const int kToolsMessageVersion = 1;
diff --git a/pkgs/unified_analytics/lib/src/enums.dart b/pkgs/unified_analytics/lib/src/enums.dart
new file mode 100644
index 0000000..d67ab66
--- /dev/null
+++ b/pkgs/unified_analytics/lib/src/enums.dart
@@ -0,0 +1,234 @@
+// Copyright (c) 2023, 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.
+
+/// The valid dash tool labels stored in the [DashTool] enum.
+List<String> get validDashTools =>
+    DashTool.values.map((e) => e.label).toList()..sort();
+
+/// Values for the event name to be sent to Google Analytics.
+///
+/// The [label] for each enum value is what will be logged, the [description]
+/// is here for documentation purposes.
+///
+/// Set the nullable [toolOwner] parameter if the event belongs to one specific
+/// tool, otherwise, if multiple tools will be sending the event, leave it null.
+enum DashEvent {
+  // Events that can be sent by all tools; these
+  // events should not be tool specific; toolOwner
+  // not necessary for these events
+
+  analyticsCollectionEnabled(
+    label: 'analytics_collection_enabled',
+    description: 'The opt-in status for analytics collection',
+  ),
+  analyticsException(
+    label: 'analytics_exception',
+    description: 'Errors that are encountered within package:unified_analytics',
+  ),
+  exception(
+    label: 'exception',
+    description: 'General errors to log',
+  ),
+  surveyAction(
+    label: 'survey_action',
+    description: 'Actions taken by users when shown survey',
+  ),
+  surveyShown(
+    label: 'survey_shown',
+    description: 'Survey shown to the user',
+  ),
+  timing(
+    label: 'timing',
+    description: 'Events for timing how long a process takes',
+  ),
+
+  // Events for the Dart CLI
+
+  dartCliCommandExecuted(
+    label: 'dart_cli_command_executed',
+    description: 'Information about the execution of a Dart CLI command',
+    toolOwner: DashTool.dartTool,
+  ),
+  pubGet(
+    label: 'pub_get',
+    description: 'Pub package resolution details',
+    toolOwner: DashTool.dartTool,
+  ),
+
+  // Events for Flutter devtools
+
+  devtoolsEvent(
+    label: 'devtools_event',
+    description: 'Information for various devtools events',
+    toolOwner: DashTool.devtools,
+  ),
+
+  // Events for the Flutter CLI
+
+  appleUsageEvent(
+    label: 'apple_usage_event',
+    description:
+        'Events related to iOS/macOS workflows within the flutter tool',
+    toolOwner: DashTool.flutterTool,
+  ),
+  codeSizeAnalysis(
+    label: 'code_size_analysis',
+    description: 'Indicates when the "--analyize-size" command is run',
+    toolOwner: DashTool.flutterTool,
+  ),
+  commandUsageValues(
+    label: 'command_usage_values',
+    description: 'Contains command level custom dimensions from legacy '
+        'flutter analytics',
+    toolOwner: DashTool.flutterTool,
+  ),
+  doctorValidatorResult(
+    label: 'doctor_validator_result',
+    description: 'Results from a specific doctor validator',
+    toolOwner: DashTool.flutterTool,
+  ),
+  flutterBuildInfo(
+    label: 'flutter_build_info',
+    description: 'Information for a flutter build invocation',
+    toolOwner: DashTool.flutterTool,
+  ),
+  flutterCommandResult(
+    label: 'flutter_command_result',
+    description: 'Provides information about flutter commands that ran',
+    toolOwner: DashTool.flutterTool,
+  ),
+  hotReloadTime(
+    label: 'hot_reload_time',
+    description: 'Hot reload duration',
+    toolOwner: DashTool.flutterTool,
+  ),
+  hotRunnerInfo(
+    label: 'hot_runner_info',
+    description: 'Information related to the Flutter hot runner',
+    toolOwner: DashTool.flutterTool,
+  ),
+
+  // Events for language_server below
+
+  clientNotification(
+    label: 'client_notification',
+    description: 'Notifications sent from the client',
+  ),
+  clientRequest(
+    label: 'client_request',
+    description: 'Requests sent from the client',
+  ),
+  commandExecuted(
+    label: 'command_executed',
+    description: 'Number of times a command is executed',
+  ),
+  contextStructure(
+    label: 'context_structure',
+    description: 'Structure of the analysis contexts being analyzed',
+  ),
+  lintUsageCount(
+    label: 'lint_usage_count',
+    description: 'Number of times a given lint is enabled',
+  ),
+  memoryInfo(
+    label: 'memory_info',
+    description: 'Memory usage information',
+  ),
+  pluginRequest(
+    label: 'plugin_request',
+    description: 'Request responses from plugins',
+  ),
+  pluginUse(
+    label: 'plugin_use',
+    description: 'Information about how often a plugin was used',
+  ),
+  serverSession(
+    label: 'server_session',
+    description: 'Dart Analyzer Server session data',
+  ),
+  severityAdjustment(
+    label: 'severity_adjustment',
+    description: 'Number of times diagnostic severity is changed',
+  ),
+  ;
+
+  final String label;
+  final String description;
+  final DashTool? toolOwner;
+  const DashEvent({
+    required this.label,
+    required this.description,
+    this.toolOwner,
+  });
+
+  /// This takes in the string label for a given [DashEvent] and returns the
+  /// enum for that string label.
+  static DashEvent? fromLabel(String label) =>
+      DashEvent.values.where((e) => e.label == label).firstOrNull;
+}
+
+/// Officially-supported clients of this package as logical
+/// tools, grouped by user point of view.  Derived directly
+/// from the PDD.
+enum DashTool {
+  androidStudioPlugins(
+    label: 'android-studio-plugins',
+    description: 'Android Studio IDE plugins for Dart and Flutter',
+  ),
+  dartTool(
+    label: 'dart-tool',
+    description: 'Dart CLI developer tool',
+  ),
+  devtools(
+    label: 'devtools',
+    description: 'DevTools debugging and performance tools',
+  ),
+  flutterTool(
+    label: 'flutter-tool',
+    description: 'Flutter CLI developer tool',
+  ),
+  intellijPlugins(
+    label: 'intellij-plugins',
+    description: 'IntelliJ IDE plugins for Dart and Flutter',
+  ),
+  vscodePlugins(
+    label: 'vscode-plugins',
+    description: 'VS Code IDE extensions for Dart and Flutter',
+  );
+
+  /// String used as the control flag and the value of the tool key in
+  /// analytics.
+  final String label;
+
+  /// The "notice string", a human-readable description of the logical tool
+  /// grouping.
+  final String description;
+
+  const DashTool({
+    required this.label,
+    required this.description,
+  });
+
+  /// This takes in the string label for a given [DashTool] and returns the
+  /// enum for that string label.
+  static DashTool fromLabel(String label) {
+    final tool = DashTool.values.where((t) => t.label == label).firstOrNull;
+    if (tool != null) return tool;
+
+    throw Exception('The tool $label from the survey metadata file is not '
+        'a valid DashTool enum value\n'
+        'Valid labels for dash tools: ${validDashTools.join(', ')}');
+  }
+}
+
+/// Enumerate options for platforms supported.
+enum DevicePlatform {
+  windows('Windows'),
+  macos('macOS'),
+  linux('Linux'),
+  ;
+
+  final String label;
+  const DevicePlatform(this.label);
+}
diff --git a/pkgs/unified_analytics/lib/src/event.dart b/pkgs/unified_analytics/lib/src/event.dart
new file mode 100644
index 0000000..a24fe0c
--- /dev/null
+++ b/pkgs/unified_analytics/lib/src/event.dart
@@ -0,0 +1,889 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:convert';
+
+import 'enums.dart';
+
+final class Event {
+  final DashEvent eventName;
+  final Map<String, Object?> eventData;
+
+  /// Event that is emitted whenever a user has opted in
+  /// or out of the analytics collection.
+  ///
+  /// [status] - boolean value where `true` indicates user is opting in.
+  Event.analyticsCollectionEnabled({required bool status})
+      : eventName = DashEvent.analyticsCollectionEnabled,
+        eventData = {'status': status};
+
+  /// Event that is emitted when an error occurs within
+  /// `package:unified_analytics`, tools that are using this package
+  /// should not use this event constructor.
+  ///
+  /// Tools using this package should instead use the more generic
+  /// [Event.exception] constructor.
+  ///
+  /// [workflow] - refers to what process caused the error, such as
+  ///   "LogHandler.logFileStats".
+  ///
+  /// [error] - the name of the error, such as "FormatException".
+  ///
+  /// [description] - the description of the error being caught.
+  Event.analyticsException({
+    required String workflow,
+    required String error,
+    String? description,
+  })  : eventName = DashEvent.analyticsException,
+        eventData = {
+          'workflow': workflow,
+          'error': error,
+          if (description != null) 'description': description,
+        };
+
+  /// This is for various workflows within the flutter tool related
+  /// to iOS and macOS workflows.
+  ///
+  /// [workflow] - which workflow is running, such as "assemble".
+  ///
+  /// [parameter] - subcategory of the workflow, such as "ios-archive".
+  ///
+  /// [result] - usually to indicate success or failure of the workflow.
+  Event.appleUsageEvent({
+    required String workflow,
+    required String parameter,
+    String? result,
+  })  : eventName = DashEvent.appleUsageEvent,
+        eventData = {
+          'workflow': workflow,
+          'parameter': parameter,
+          if (result != null) 'result': result,
+        };
+
+  /// Event that is emitted periodically to report the performance of the
+  /// analysis server's handling of a specific kind of notification from the
+  /// client.
+  ///
+  /// [duration] - json encoded percentile values indicating how long it took
+  ///     from the time the server started handling the notification until the
+  ///     server had finished handling the notification.
+  ///
+  /// [latency] - json encoded percentile values indicating how long it took
+  ///     from the time the notification was sent until the server started
+  ///     handling it.
+  ///
+  /// [method] - the name of the notification method that was sent.
+  Event.clientNotification({
+    required String duration,
+    required String latency,
+    required String method,
+  })  : eventName = DashEvent.clientNotification,
+        eventData = {
+          'duration': duration,
+          'latency': latency,
+          'method': method,
+        };
+
+  /// Event that is emitted periodically to report the performance of the
+  /// analysis server's handling of a specific kind of request from the client.
+  ///
+  /// [duration] - json encoded percentile values indicating how long it took
+  ///     from the time the server started handling the request until the server
+  ///     had send a response.
+  ///
+  /// [latency] - json encoded percentile values indicating how long it took
+  ///     from the time the request was sent until the server started handling
+  ///     it.
+  ///
+  /// [method] - the name of the request method that was sent.
+  ///
+  /// If the method is `workspace/didChangeWorkspaceFolders`, then the following
+  /// parameters should be included:
+  ///
+  /// [added] - json encoded percentile values indicating the number of folders
+  ///     that were added.
+  ///
+  /// [removed] - json encoded percentile values indicating the number of
+  ///     folders that were removed.
+  ///
+  /// If the method is `initialized`, then the following parameters should be
+  /// included:
+  ///
+  /// [openWorkspacePaths] - json encoded percentile values indicating the
+  ///     number of workspace paths that were opened.
+  ///
+  /// If the method is `analysis.setAnalysisRoots`, then the following
+  /// parameters should be included:
+  ///
+  /// [included] - json encoded percentile values indicating the number of
+  ///     analysis roots in the included list.
+  ///
+  /// [excluded] - json encoded percentile values indicating the number of
+  ///     analysis roots in the excluded list.
+  ///
+  /// If the method is `analysis.setPriorityFiles`, then the following
+  /// parameters should be included:
+  ///
+  /// [files] - json encoded percentile values indicating the number of priority
+  ///     files.
+  ///
+  Event.clientRequest({
+    required String duration,
+    required String latency,
+    required String method,
+    String? added,
+    String? excluded,
+    String? files,
+    String? included,
+    String? openWorkspacePaths,
+    String? removed,
+  })  : eventName = DashEvent.clientRequest,
+        eventData = {
+          if (added != null) 'added': added,
+          'duration': duration,
+          if (excluded != null) 'excluded': excluded,
+          if (files != null) 'files': files,
+          if (included != null) 'included': included,
+          'latency': latency,
+          'method': method,
+          if (openWorkspacePaths != null)
+            'openWorkspacePaths': openWorkspacePaths,
+          if (removed != null) 'removed': removed,
+        };
+
+  /// An event that reports when the code size measurement is run
+  /// via `--analyze-size`.
+  ///
+  /// [platform] - string identifier for which platform was run "ios", "apk",
+  ///   "aab", etc.
+  Event.codeSizeAnalysis({required String platform})
+      : eventName = DashEvent.codeSizeAnalysis,
+        eventData = {
+          'platform': platform,
+        };
+
+  /// Event that is emitted periodically to report the number of times a given
+  /// command has been executed.
+  ///
+  /// [count] - the number of times the command was executed.
+  ///
+  /// [name] - the name of the command that was executed.
+  Event.commandExecuted({
+    required int count,
+    required String name,
+  })  : eventName = DashEvent.commandExecuted,
+        eventData = {
+          'count': count,
+          'name': name,
+        };
+
+  /// Event to capture usage values for different flutter commands.
+  ///
+  /// There are several implementations of the `FlutterCommand` class within the
+  /// flutter-tool that pass information based on the [workflow] being ran. An
+  /// example of a [workflow] can be "create". The optional parameters for this
+  /// constructor are a superset of all the implementations of `FlutterCommand`.
+  /// There should never be a time where all of the parameters are passed to
+  /// this constructor.
+  Event.commandUsageValues({
+    required String workflow,
+    required bool commandHasTerminal,
+
+    // Assemble && build bundle implementation parameters
+    String? buildBundleTargetPlatform,
+    bool? buildBundleIsModule,
+
+    // Build aar implementation parameters
+    String? buildAarProjectType,
+    String? buildAarTargetPlatform,
+
+    // Build apk implementation parameters
+    String? buildApkTargetPlatform,
+    String? buildApkBuildMode,
+    bool? buildApkSplitPerAbi,
+
+    // Build app bundle implementation parameters
+    String? buildAppBundleTargetPlatform,
+    String? buildAppBundleBuildMode,
+
+    // Create implementation parameters
+    String? createProjectType,
+    String? createAndroidLanguage,
+    String? createIosLanguage,
+
+    // Packages implementation parameters
+    int? packagesNumberPlugins,
+    bool? packagesProjectModule,
+    String? packagesAndroidEmbeddingVersion,
+
+    // Run implementation parameters
+    bool? runIsEmulator,
+    String? runTargetName,
+    String? runTargetOsVersion,
+    String? runModeName,
+    bool? runProjectModule,
+    String? runProjectHostLanguage,
+    String? runAndroidEmbeddingVersion,
+    bool? runEnableImpeller,
+    String? runIOSInterfaceType,
+    bool? runIsTest,
+  })  : eventName = DashEvent.commandUsageValues,
+        eventData = {
+          'workflow': workflow,
+          'commandHasTerminal': commandHasTerminal,
+          if (buildBundleTargetPlatform != null)
+            'buildBundleTargetPlatform': buildBundleTargetPlatform,
+          if (buildBundleIsModule != null)
+            'buildBundleIsModule': buildBundleIsModule,
+          if (buildAarProjectType != null)
+            'buildAarProjectType': buildAarProjectType,
+          if (buildAarTargetPlatform != null)
+            'buildAarTargetPlatform': buildAarTargetPlatform,
+          if (buildApkTargetPlatform != null)
+            'buildApkTargetPlatform': buildApkTargetPlatform,
+          if (buildApkBuildMode != null) 'buildApkBuildMode': buildApkBuildMode,
+          if (buildApkSplitPerAbi != null)
+            'buildApkSplitPerAbi': buildApkSplitPerAbi,
+          if (buildAppBundleTargetPlatform != null)
+            'buildAppBundleTargetPlatform': buildAppBundleTargetPlatform,
+          if (buildAppBundleBuildMode != null)
+            'buildAppBundleBuildMode': buildAppBundleBuildMode,
+          if (createProjectType != null) 'createProjectType': createProjectType,
+          if (createAndroidLanguage != null)
+            'createAndroidLanguage': createAndroidLanguage,
+          if (createIosLanguage != null) 'createIosLanguage': createIosLanguage,
+          if (packagesNumberPlugins != null)
+            'packagesNumberPlugins': packagesNumberPlugins,
+          if (packagesProjectModule != null)
+            'packagesProjectModule': packagesProjectModule,
+          if (packagesAndroidEmbeddingVersion != null)
+            'packagesAndroidEmbeddingVersion': packagesAndroidEmbeddingVersion,
+          if (runIsEmulator != null) 'runIsEmulator': runIsEmulator,
+          if (runTargetName != null) 'runTargetName': runTargetName,
+          if (runTargetOsVersion != null)
+            'runTargetOsVersion': runTargetOsVersion,
+          if (runModeName != null) 'runModeName': runModeName,
+          if (runProjectModule != null) 'runProjectModule': runProjectModule,
+          if (runProjectHostLanguage != null)
+            'runProjectHostLanguage': runProjectHostLanguage,
+          if (runAndroidEmbeddingVersion != null)
+            'runAndroidEmbeddingVersion': runAndroidEmbeddingVersion,
+          if (runEnableImpeller != null) 'runEnableImpeller': runEnableImpeller,
+          if (runIOSInterfaceType != null)
+            'runIOSInterfaceType': runIOSInterfaceType,
+          if (runIsTest != null) 'runIsTest': runIsTest,
+        };
+
+  /// Event that is emitted on shutdown to report the structure of the analysis
+  /// contexts created immediately after startup.
+  ///
+  /// [contextsFromBothFiles] - the number of contexts that were created because
+  ///     of both a package config and an analysis options file.
+  ///
+  /// [contextsFromOptionsFiles] - the number of contexts that were created
+  ///     because of an analysis options file.
+  ///
+  /// [contextsFromPackagesFiles] - the number of contexts that were created
+  ///     because of a package config file.
+  ///
+  /// [contextsWithoutFiles] - the number of contexts that were created because
+  ///     of the lack of either a package config or an analysis options file.
+  ///
+  /// [immediateFileCount] - the number of files in one of the analysis
+  ///     contexts.
+  ///
+  /// [immediateFileLineCount] - the number of lines in the immediate files.
+  ///
+  /// [numberOfContexts] - the number of analysis context created.
+  ///
+  /// [transitiveFileCount] - the number of files reachable from the files in
+  ///     each analysis context, where files can be counted multiple times if
+  ///     they are reachable from multiple contexts.
+  ///
+  /// [transitiveFileLineCount] - the number of lines in the transitive files,
+  ///     where files can be counted multiple times if they are reachable from
+  ///     multiple contexts.
+  ///
+  /// [transitiveFileUniqueCount] - the number of unique files reachable from
+  ///     the files in each analysis context.
+  ///
+  /// [transitiveFileUniqueLineCount] - the number of lines in the unique
+  ///     transitive files.
+  Event.contextStructure({
+    required int contextsFromBothFiles,
+    required int contextsFromOptionsFiles,
+    required int contextsFromPackagesFiles,
+    required int contextsWithoutFiles,
+    required int immediateFileCount,
+    required int immediateFileLineCount,
+    required int numberOfContexts,
+    required int transitiveFileCount,
+    required int transitiveFileLineCount,
+    required int transitiveFileUniqueCount,
+    required int transitiveFileUniqueLineCount,
+  })  : eventName = DashEvent.contextStructure,
+        eventData = {
+          'contextsFromBothFiles': contextsFromBothFiles,
+          'contextsFromOptionsFiles': contextsFromOptionsFiles,
+          'contextsFromPackagesFiles': contextsFromPackagesFiles,
+          'contextsWithoutFiles': contextsWithoutFiles,
+          'immediateFileCount': immediateFileCount,
+          'immediateFileLineCount': immediateFileLineCount,
+          'numberOfContexts': numberOfContexts,
+          'transitiveFileCount': transitiveFileCount,
+          'transitiveFileLineCount': transitiveFileLineCount,
+          'transitiveFileUniqueCount': transitiveFileUniqueCount,
+          'transitiveFileUniqueLineCount': transitiveFileUniqueLineCount,
+        };
+
+  /// Event that is emitted when a Dart CLI command has been executed.
+  ///
+  /// [name] - the name of the command that was executed
+  ///
+  /// [enabledExperiments] - a set of Dart language experiments enabled when
+  ///          running the command.
+  ///
+  /// [exitCode] - the process exit code set as a result of running the command.
+  Event.dartCliCommandExecuted({
+    required String name,
+    required String enabledExperiments,
+    int? exitCode,
+  })  : eventName = DashEvent.dartCliCommandExecuted,
+        eventData = {
+          'name': name,
+          'enabledExperiments': enabledExperiments,
+          if (exitCode != null) 'exitCode': exitCode,
+        };
+
+  /// Event that is sent from devtools for various different actions as
+  /// indicated by the [eventCategory].
+  Event.devtoolsEvent({
+    required String eventCategory,
+    required String label,
+    required int value,
+
+    // Defaulted values
+    bool userInitiatedInteraction = true,
+
+    // Optional parameters
+    String? g3Username,
+    String? userApp,
+    String? userBuild,
+    String? userPlatform,
+    String? devtoolsPlatform,
+    String? devtoolsChrome,
+    String? devtoolsVersion,
+    String? ideLaunched,
+    String? isExternalBuild,
+    String? isEmbedded,
+    String? ideLaunchedFeature,
+    String? isWasm,
+
+    // PerformanceScreenMetrics
+    int? uiDurationMicros,
+    int? rasterDurationMicros,
+    int? shaderCompilationDurationMicros,
+    int? traceEventCount,
+
+    // ProfilerScreenMetrics
+    int? cpuSampleCount,
+    int? cpuStackDepth,
+
+    // MemoryScreenMetrics
+    int? heapDiffObjectsBefore,
+    int? heapDiffObjectsAfter,
+    int? heapObjectsTotal,
+
+    // InspectorScreenMetrics
+    int? rootSetCount,
+    int? rowCount,
+    int? inspectorTreeControllerId,
+
+    // DeepLinkScreenMetrics
+    String? androidAppId,
+    String? iosBundleId,
+  })  : eventName = DashEvent.devtoolsEvent,
+        eventData = {
+          'eventCategory': eventCategory,
+          'label': label,
+          'value': value,
+
+          'userInitiatedInteraction': userInitiatedInteraction,
+
+          // Optional parameters
+          if (g3Username != null) 'g3Username': g3Username,
+          if (userApp != null) 'userApp': userApp,
+          if (userBuild != null) 'userBuild': userBuild,
+          if (userPlatform != null) 'userPlatform': userPlatform,
+          if (devtoolsPlatform != null) 'devtoolsPlatform': devtoolsPlatform,
+          if (devtoolsChrome != null) 'devtoolsChrome': devtoolsChrome,
+          if (devtoolsVersion != null) 'devtoolsVersion': devtoolsVersion,
+          if (ideLaunched != null) 'ideLaunched': ideLaunched,
+          if (isExternalBuild != null) 'isExternalBuild': isExternalBuild,
+          if (isEmbedded != null) 'isEmbedded': isEmbedded,
+          if (ideLaunchedFeature != null)
+            'ideLaunchedFeature': ideLaunchedFeature,
+          if (isWasm != null) 'isWasm': isWasm,
+
+          // PerformanceScreenMetrics
+          if (uiDurationMicros != null) 'uiDurationMicros': uiDurationMicros,
+          if (rasterDurationMicros != null)
+            'rasterDurationMicros': rasterDurationMicros,
+          if (shaderCompilationDurationMicros != null)
+            'shaderCompilationDurationMicros': shaderCompilationDurationMicros,
+          if (traceEventCount != null) 'traceEventCount': traceEventCount,
+
+          // ProfilerScreenMetrics
+          if (cpuSampleCount != null) 'cpuSampleCount': cpuSampleCount,
+          if (cpuStackDepth != null) 'cpuStackDepth': cpuStackDepth,
+
+          // MemoryScreenMetrics
+          if (heapDiffObjectsBefore != null)
+            'heapDiffObjectsBefore': heapDiffObjectsBefore,
+          if (heapDiffObjectsAfter != null)
+            'heapDiffObjectsAfter': heapDiffObjectsAfter,
+          if (heapObjectsTotal != null) 'heapObjectsTotal': heapObjectsTotal,
+
+          // InspectorScreenMetrics
+          if (rootSetCount != null) 'rootSetCount': rootSetCount,
+          if (rowCount != null) 'rowCount': rowCount,
+          if (inspectorTreeControllerId != null)
+            'inspectorTreeControllerId': inspectorTreeControllerId,
+          // DeepLinkScreenMetrics
+          if (androidAppId != null) 'androidAppId': androidAppId,
+          if (iosBundleId != null) 'iosBundleId': iosBundleId,
+        };
+
+  /// Event that contains the results for a specific doctor validator.
+  ///
+  /// [validatorName] - the name for the doctor validator.
+  ///
+  /// [result] - the final result for a specific doctor validator.
+  ///
+  /// [partOfGroupedValidator] - `true` indicates that this validator belongs
+  ///   to a grouped validator.
+  ///
+  /// [doctorInvocationId] - epoch formatted timestamp that can be used in
+  ///   combination with the client ID in GA4 to group the validators that
+  ///   ran in one doctor invocation.
+  ///
+  /// [statusInfo] - optional description of the result from the
+  ///   doctor validator.
+  Event.doctorValidatorResult({
+    required String validatorName,
+    required String result,
+    required bool partOfGroupedValidator,
+    required int doctorInvocationId,
+    String? statusInfo,
+  })  : eventName = DashEvent.doctorValidatorResult,
+        eventData = {
+          'validatorName': validatorName,
+          'result': result,
+          'partOfGroupedValidator': partOfGroupedValidator,
+          'doctorInvocationId': doctorInvocationId,
+          if (statusInfo != null) 'statusInfo': statusInfo,
+        };
+
+  /// Generic event for all dash tools to use when encountering an
+  /// exception that we want to log.
+  ///
+  /// [exception] - string representation of the exception that occured.
+  /// [data] - optional structured data to include with the exception event.
+  Event.exception({
+    required String exception,
+    Map<String, Object?> data = const <String, Object?>{},
+  })  : eventName = DashEvent.exception,
+        eventData = {
+          'exception': exception,
+          ...data,
+        };
+
+  /// Event that is emitted from the flutter tool when a build invocation
+  /// has been run by the user.
+  ///
+  /// [label] - the identifier for that build event.
+  ///
+  /// [buildType] - the identifier for which platform the build event was for,
+  ///   examples include "ios", "gradle", and "web".
+  ///
+  /// [command] - the command that was ran to kick off the build event.
+  ///
+  /// [settings] - the settings used for the build event related to
+  ///   configuration and other relevant build information.
+  ///
+  /// [error] - short identifier used to explain the cause of the build error,
+  ///   stacktraces should not be passed to this parameter.
+  Event.flutterBuildInfo({
+    required String label,
+    required String buildType,
+    String? command,
+    String? settings,
+    String? error,
+  })  : eventName = DashEvent.flutterBuildInfo,
+        eventData = {
+          'label': label,
+          'buildType': buildType,
+          if (command != null) 'command': command,
+          if (settings != null) 'settings': settings,
+          if (error != null) 'error': error,
+        };
+
+  /// Provides information about which flutter command was run
+  /// and whether it was successful.
+  ///
+  /// [commandPath] - information about the flutter command, such as "build/apk".
+  ///
+  /// [result] - if the command failed or succeeded.
+  ///
+  /// [commandHasTerminal] - boolean indicating if the flutter command ran with
+  ///   a terminal.
+  ///
+  /// [maxRss] - maximum resident size for a given flutter command.
+  Event.flutterCommandResult({
+    required String commandPath,
+    required String result,
+    required bool commandHasTerminal,
+    int? maxRss,
+  })  : eventName = DashEvent.flutterCommandResult,
+        eventData = {
+          'commandPath': commandPath,
+          'result': result,
+          'commandHasTerminal': commandHasTerminal,
+          if (maxRss != null) 'maxRss': maxRss,
+        };
+
+  // TODO: eliasyishak, remove this or replace once we have a generic
+  //  timing event that can be used by potentially more than one DashTool
+  Event.hotReloadTime({required int timeMs})
+      : eventName = DashEvent.hotReloadTime,
+        eventData = {'timeMs': timeMs};
+
+  /// Events to be sent for the Flutter Hot Runner.
+  Event.hotRunnerInfo({
+    required String label,
+    required String targetPlatform,
+    required String sdkName,
+    required bool emulator,
+    required bool fullRestart,
+    String? reason,
+    int? finalLibraryCount,
+    int? syncedLibraryCount,
+    int? syncedClassesCount,
+    int? syncedProceduresCount,
+    int? syncedBytes,
+    int? invalidatedSourcesCount,
+    int? transferTimeInMs,
+    int? overallTimeInMs,
+    int? compileTimeInMs,
+    int? findInvalidatedTimeInMs,
+    int? scannedSourcesCount,
+    int? reassembleTimeInMs,
+    int? reloadVMTimeInMs,
+  })  : eventName = DashEvent.hotRunnerInfo,
+        eventData = {
+          'label': label,
+          'targetPlatform': targetPlatform,
+          'sdkName': sdkName,
+          'emulator': emulator,
+          'fullRestart': fullRestart,
+          if (reason != null) 'reason': reason,
+          if (finalLibraryCount != null) 'finalLibraryCount': finalLibraryCount,
+          if (syncedLibraryCount != null)
+            'syncedLibraryCount': syncedLibraryCount,
+          if (syncedClassesCount != null)
+            'syncedClassesCount': syncedClassesCount,
+          if (syncedProceduresCount != null)
+            'syncedProceduresCount': syncedProceduresCount,
+          if (syncedBytes != null) 'syncedBytes': syncedBytes,
+          if (invalidatedSourcesCount != null)
+            'invalidatedSourcesCount': invalidatedSourcesCount,
+          if (transferTimeInMs != null) 'transferTimeInMs': transferTimeInMs,
+          if (overallTimeInMs != null) 'overallTimeInMs': overallTimeInMs,
+          if (compileTimeInMs != null) 'compileTimeInMs': compileTimeInMs,
+          if (findInvalidatedTimeInMs != null)
+            'findInvalidatedTimeInMs': findInvalidatedTimeInMs,
+          if (scannedSourcesCount != null)
+            'scannedSourcesCount': scannedSourcesCount,
+          if (reassembleTimeInMs != null)
+            'reassembleTimeInMs': reassembleTimeInMs,
+          if (reloadVMTimeInMs != null) 'reloadVMTimeInMs': reloadVMTimeInMs,
+        };
+
+  // TODO: eliasyishak, add better dartdocs to explain each param
+  /// Event that is emitted periodically to report the number of times each lint
+  /// has been enabled.
+  ///
+  /// [count] - the number of contexts in which the lint was enabled.
+  ///
+  /// [name] - the name of the lint.
+  Event.lintUsageCount({
+    required int count,
+    required String name,
+  })  : eventName = DashEvent.lintUsageCount,
+        eventData = {
+          'count': count,
+          'name': name,
+        };
+
+  /// Event that is emitted periodically to report the amount of memory being
+  /// used.
+  ///
+  /// [rss] - the resident set size in megabytes.
+  ///
+  /// If this is not the first time memory has been reported for this session,
+  /// then the following parameters should be included:
+  ///
+  /// [periodSec] - the number of seconds since the last memory usage data was
+  ///     gathered.
+  ///
+  /// [mbPerSec] - the number of megabytes of memory that were added or
+  ///     subtracted per second since the last report.
+  Event.memoryInfo({
+    required int rss,
+    int? periodSec,
+    double? mbPerSec,
+  })  : eventName = DashEvent.memoryInfo,
+        eventData = {
+          'rss': rss,
+          if (periodSec != null) 'periodSec': periodSec,
+          if (mbPerSec != null) 'mbPerSec': mbPerSec
+        };
+
+  /// Event that is emitted periodically to report the performance of plugins
+  /// when handling requests.
+  ///
+  /// [duration] - json encoded percentile values indicating how long it took
+  ///     from the time the request was sent to the plugin until the response
+  ///     was processed by the server.
+  ///
+  /// [method] - the name of the request sent to the plugin.
+  ///
+  /// [pluginId] - the id of the plugin whose performance is being reported.
+  Event.pluginRequest({
+    required String duration,
+    required String method,
+    required String pluginId,
+  })  : eventName = DashEvent.pluginRequest,
+        eventData = {
+          'duration': duration,
+          'method': method,
+          'pluginId': pluginId,
+        };
+
+  /// Event that is emitted periodically to report the frequency with which a
+  /// given plugin has been used.
+  ///
+  /// [count] - the number of times plugins usage was changed, which will always
+  ///     be at least one.
+  ///
+  /// [enabled] - json encoded percentile values indicating the number of
+  ///     contexts for which the plugin was enabled.
+  ///
+  /// [pluginId] - the id of the plugin associated with the data.
+  Event.pluginUse({
+    required int count,
+    required String enabled,
+    required String pluginId,
+  })  : eventName = DashEvent.pluginUse,
+        eventData = {
+          'count': count,
+          'enabled': enabled,
+          'pluginId': pluginId,
+        };
+
+  /// Event that is emitted when `pub get` is run.
+  ///
+  /// [packageName] - the name of the package that was resolved
+  ///
+  /// [version] - the resolved, canonicalized package version
+  ///
+  /// [dependencyType] - the kind of dependency that resulted in this package
+  ///     being resolved (e.g., direct, transitive, or dev dependencies).
+  Event.pubGet({
+    required String packageName,
+    required String version,
+    required String dependencyType,
+  })  : eventName = DashEvent.pubGet,
+        eventData = {
+          'packageName': packageName,
+          'version': version,
+          'dependencyType': dependencyType,
+        };
+
+  /// Event that is emitted on shutdown to report information about the whole
+  /// session for which the analysis server was running.
+  ///
+  /// [clientId] - the id of the client that started the server.
+  ///
+  /// [clientVersion] - the version of the client that started the server.
+  ///
+  /// [duration] - the number of milliseconds for which the server was running.
+  ///
+  /// [flags] - the flags passed to the analysis server on startup, without any
+  ///     argument values for flags that take values, or an empty string if
+  ///     there were no arguments.
+  ///
+  /// [parameters] - the names of the parameters passed to the `initialize`
+  ///     request, or an empty string if the `initialize` request was not sent
+  ///     or if there were no parameters given.
+  Event.serverSession({
+    required String clientId,
+    required String clientVersion,
+    required int duration,
+    required String flags,
+    required String parameters,
+  })  : eventName = DashEvent.serverSession,
+        eventData = {
+          'clientId': clientId,
+          'clientVersion': clientVersion,
+          'duration': duration,
+          'flags': flags,
+          'parameters': parameters,
+        };
+
+  /// Event that is emitted periodically to report the number of times the
+  /// severity of a diagnostic was changed in the analysis options file.
+  ///
+  /// [diagnostic] - the name of the diagnostic whose severity was changed.
+  ///
+  /// [adjustments] - json encoded map of severities to the number of times the
+  ///     diagnostic's severity was changed to the key.
+  Event.severityAdjustment({
+    required String diagnostic,
+    required String adjustments,
+  })  : eventName = DashEvent.severityAdjustment,
+        eventData = {
+          'diagnostic': diagnostic,
+          'adjustments': adjustments,
+        };
+
+  /// Event that is emitted by `package:unified_analytics` when
+  /// the user takes action when prompted with a survey.
+  ///
+  /// [surveyId] - the unique id for a given survey.
+  ///
+  /// [status] - the string identifier for a given `SurveyButton` under the
+  ///     `action` field.
+  Event.surveyAction({
+    required String surveyId,
+    required String status,
+  })  : eventName = DashEvent.surveyAction,
+        eventData = {
+          'surveyId': surveyId,
+          'status': status,
+        };
+
+  /// Event that is emitted by `package:unified_analytics` when the
+  /// user has been shown a survey.
+  ///
+  /// [surveyId] - the unique id for a given survey.
+  Event.surveyShown({
+    required String surveyId,
+  })  : eventName = DashEvent.surveyShown,
+        eventData = {
+          'surveyId': surveyId,
+        };
+
+  /// Event that records how long a given process takes to complete.
+  ///
+  /// [workflow] - the overall process or command being run, for example
+  ///   "build" is a possible value for the flutter tool.
+  ///
+  /// [variableName] - the specific variable being measured, for example
+  ///   "gradle" would indicate how long it took for a gradle build under the
+  ///   "build" [workflow].
+  ///
+  /// [elapsedMilliseconds] - how long the process took in milliseconds.
+  ///
+  /// [label] - an optional field that can be used for further filtering, for
+  ///   example, "success" can indicate how long a successful build in gradle
+  ///   takes to complete.
+  Event.timing({
+    required String workflow,
+    required String variableName,
+    required int elapsedMilliseconds,
+    String? label,
+  })  : eventName = DashEvent.timing,
+        eventData = {
+          'workflow': workflow,
+          'variableName': variableName,
+          'elapsedMilliseconds': elapsedMilliseconds,
+          if (label != null) 'label': label,
+        };
+
+  /// Private constructor to be used when deserializing JSON into an instance
+  /// of [Event].
+  Event._({required this.eventName, required this.eventData});
+
+  @override
+  int get hashCode => Object.hash(eventName, jsonEncode(eventData));
+
+  @override
+  bool operator ==(Object other) =>
+      other is Event &&
+      other.runtimeType == runtimeType &&
+      other.eventName == eventName &&
+      _compareEventData(other.eventData, eventData);
+
+  /// Converts an instance of [Event] to JSON.
+  String toJson() => jsonEncode({
+        'eventName': eventName.label,
+        'eventData': eventData,
+      });
+
+  @override
+  String toString() => toJson();
+
+  /// Utility function to take in two maps [a] and [b] and compares them
+  /// to ensure that they have the same keys and values
+  bool _compareEventData(Map<String, Object?> a, Map<String, Object?> b) {
+    final keySetA = a.keys.toSet();
+    final keySetB = b.keys.toSet();
+    final intersection = keySetA.intersection(keySetB);
+
+    // Ensure that the keys are the same for each object
+    if (intersection.length != keySetA.length ||
+        intersection.length != keySetB.length) {
+      return false;
+    }
+
+    // Ensure that each of the key's values are the same
+    for (final key in a.keys) {
+      if (a[key] != b[key]) return false;
+    }
+
+    return true;
+  }
+
+  /// Returns a valid instance of [Event] if [json] follows the correct schema.
+  ///
+  /// Common use case for this static method involves clients of this package
+  /// that have a client-server setup where the server sends events that the
+  /// client creates.
+  static Event? fromJson(String json) {
+    try {
+      final jsonMap = jsonDecode(json) as Map<String, Object?>;
+
+      // Ensure that eventName is a string and a valid label and
+      // eventData is a nested object
+      if (jsonMap
+          case {
+            'eventName': final String eventName,
+            'eventData': final Map<String, Object?> eventData,
+          }) {
+        final dashEvent = DashEvent.fromLabel(eventName);
+        if (dashEvent == null) return null;
+
+        return Event._(
+          eventName: dashEvent,
+          eventData: eventData,
+        );
+      }
+
+      return null;
+    } on FormatException {
+      return null;
+    }
+  }
+}
diff --git a/pkgs/unified_analytics/lib/src/ga_client.dart b/pkgs/unified_analytics/lib/src/ga_client.dart
new file mode 100644
index 0000000..2c3e83e
--- /dev/null
+++ b/pkgs/unified_analytics/lib/src/ga_client.dart
@@ -0,0 +1,86 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:convert';
+
+import 'package:http/http.dart' as http;
+
+import 'constants.dart';
+
+class FakeGAClient implements GAClient {
+  const FakeGAClient();
+
+  @override
+  String get apiSecret => throw UnimplementedError();
+
+  @override
+  String get measurementId => throw UnimplementedError();
+
+  @override
+  String get postUrl => throw UnimplementedError();
+
+  @override
+  http.Client get _client => throw UnimplementedError();
+
+  @override
+  void close() {}
+
+  @override
+  Future<http.Response> sendData(Map<String, Object?> body) =>
+      Future<http.Response>.value(http.Response('', 200));
+}
+
+class GAClient {
+  final String measurementId;
+  final String apiSecret;
+  final String postUrl;
+  final http.Client _client;
+
+  GAClient({
+    required this.measurementId,
+    required this.apiSecret,
+  })  : postUrl = '$kAnalyticsUrl?'
+            'measurement_id=$measurementId&api_secret=$apiSecret',
+        _client = http.Client();
+
+  /// Closes the http client's connection to prevent lingering requests.
+  void close() => _client.close();
+
+  /// Receive the payload in Map form and parse
+  /// into JSON to send to GA.
+  ///
+  /// The [http.Response] returned from this method can be
+  /// checked to ensure that events have been sent. A response
+  /// status code of `2xx` indicates a successful send event.
+  /// A response status code of `500` indicates an error occured on the send
+  /// can the error message can be found in the [http.Response.body].
+  Future<http.Response> sendData(Map<String, Object?> body) async {
+    final uri = Uri.parse(postUrl);
+
+    // Using a try catch all since post method can result in several
+    // errors; clients using this method can check the awaited status
+    // code to get a specific error message if the status code returned
+    // is a 500 error status code
+    try {
+      return await _client.post(
+        uri,
+        headers: <String, String>{
+          'Content-Type': 'application/json; charset=UTF-8',
+        },
+        body: jsonEncode(body),
+      );
+      // ignore: avoid_catches_without_on_clauses
+    } catch (error) {
+      return Future<http.Response>.value(
+        http.Response(
+          error.toString(),
+          500,
+          headers: <String, String>{
+            'content-type': 'text/plain; charset=utf-8',
+          },
+        ),
+      );
+    }
+  }
+}
diff --git a/pkgs/unified_analytics/lib/src/initializer.dart b/pkgs/unified_analytics/lib/src/initializer.dart
new file mode 100644
index 0000000..131968b
--- /dev/null
+++ b/pkgs/unified_analytics/lib/src/initializer.dart
@@ -0,0 +1,118 @@
+// Copyright (c) 2023, 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.
+
+import 'package:clock/clock.dart';
+import 'package:file/file.dart';
+
+import 'constants.dart';
+import 'utils.dart';
+
+/// Creates the text file that will contain the client ID
+/// which will be used across all related tools for analytics
+/// reporting in GA.
+void createClientIdFile({required File clientIdFile}) {
+  clientIdFile.createSync(recursive: true);
+  clientIdFile.writeAsStringSync(Uuid().generateV4());
+}
+
+/// Creates the configuration file with the default message
+/// in the user's home directory.
+void createConfigFile({
+  required File configFile,
+  required Directory homeDirectory,
+}) {
+  configFile.createSync(recursive: true);
+
+  // If the user was previously opted out, then we will
+  // replace the line that assumes automatic opt in with
+  // an opt out from the start
+  if (legacyOptOut(homeDirectory: homeDirectory)) {
+    configFile.writeAsStringSync(
+        kConfigString.replaceAll('reporting=1', 'reporting=0'));
+  } else {
+    configFile.writeAsStringSync(kConfigString);
+  }
+}
+
+/// Creates that file that will persist dismissed survey ids.
+void createDismissedSurveyFile({required File dismissedSurveyFile}) {
+  dismissedSurveyFile.createSync(recursive: true);
+  dismissedSurveyFile.writeAsStringSync('{}');
+}
+
+/// Creates that log file that will store the record formatted
+/// events locally on the user's machine.
+void createLogFile({required File logFile}) {
+  logFile.createSync(recursive: true);
+}
+
+/// Creates the session file which will contain
+/// the current session id which is the current timestamp.
+///
+/// It also returns the timestamp used for the session if it needs
+/// to be accessed.
+DateTime createSessionFile({required File sessionFile}) {
+  final now = clock.now();
+  sessionFile.createSync(recursive: true);
+  writeSessionContents(sessionFile: sessionFile);
+
+  return now;
+}
+
+/// Performs all of the initialization checks for the required files.
+///
+/// Returns `true` if the config file was created indicating it is the first
+/// time this package was run on a user's machine.
+///
+/// Checks for the following:
+/// - Config file
+/// - Client ID file
+/// - Session JSON file
+/// - Log file
+/// - Dismissed survey JSON file
+bool runInitialization({
+  required Directory homeDirectory,
+}) {
+  var firstRun = false;
+  final dartToolDirectory =
+      homeDirectory.childDirectory(kDartToolDirectoryName);
+
+  // When the config file doesn't exist, initialize it with the default tools
+  // and the current date.
+  final configFile = dartToolDirectory.childFile(kConfigFileName);
+  if (!configFile.existsSync()) {
+    firstRun = true;
+    createConfigFile(
+      configFile: configFile,
+      homeDirectory: homeDirectory,
+    );
+  }
+
+  // Begin initialization checks for the client id.
+  final clientFile = dartToolDirectory.childFile(kClientIdFileName);
+  if (!clientFile.existsSync()) {
+    createClientIdFile(clientIdFile: clientFile);
+  }
+
+  // Begin initialization checks for the session file.
+  final sessionFile = dartToolDirectory.childFile(kSessionFileName);
+  if (!sessionFile.existsSync()) {
+    createSessionFile(sessionFile: sessionFile);
+  }
+
+  // Begin initialization checks for the log file to persist events locally.
+  final logFile = dartToolDirectory.childFile(kLogFileName);
+  if (!logFile.existsSync()) {
+    createLogFile(logFile: logFile);
+  }
+
+  // Begin initialization checks for the dismissed survey file.
+  final dismissedSurveyFile =
+      dartToolDirectory.childFile(kDismissedSurveyFileName);
+  if (!dismissedSurveyFile.existsSync()) {
+    createDismissedSurveyFile(dismissedSurveyFile: dismissedSurveyFile);
+  }
+
+  return firstRun;
+}
diff --git a/pkgs/unified_analytics/lib/src/log_handler.dart b/pkgs/unified_analytics/lib/src/log_handler.dart
new file mode 100644
index 0000000..a6ef2f5
--- /dev/null
+++ b/pkgs/unified_analytics/lib/src/log_handler.dart
@@ -0,0 +1,464 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:convert';
+
+import 'package:clock/clock.dart';
+import 'package:file/file.dart';
+
+import 'constants.dart';
+import 'event.dart';
+import 'initializer.dart';
+
+/// Data class that will be returned when analyzing the
+/// persisted log file on the client's machine.
+class LogFileStats {
+  /// The oldest timestamp in the log file.
+  final DateTime startDateTime;
+
+  /// Number of minutes from [startDateTime] to now using [clock].
+  final int minsFromStartDateTime;
+
+  /// The latest timestamp in the log file.
+  final DateTime endDateTime;
+
+  /// Number of minutes from [endDateTime] to now using [clock].
+  final int minsFromEndDateTime;
+
+  /// The number of unique session ids found in the log file.
+  final int sessionCount;
+
+  /// The map containing all of the flutter channels and a count
+  /// of how many events were under each channel.
+  ///
+  /// ```
+  /// {
+  ///   'stable': 123,
+  ///   'beta': 50,
+  ///   'master': 5,
+  /// }
+  /// ```
+  final Map<String, int> flutterChannelCount;
+
+  /// The map containing all of the tools that have sent events
+  /// and how many events were sent by each tool.
+  ///
+  /// ```
+  /// {
+  ///   'flutter-tool': 500,
+  ///   'dart-tool': 45,
+  ///   'vscode-plugins': 321,
+  /// }
+  /// ```
+  final Map<String, int> toolCount;
+
+  /// The map containing all of the events in the file along with
+  /// how many times they have occured.
+  ///
+  /// ```
+  /// {
+  ///   'client_request': 345,
+  ///   'hot_reload_time': 765,
+  ///   'memory_info': 90,
+  /// }
+  /// ```
+  final Map<String, int> eventCount;
+
+  /// Total number of records in the log file.
+  final int recordCount;
+
+  /// Contains the data from the [LogHandler.logFileStats] method.
+  const LogFileStats({
+    required this.startDateTime,
+    required this.minsFromStartDateTime,
+    required this.endDateTime,
+    required this.minsFromEndDateTime,
+    required this.sessionCount,
+    required this.flutterChannelCount,
+    required this.toolCount,
+    required this.recordCount,
+    required this.eventCount,
+  });
+
+  /// Pass in a string label for one of the instance variables
+  /// and return the integer value of that label.
+  ///
+  /// If label passed for [DateTime] instance variable, integer
+  /// in the form of [DateTime.millisecondsSinceEpoch] will be
+  /// returned.
+  ///
+  /// Returns null if the label passed does not match anything.
+  int? getValueByString(String label) {
+    // When querying counts, the label will include the
+    // key for the appropriate map
+    //
+    // Example: logFileStats.toolCount.flutter-tool is asking
+    //   for the number of events sent via flutter cli
+    final parts = label.split('.');
+    String? key;
+    if (parts.length >= 3) {
+      // Assign the first two parts of the string as the label
+      // ie. logFileStats.toolCount.flutter-tool -> logFileStats.toolCount
+      label = parts.sublist(0, 2).join('.');
+      key = parts.sublist(2, parts.length).join('.');
+    }
+
+    switch (label) {
+      case 'logFileStats.startDateTime':
+        return startDateTime.millisecondsSinceEpoch;
+      case 'logFileStats.minsFromStartDateTime':
+        return minsFromStartDateTime;
+      case 'logFileStats.endDateTime':
+        return endDateTime.millisecondsSinceEpoch;
+      case 'logFileStats.minsFromEndDateTime':
+        return minsFromEndDateTime;
+      case 'logFileStats.sessionCount':
+        return sessionCount;
+      case 'logFileStats.recordCount':
+        return recordCount;
+      case 'logFileStats.flutterChannelCount':
+        if (key != null && flutterChannelCount.containsKey(key)) {
+          return flutterChannelCount[key];
+        }
+      case 'logFileStats.toolCount':
+        if (key != null && toolCount.containsKey(key)) {
+          return toolCount[key];
+        }
+      case 'logFileStats.eventCount':
+        if (key != null && eventCount.containsKey(key)) {
+          return eventCount[key];
+        }
+    }
+
+    return null;
+  }
+
+  @override
+  String toString() {
+    const encoder = JsonEncoder.withIndent('  ');
+    return encoder.convert({
+      'startDateTime': startDateTime.toString(),
+      'minsFromStartDateTime': minsFromStartDateTime,
+      'endDateTime': endDateTime.toString(),
+      'minsFromEndDateTime': minsFromEndDateTime,
+      'sessionCount': sessionCount,
+      'recordCount': recordCount,
+      'eventCount': eventCount,
+      'toolCount': toolCount,
+      'flutterChannelCount': flutterChannelCount,
+    });
+  }
+}
+
+/// This class is responsible for writing to a log
+/// file that has been initialized by the [createLogFile].
+///
+/// It will be treated as an append only log and will be limited
+/// to have has many data records as specified by [kLogFileLength].
+class LogHandler {
+  final File logFile;
+
+  /// Contains instances of [Event.analyticsException] that were encountered
+  /// during a workflow and will be sent to GA4 for collection.
+  final Set<Event> errorSet = {};
+
+  /// A log handler constructor that will delegate saving
+  /// logs and retrieving stats from the persisted log.
+  LogHandler({required this.logFile});
+
+  /// Get stats from the persisted log file.
+  ///
+  /// Note that some developers may only be Dart
+  /// developers and will not have any data for flutter
+  /// related metrics.
+  LogFileStats? logFileStats() {
+    // Parse each line of the log file through [LogItem],
+    // some returned records may be null if malformed, they will be
+    // removed later through `whereType<LogItem>`
+    final records = logFile
+        .readAsLinesSync()
+        .map((String e) {
+          try {
+            return LogItem.fromRecord(jsonDecode(e) as Map<String, Object?>);
+          } on FormatException catch (err) {
+            errorSet.add(Event.analyticsException(
+              workflow: 'LogFileStats.logFileStats',
+              error: err.runtimeType.toString(),
+              description: 'message: ${err.message}\nsource: ${err.source}',
+            ));
+
+            return null;
+            // ignore: avoid_catching_errors
+          } on TypeError catch (err) {
+            errorSet.add(Event.analyticsException(
+              workflow: 'LogFileStats.logFileStats',
+              error: err.runtimeType.toString(),
+            ));
+
+            return null;
+          }
+        })
+        .whereType<LogItem>()
+        .toList();
+
+    if (records.isEmpty) return null;
+
+    // Get the start and end dates for the log file
+    final startDateTime = records.first.localTime;
+    final endDateTime = records.last.localTime;
+
+    // Map with counters for user properties
+    final counter = <String, Set<Object>>{
+      'sessions': <int>{},
+      'flutter_channel': <String>{},
+      'tool': <String>{},
+    };
+
+    // Map of counters for each event
+    final eventCount = <String, int>{};
+    final flutterChannelCount = <String, int>{};
+    final toolCount = <String, int>{};
+    for (final record in records) {
+      counter['sessions']!.add(record.sessionId);
+      counter['tool']!.add(record.tool);
+      if (record.flutterChannel != null) {
+        counter['flutter_channel']!.add(record.flutterChannel!);
+      }
+
+      // Count each event, if it doesn't exist in the [eventCount]
+      // it will be added first
+      if (!eventCount.containsKey(record.eventName)) {
+        eventCount[record.eventName] = 0;
+      }
+      eventCount[record.eventName] = eventCount[record.eventName]! + 1;
+
+      // Counting how many events were recorded for each tool
+      if (!toolCount.containsKey(record.tool)) {
+        toolCount[record.tool] = 0;
+      }
+      toolCount[record.tool] = toolCount[record.tool]! + 1;
+
+      // Necessary to perform a null check for flutter channel because
+      // not all events will have information about flutter
+      if (record.flutterChannel != null) {
+        final flutterChannel = record.flutterChannel!;
+        if (!flutterChannelCount.containsKey(flutterChannel)) {
+          flutterChannelCount[flutterChannel] = 0;
+        }
+
+        flutterChannelCount[flutterChannel] =
+            flutterChannelCount[flutterChannel]! + 1;
+      }
+    }
+
+    final now = clock.now();
+
+    return LogFileStats(
+      startDateTime: startDateTime,
+      minsFromStartDateTime: now.difference(startDateTime).inMinutes,
+      endDateTime: endDateTime,
+      minsFromEndDateTime: now.difference(endDateTime).inMinutes,
+      sessionCount: counter['sessions']!.length,
+      flutterChannelCount: flutterChannelCount,
+      toolCount: toolCount,
+      eventCount: eventCount,
+      recordCount: records.length,
+    );
+  }
+
+  /// Saves the data passed in as a single line in the log file.
+  ///
+  /// This will keep the max number of records limited to equal to
+  /// or less than [kLogFileLength] records.
+  void save({required Map<String, Object?> data}) {
+    try {
+      final stat = logFile.statSync();
+      List<String> records;
+      if (stat.size > kMaxLogFileSize) {
+        logFile.deleteSync();
+        logFile.createSync();
+        records = [];
+      } else {
+        records = logFile.readAsLinesSync();
+      }
+      final content = '${jsonEncode(data)}\n';
+
+      // When the record count is less than the max, add as normal;
+      // else drop the oldest records until equal to max
+      if (records.length < kLogFileLength) {
+        logFile.writeAsStringSync(content, mode: FileMode.writeOnlyAppend);
+      } else {
+        records.add(content);
+        records = records.skip(records.length - kLogFileLength).toList();
+
+        logFile.writeAsStringSync(records.join('\n'));
+      }
+    } on FileSystemException {
+      // Logging isn't important enough to warrant raising a
+      // FileSystemException that will surprise consumers of this package.
+    }
+  }
+}
+
+/// Data class for each record persisted on the client's machine.
+class LogItem {
+  final String eventName;
+  final int sessionId;
+  final String? flutterChannel;
+  final String host;
+  final String? flutterVersion;
+  final String dartVersion;
+  final String tool;
+  final DateTime localTime;
+  final String hostOsVersion;
+  final String locale;
+  final String? clientIde;
+
+  LogItem({
+    required this.eventName,
+    required this.sessionId,
+    this.flutterChannel,
+    required this.host,
+    this.flutterVersion,
+    required this.dartVersion,
+    required this.tool,
+    required this.localTime,
+    required this.hostOsVersion,
+    required this.locale,
+    required this.clientIde,
+  });
+
+  /// Serves a parser for each record in the log file.
+  ///
+  /// Using this method guarantees that we have parsed out
+  /// fields that are necessary for the [LogHandler.logFileStats]
+  /// method.
+  ///
+  /// If the returned value is null, that indicates a malformed
+  /// record which can be discarded during analysis.
+  ///
+  /// Example of what a record looks like:
+  /// ```
+  /// {
+  ///     "client_id": "ffcea97b-db5e-4c66-98c2-3942de4fac40",
+  ///     "events": [
+  ///         {
+  ///             "name": "hot_reload_time",
+  ///             "params": {
+  ///                 "timeMs": 135
+  ///             }
+  ///         }
+  ///     ],
+  ///     "user_properties": {
+  ///         "session_id": {
+  ///             "value": 1699385899950
+  ///         },
+  ///         "flutter_channel": {
+  ///             "value": "ey-test-channel"
+  ///         },
+  ///         "host": {
+  ///             "value": "macOS"
+  ///         },
+  ///         "flutter_version": {
+  ///             "value": "Flutter 3.6.0-7.0.pre.47"
+  ///         },
+  ///         "dart_version": {
+  ///             "value": "Dart 2.19.0"
+  ///         },
+  ///         "analytics_pkg_version": {
+  ///             "value": "5.2.0"
+  ///         },
+  ///         "tool": {
+  ///             "value": "flutter-tool"
+  ///         },
+  ///         "local_time": {
+  ///             "value": "2023-11-07 15:09:03.025559 -0500"
+  ///         },
+  ///         "host_os_version": {
+  ///             "value": "Version 14.1 (Build 23B74)"
+  ///         },
+  ///         "locale": {
+  ///             "value": "en"
+  ///         },
+  ///         "clientIde": {
+  ///             "value": "VSCode"
+  ///         }
+  ///     }
+  /// }
+  /// ```
+  static LogItem? fromRecord(Map<String, Object?> record) {
+    if (!record.containsKey('user_properties') ||
+        !record.containsKey('events')) {
+      return null;
+    }
+
+    // Parse out values from the top level key = 'events' and return
+    // a map for the one event in the value
+    final eventProp =
+        (record['events']! as List<Object?>).first as Map<String, Object?>;
+    final eventName = eventProp['name'] as String;
+
+    // Parse the data out of the `user_properties` value
+    final userProps = record['user_properties'] as Map<String, Object?>;
+
+    // Parse out the values from the top level key = 'user_properties`
+    final sessionId =
+        (userProps['session_id']! as Map<String, Object?>)['value'] as int?;
+    final flutterChannel = (userProps['flutter_channel']!
+        as Map<String, Object?>)['value'] as String?;
+    final host =
+        (userProps['host']! as Map<String, Object?>)['value'] as String?;
+    final flutterVersion = (userProps['flutter_version']!
+        as Map<String, Object?>)['value'] as String?;
+    final dartVersion = (userProps['dart_version']!
+        as Map<String, Object?>)['value'] as String?;
+    final tool =
+        (userProps['tool']! as Map<String, Object?>)['value'] as String?;
+    final localTimeString =
+        (userProps['local_time']! as Map<String, Object?>)['value'] as String?;
+    final hostOsVersion = (userProps['host_os_version']!
+        as Map<String, Object?>)['value'] as String?;
+    final locale =
+        (userProps['locale']! as Map<String, Object?>)['value'] as String?;
+    final clientIde =
+        (userProps['client_ide']! as Map<String, Object?>)['value'] as String?;
+
+    // If any of the above values are null, return null since that
+    // indicates the record is malformed; note that `flutter_version`,
+    // `flutter_channel`, and `client_ide` are nullable fields in the log file
+    final values = <Object?>[
+      // Values associated with the top level key = 'events'
+      eventName,
+
+      // Values associated with the top level key = 'events'
+      sessionId,
+      host,
+      dartVersion,
+      tool,
+      localTimeString,
+      hostOsVersion,
+      locale,
+    ];
+    for (final value in values) {
+      if (value == null) return null;
+    }
+
+    // Parse the local time from the string extracted
+    final localTime = DateTime.parse(localTimeString!).toLocal();
+
+    return LogItem(
+      eventName: eventName,
+      sessionId: sessionId!,
+      flutterChannel: flutterChannel,
+      host: host!,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion!,
+      tool: tool!,
+      localTime: localTime,
+      hostOsVersion: hostOsVersion!,
+      locale: locale!,
+      clientIde: clientIde,
+    );
+  }
+}
diff --git a/pkgs/unified_analytics/lib/src/survey_handler.dart b/pkgs/unified_analytics/lib/src/survey_handler.dart
new file mode 100644
index 0000000..7461dfc
--- /dev/null
+++ b/pkgs/unified_analytics/lib/src/survey_handler.dart
@@ -0,0 +1,366 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:convert';
+
+import 'package:clock/clock.dart';
+import 'package:file/file.dart';
+import 'package:http/http.dart' as http;
+
+import 'constants.dart';
+import 'enums.dart';
+import 'initializer.dart';
+import 'log_handler.dart';
+
+class Condition {
+  /// How to query the log file.
+  ///
+  ///
+  /// Example: logFileStats.recordCount refers to the
+  /// total record count being returned by [LogFileStats].
+  final String field;
+
+  /// String representation of operator.
+  ///
+  ///
+  /// Allowed values:
+  /// - '>=' `greater than or equal to`
+  /// - '<=' `less than or equal to`
+  /// - '>' `greater than`
+  /// - '<' `less then`
+  /// - '==' `equals`
+  /// - '!=' `not equal`
+  final String operatorString;
+
+  /// The value we will be comparing against using the [operatorString].
+  final int value;
+
+  /// One of the conditions that need to be valid for
+  /// a survey to be returned to the user.
+  ///
+  /// Example of raw json:
+  /// ```
+  /// {
+  /// 	"field": "logFileStats.recordCount",
+  /// 	"operator": ">=",
+  /// 	"value": 1000
+  /// }
+  /// ```
+  Condition(
+    this.field,
+    this.operatorString,
+    this.value,
+  );
+
+  Condition.fromJson(Map<String, dynamic> json)
+      : field = json['field'] as String,
+        operatorString = json['operator'] as String,
+        value = json['value'] as int;
+
+  Map<String, Object?> toMap() => <String, Object?>{
+        'field': field,
+        'operator': operatorString,
+        'value': value,
+      };
+
+  @override
+  String toString() => jsonEncode(toMap());
+}
+
+/// Data class for the persisted survey contents.
+///
+/// [uniqueId] is the identifier for each survey, [timestamp] refers
+/// to when the survey was added to the persisted file.
+///
+/// The boolean [snoozed] is set to `true` if the survey has been dismissed
+/// temporarily by the user. When set to `false` this indicates that the survey
+/// has been dismissed permanently and will not be shown to the user again.
+class PersistedSurvey {
+  final String uniqueId;
+  final bool snoozed;
+  final DateTime timestamp;
+
+  PersistedSurvey({
+    required this.uniqueId,
+    required this.snoozed,
+    required this.timestamp,
+  });
+
+  @override
+  String toString() => jsonEncode({
+        'uniqueId': uniqueId,
+        'snoozed': snoozed,
+        'timestamp': timestamp.toString(),
+      });
+}
+
+class Survey {
+  final String uniqueId;
+  final DateTime startDate;
+  final DateTime endDate;
+  final String description;
+  final int snoozeForMinutes;
+  final double samplingRate;
+  final List<DashTool> excludeDashToolList;
+  final List<Condition> conditionList;
+  final List<SurveyButton> buttonList;
+
+  /// A data class that contains the relevant information for a given
+  /// survey parsed from the survey's metadata file.
+  const Survey({
+    required this.uniqueId,
+    required this.startDate,
+    required this.endDate,
+    required this.description,
+    required this.snoozeForMinutes,
+    required this.samplingRate,
+    required this.excludeDashToolList,
+    required this.conditionList,
+    required this.buttonList,
+  });
+
+  /// Parse the contents of the json metadata file hosted externally.
+  Survey.fromJson(Map<String, dynamic> json)
+      : uniqueId = json['uniqueId'] as String,
+        startDate = DateTime.parse(json['startDate'] as String),
+        endDate = DateTime.parse(json['endDate'] as String),
+        description = json['description'] as String,
+        // Handle both string and integer fields
+        snoozeForMinutes = json['snoozeForMinutes'] is String
+            ? int.parse(json['snoozeForMinutes'] as String)
+            : json['snoozeForMinutes'] as int,
+        // Handle both string and double fields
+        samplingRate = json['samplingRate'] is String
+            ? double.parse(json['samplingRate'] as String)
+            : json['samplingRate'] as double,
+        excludeDashToolList = (json['excludeDashTools'] as List<dynamic>)
+            .map((e) => DashTool.fromLabel(e as String))
+            .toList(),
+        conditionList = (json['conditions'] as List<dynamic>).map((e) {
+          return Condition.fromJson(e as Map<String, dynamic>);
+        }).toList(),
+        buttonList = (json['buttons'] as List<dynamic>).map((e) {
+          return SurveyButton.fromJson(e as Map<String, dynamic>);
+        }).toList();
+
+  @override
+  String toString() {
+    const encoder = JsonEncoder.withIndent('  ');
+    return encoder.convert({
+      'uniqueId': uniqueId,
+      'startDate': startDate.toString(),
+      'endDate': endDate.toString(),
+      'description': description,
+      'snoozeForMinutes': snoozeForMinutes,
+      'samplingRate': samplingRate,
+      'conditionList': conditionList.map((e) => e.toMap()).toList(),
+      'buttonList': buttonList.map((e) => e.toMap()).toList(),
+    });
+  }
+}
+
+class SurveyButton {
+  final String buttonText;
+  final String action;
+  final bool promptRemainsVisible;
+  final String? url;
+
+  SurveyButton({
+    required this.buttonText,
+    required this.action,
+    required this.promptRemainsVisible,
+    this.url,
+  });
+
+  SurveyButton.fromJson(Map<String, dynamic> json)
+      : buttonText = json['buttonText'] as String,
+        action = json['action'] as String,
+        promptRemainsVisible = json['promptRemainsVisible'] as bool,
+        url = json['url'] as String?;
+
+  Map<String, Object?> toMap() => <String, Object?>{
+        'buttonText': buttonText,
+        'action': action,
+        'promptRemainsVisible': promptRemainsVisible,
+        'url': url,
+      };
+}
+
+class SurveyHandler {
+  final File dismissedSurveyFile;
+
+  SurveyHandler({required this.dismissedSurveyFile});
+
+  /// Invoking this method will persist the survey's id in
+  /// the local file with either a snooze or permanently dismissed
+  /// indicator.
+  ///
+  /// In the snoozed state, the survey will be prompted again after
+  /// the survey's specified snooze period.
+  ///
+  /// Each entry for a survey will have the following format:
+  /// ```
+  /// {
+  ///   "survey-unique-id": {
+  ///     "status": "snoozed",  // status is either snoozed or dismissed
+  ///     "timestamp": 1690219834859
+  ///   }
+  /// }
+  /// ```
+  void dismiss(Survey survey, bool permanently) {
+    final contents = _parseJsonFile();
+
+    // Add the new data and write back out to the file
+    final status = permanently ? 'dismissed' : 'snoozed';
+    contents[survey.uniqueId] = {
+      'status': status,
+      'timestamp': clock.now().millisecondsSinceEpoch,
+    };
+
+    dismissedSurveyFile.writeAsStringSync(jsonEncode(contents));
+  }
+
+  /// Retrieve a list of strings for each [Survey] persisted on disk.
+  ///
+  /// The survey may be in a snoozed or dismissed state based on user action.
+  Map<String, PersistedSurvey> fetchPersistedSurveys() {
+    final contents = _parseJsonFile();
+
+    // Initialize the list of persisted surveys and add to them
+    // as they are being parsed
+    final persistedSurveys = <String, PersistedSurvey>{};
+    contents.forEach((key, value) {
+      value as Map<String, dynamic>;
+
+      final uniqueId = key;
+      final snoozed = value['status'] == 'snoozed' ? true : false;
+      final timestamp =
+          DateTime.fromMillisecondsSinceEpoch(value['timestamp'] as int);
+
+      persistedSurveys[uniqueId] = PersistedSurvey(
+        uniqueId: uniqueId,
+        snoozed: snoozed,
+        timestamp: timestamp,
+      );
+    });
+
+    return persistedSurveys;
+  }
+
+  /// Retrieves the survey metadata file from [kContextualSurveyUrl].
+  Future<List<Survey>> fetchSurveyList() async {
+    final List<dynamic> body;
+    try {
+      final payload = await _fetchContents();
+      body = jsonDecode(payload) as List<dynamic>;
+      // ignore: avoid_catches_without_on_clauses
+    } catch (err) {
+      return [];
+    }
+
+    final surveyList = parseSurveysFromJson(body);
+
+    return surveyList;
+  }
+
+  /// Fetches the json in string form from the remote location.
+  Future<String> _fetchContents() async {
+    final uri = Uri.parse(kContextualSurveyUrl);
+    final response = await http.get(uri);
+    return response.body;
+  }
+
+  /// Method to return a Map representation of the json persisted file.
+  Map<String, dynamic> _parseJsonFile() {
+    Map<String, dynamic> contents;
+    try {
+      contents = jsonDecode(dismissedSurveyFile.readAsStringSync())
+          as Map<String, dynamic>;
+    } on FormatException {
+      createDismissedSurveyFile(dismissedSurveyFile: dismissedSurveyFile);
+      contents = {};
+    } on FileSystemException {
+      createDismissedSurveyFile(dismissedSurveyFile: dismissedSurveyFile);
+      contents = {};
+    }
+
+    return contents;
+  }
+
+  /// Function to ensure that each survey is still valid by
+  /// checking the [Survey.startDate] and [Survey.endDate]
+  /// against the current [clock] now date.
+  static bool checkSurveyDate(Survey survey) {
+    final now = clock.now();
+    return survey.startDate.isBefore(now) && survey.endDate.isAfter(now);
+  }
+
+  /// Function that takes in a json data structure that is in
+  /// the form of a list and returns a list of [Survey] items.
+  ///
+  /// This will also check the survey's dates to make sure it
+  /// has not expired.
+  static List<Survey> parseSurveysFromJson(List<dynamic> body) => body
+      .map((element) {
+        // Error handling to skip any surveys from the remote location
+        // that fail to parse
+        try {
+          return Survey.fromJson(element as Map<String, dynamic>);
+          // ignore: avoid_catching_errors
+        } on TypeError {
+          return null;
+        } on FormatException {
+          return null;
+        } on Exception {
+          return null;
+        }
+      })
+      .whereType<Survey>()
+      .where(checkSurveyDate)
+      .toList();
+}
+
+class FakeSurveyHandler extends SurveyHandler {
+  final List<Survey> _fakeInitializedSurveys = [];
+
+  /// Use this class in tests if you can provide the
+  /// list of [Survey] objects.
+  ///
+  /// Important: the surveys in the [initializedSurveys] list
+  /// will have their dates checked to ensure they are valid; it is
+  /// recommended to use `package:clock` to set a fixed time for testing.
+  FakeSurveyHandler.fromList({
+    required super.dismissedSurveyFile,
+    required List<Survey> initializedSurveys,
+  }) {
+    // We must pass the surveys from the list to the
+    // `checkSurveyDate` function here and not for the
+    // `.fromString()` constructor because the `parseSurveysFromJson`
+    // method already checks their date
+    for (final survey in initializedSurveys) {
+      if (SurveyHandler.checkSurveyDate(survey)) {
+        _fakeInitializedSurveys.add(survey);
+      }
+    }
+  }
+
+  /// Use this class in tests if you can provide raw
+  /// json strings to simulate a response from a remote server.
+  FakeSurveyHandler.fromString({
+    required super.dismissedSurveyFile,
+    required String content,
+  }) {
+    final body = jsonDecode(content) as List<dynamic>;
+    for (final fakeSurvey in SurveyHandler.parseSurveysFromJson(body)) {
+      _fakeInitializedSurveys.add(fakeSurvey);
+    }
+  }
+
+  @override
+  Future<List<Survey>> fetchSurveyList() =>
+      Future<List<Survey>>.value(_fakeInitializedSurveys);
+
+  @override
+  Future<String> _fetchContents() => throw UnimplementedError();
+}
diff --git a/pkgs/unified_analytics/lib/src/user_property.dart b/pkgs/unified_analytics/lib/src/user_property.dart
new file mode 100644
index 0000000..f0e177d
--- /dev/null
+++ b/pkgs/unified_analytics/lib/src/user_property.dart
@@ -0,0 +1,162 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:convert';
+
+import 'package:clock/clock.dart';
+import 'package:file/file.dart';
+
+import 'constants.dart';
+import 'event.dart';
+import 'initializer.dart';
+import 'utils.dart';
+
+class UserProperty {
+  final String? flutterChannel;
+  final String host;
+  final String? flutterVersion;
+  final String dartVersion;
+  final String tool;
+  final String hostOsVersion;
+  final String locale;
+  final String? clientIde;
+  final String? enabledFeatures;
+
+  final File sessionFile;
+
+  /// Contains instances of [Event.analyticsException] that were encountered
+  /// during a workflow and will be sent to GA4 for collection.
+  final Set<Event> errorSet = {};
+
+  int? _sessionId;
+
+  /// This class is intended to capture all of the user's
+  /// metadata when the class gets initialized as well as collecting
+  /// session data to send in the json payload to Google Analytics.
+  UserProperty({
+    required this.flutterChannel,
+    required this.host,
+    required this.flutterVersion,
+    required this.dartVersion,
+    required this.tool,
+    required this.hostOsVersion,
+    required this.locale,
+    required this.clientIde,
+    required this.enabledFeatures,
+    required this.sessionFile,
+  });
+
+  /// This will use the data parsed from the
+  /// session file in the dart-tool directory
+  /// to get the session id if the last ping was within
+  /// [kSessionDurationMinutes].
+  ///
+  /// If time since last ping exceeds the duration, then the file
+  /// will be updated with a new session id and that will be returned.
+  ///
+  /// Note, the file will always be updated when calling this method
+  /// because the last ping variable will always need to be persisted.
+  int? getSessionId() {
+    _refreshSessionData();
+    final now = clock.now();
+
+    // Convert the epoch time from the last ping into datetime and check if we
+    // are within the kSessionDurationMinutes.
+    final lastPingDateTime = sessionFile.lastModifiedSync();
+    if (now.difference(lastPingDateTime).inMinutes > kSessionDurationMinutes) {
+      // Update the session file with the latest session id
+      _sessionId = now.millisecondsSinceEpoch;
+      writeSessionContents(sessionFile: sessionFile);
+    } else {
+      // Update the last modified timestamp with the current timestamp so that
+      // we can use it for the next _lastPing calculation
+      sessionFile.setLastModifiedSync(now);
+    }
+
+    return _sessionId;
+  }
+
+  /// This method will take the data in this class and convert it into
+  /// a Map that is suitable for the POST request schema.
+  ///
+  /// This will call the [UserProperty] object's [UserProperty.getSessionId]
+  /// method which will update the session file and get a new session id
+  /// if necessary.
+  ///
+  /// https://developers.google.com/analytics/devguides/collection/protocol/ga4/user-properties?client_type=gtag
+  Map<String, Map<String, Object?>> preparePayload() {
+    return <String, Map<String, Object?>>{
+      for (final entry in _toMap().entries)
+        entry.key: <String, Object?>{'value': entry.value}
+    };
+  }
+
+  @override
+  String toString() {
+    return jsonEncode(_toMap());
+  }
+
+  /// This will go to the session file within the dart-tool
+  /// directory and fetch the latest data from the session file to update
+  /// the class's variables. If the session file is malformed, a new
+  /// session file will be recreated.
+  ///
+  /// This allows the session data in this class to always be up
+  /// to date incase another tool is also calling this package and
+  /// making updates to the session file.
+  void _refreshSessionData() {
+    /// Using a nested function here to reduce verbosity
+    void parseContents() {
+      final sessionFileContents = sessionFile.readAsStringSync();
+      final sessionObj =
+          jsonDecode(sessionFileContents) as Map<String, Object?>;
+      _sessionId = sessionObj['session_id'] as int;
+    }
+
+    try {
+      // Failing to parse the contents will result in the current timestamp
+      // being used as the session id and will get used to recreate the file
+      parseContents();
+    } on FormatException catch (err) {
+      final now = createSessionFile(sessionFile: sessionFile);
+
+      errorSet.add(Event.analyticsException(
+        workflow: 'UserProperty._refreshSessionData',
+        error: err.runtimeType.toString(),
+        description: 'message: ${err.message}\nsource: ${err.source}',
+      ));
+
+      // Fallback to setting the session id as the current time
+      _sessionId = now.millisecondsSinceEpoch;
+    } on FileSystemException catch (err) {
+      final now = createSessionFile(sessionFile: sessionFile);
+
+      errorSet.add(Event.analyticsException(
+        workflow: 'UserProperty._refreshSessionData',
+        error: err.runtimeType.toString(),
+        description: err.osError?.toString(),
+      ));
+
+      // Fallback to setting the session id as the current time
+      _sessionId = now.millisecondsSinceEpoch;
+    }
+  }
+
+  /// Convert the data stored in this class into a map while also
+  /// getting the latest session id using the [UserProperty] class.
+  Map<String, Object?> _toMap() => <String, Object?>{
+        'session_id': getSessionId(),
+        'flutter_channel': flutterChannel,
+        'host': host,
+        'flutter_version': flutterVersion,
+        'dart_version': dartVersion,
+        'analytics_pkg_version': kPackageVersion,
+        'tool': tool,
+        'local_time': formatDateTime(clock.now()),
+        'host_os_version': hostOsVersion,
+        'locale': locale,
+        'client_ide': clientIde,
+        'enabled_features': enabledFeatures,
+      };
+}
diff --git a/pkgs/unified_analytics/lib/src/utils.dart b/pkgs/unified_analytics/lib/src/utils.dart
new file mode 100644
index 0000000..41848a2
--- /dev/null
+++ b/pkgs/unified_analytics/lib/src/utils.dart
@@ -0,0 +1,340 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:convert';
+import 'dart:io' as io;
+import 'dart:math' show Random;
+
+import 'package:clock/clock.dart';
+import 'package:convert/convert.dart';
+import 'package:file/file.dart';
+
+import 'enums.dart';
+import 'event.dart';
+import 'survey_handler.dart';
+import 'user_property.dart';
+
+/// Get a string representation of the current date in the following format:
+/// ```text
+/// yyyy-MM-dd (2023-01-09)
+/// ```
+String get dateStamp {
+  return FixedDateTimeFormatter('YYYY-MM-DD').encode(clock.now());
+}
+
+/// Reads in a directory and returns `true` if write permissions are enabled.
+///
+/// Uses the [FileStat] method `modeString()` to return a string in the form
+/// of `rwxrwxrwx` where the second character in the string indicates if write
+/// is enabled with a `w` or disabled with `-`.
+bool checkDirectoryForWritePermissions(Directory directory) {
+  if (!directory.existsSync()) return false;
+
+  final fileStat = directory.statSync();
+  return fileStat.modeString()[1] == 'w';
+}
+
+/// Format time as 'yyyy-MM-dd HH:mm:ss Z' where Z is the difference between the
+/// timezone of t and UTC formatted according to RFC 822.
+String formatDateTime(DateTime t) {
+  final sign = t.timeZoneOffset.isNegative ? '-' : '+';
+  final tzOffset = t.timeZoneOffset.abs();
+  final hoursOffset = tzOffset.inHours;
+  final minutesOffset =
+      tzOffset.inMinutes - (Duration.minutesPerHour * hoursOffset);
+  assert(hoursOffset < 24);
+  assert(minutesOffset < 60);
+
+  String twoDigits(int n) => (n >= 10) ? '$n' : '0$n';
+  return '$t $sign${twoDigits(hoursOffset)}${twoDigits(minutesOffset)}';
+}
+
+/// Construct the Map that will be converted to json for the
+/// body of the request.
+///
+/// Follows the following schema:
+///
+/// ```
+/// {
+///   "client_id": "46cc0ba6-f604-4fd9-aa2f-8a20beb24cd4",
+///   "events": [{ "name": "testing", "params": { "time_ns": 345 } }],
+///   "user_properties": {
+///     "session_id": { "value": 1673466750423 },
+///     "flutter_channel": { "value": "ey-test-channel" },
+///     "host": { "value": "macos" },
+///     "flutter_version": { "value": "Flutter 3.6.0-7.0.pre.47" },
+///     "dart_version": { "value": "Dart 2.19.0" },
+///     "tool": { "value": "flutter-tools" },
+///     "local_time": { "value": "2023-01-11 14:53:31.471816 -0500" }
+///   }
+/// }
+/// ```
+/// https://developers.google.com/analytics/devguides/collection/protocol/ga4/sending-events?client_type=gtag
+Map<String, Object?> generateRequestBody({
+  required String clientId,
+  required DashEvent eventName,
+  required Map<String, Object?> eventData,
+  required UserProperty userProperty,
+}) =>
+    <String, Object?>{
+      'client_id': clientId,
+      'events': <Map<String, Object?>>[
+        <String, Object?>{
+          'name': eventName.label,
+          'params': eventData,
+        }
+      ],
+      'user_properties': userProperty.preparePayload()
+    };
+
+/// This will use environment variables to get the user's
+/// home directory where all the directory will be created that will
+/// contain all of the analytics files.
+Directory? getHomeDirectory(FileSystem fs) {
+  String? home;
+  final envVars = io.Platform.environment;
+
+  if (io.Platform.isMacOS) {
+    home = envVars['HOME'];
+  } else if (io.Platform.isLinux) {
+    home = envVars['HOME'];
+  } else if (io.Platform.isWindows) {
+    home = envVars['AppData'];
+  }
+
+  if (home == null) return null;
+
+  return fs.directory(home);
+}
+
+/// Returns `true` if user has opted out of legacy analytics in
+/// Dart or Flutter.
+///
+/// Checks legacy opt-out status for the Flutter
+/// and Dart in the following locations.
+///
+/// Dart: `$HOME/.dart/dartdev.json`
+/// ```
+/// {
+///   "firstRun": false,
+///   "enabled": false,  <-- THIS USER HAS OPTED OUT
+///   "disclosureShown": true,
+///   "clientId": "52710e60-7c70-4335-b3a4-9d922630f12a"
+/// }
+/// ```
+///
+/// Flutter: `$HOME/.flutter`
+/// ```
+/// {
+///   "firstRun": false,
+///   "clientId": "4c3a3d1e-e545-47e7-b4f8-10129f6ab169",
+///   "enabled": false  <-- THIS USER HAS OPTED OUT
+/// }
+/// ```
+///
+/// Devtools: `$HOME/.flutter-devtools/.devtools`
+/// ```
+/// {
+///   "analyticsEnabled": false,  <-- THIS USER HAS OPTED OUT
+///   "isFirstRun": false,
+///   "lastReleaseNotesVersion": "2.31.0",
+///   "2023-Q4": {
+///     "surveyActionTaken": false,
+///     "surveyShownCount": 0
+///   }
+/// }
+/// ```
+bool legacyOptOut({required Directory homeDirectory}) {
+  // List of Maps for each of the config file, `key` refers to the
+  // key in the json file that indicates if the user has been opted
+  // out or not
+  final legacyConfigFiles = [
+    (
+      tool: DashTool.dartTool,
+      file: homeDirectory.childDirectory('.dart').childFile('dartdev.json'),
+      key: 'enabled',
+    ),
+    (
+      tool: DashTool.flutterTool,
+      file: homeDirectory.childFile('.flutter'),
+      key: 'enabled',
+    ),
+    (
+      tool: DashTool.devtools,
+      file: homeDirectory
+          .childDirectory('.flutter-devtools')
+          .childFile('.devtools'),
+      key: 'analyticsEnabled',
+    ),
+  ];
+  for (final legacyConfigObj in legacyConfigFiles) {
+    final legacyFile = legacyConfigObj.file;
+    final lookupKey = legacyConfigObj.key;
+
+    if (legacyFile.existsSync()) {
+      try {
+        final legacyFileObj =
+            jsonDecode(legacyFile.readAsStringSync()) as Map<String, Object?>;
+        if (legacyFileObj.containsKey(lookupKey) &&
+            legacyFileObj[lookupKey] == false) {
+          return true;
+        }
+      } on FormatException {
+        // In the case of an error when parsing the json file, return true
+        // which will result in the user being opted out of unified_analytics
+        //
+        // A corrupted file could mean they opted out previously but for some
+        // reason, the file was written incorrectly
+        return true;
+      } on FileSystemException {
+        return true;
+      }
+    }
+  }
+
+  return false;
+}
+
+/// Helper method that can be used to resolve the Dart SDK version for clients
+/// of package:unified_analytics.
+///
+/// Input [versionString] for this method should be the returned string from
+/// [io.Platform.version].
+///
+/// For tools that don't already have a method for resolving the Dart
+/// SDK version in semver notation, this helper can be used. This uses
+/// the [io.Platform.version] to parse the semver.
+///
+/// Example for stable version:
+/// `3.3.0 (stable) (Tue Feb 13 10:25:19 2024 +0000) on "macos_arm64"` into
+/// `3.3.0`.
+///
+/// Example for non-stable version:
+/// `2.1.0-dev.8.0.flutter-312ae32` into `2.1.0 (build 2.1.0-dev.8.0 312ae32)`.
+String parseDartSDKVersion(String versionString) {
+  versionString = versionString.trim();
+  final justVersion = versionString.split(' ')[0];
+
+  // For non-stable versions, this regex will include build information
+  return justVersion.replaceFirstMapped(RegExp(r'(\d+\.\d+\.\d+)(.+)'),
+      (Match match) {
+    final noFlutter = match[2]!.replaceAll('.flutter-', ' ');
+    return '${match[1]} (build ${match[1]}$noFlutter)'.trim();
+  });
+}
+
+/// Will use two strings to produce a double for applying a sampling
+/// rate for [Survey] to be returned to the user.
+double sampleRate(String string1, String string2) =>
+    ((string1.hashCode + string2.hashCode) % 101) / 100;
+
+/// Function to check if a given [Survey] can be shown again
+/// by checking if it was snoozed or permanently dismissed.
+///
+/// If the [Survey] doesn't exist in the persisted file, then it
+/// will be shown to the user.
+///
+/// If the [Survey] has been permanently dismissed, we will not
+/// show it to the user.
+///
+/// If the [Survey] has been snoozed, we will check the timestamp
+/// that it was snoozed at with the current time from [clock]
+/// and if the snooze period has elapsed, then we will show it to the user.
+bool surveySnoozedOrDismissed(
+  Survey survey,
+  Map<String, PersistedSurvey> persistedSurveyMap,
+) {
+  // If this survey hasn't been persisted yet, it is okay to pass
+  // to the user
+  if (!persistedSurveyMap.containsKey(survey.uniqueId)) return false;
+
+  final persistedSurveyObj = persistedSurveyMap[survey.uniqueId]!;
+
+  // If the survey has been dismissed permanently, we will not show the
+  // survey
+  if (!persistedSurveyObj.snoozed) return true;
+
+  // Find how many minutes has elapsed from the timestamp and now
+  final minutesElapsed =
+      clock.now().difference(persistedSurveyObj.timestamp).inMinutes;
+
+  return survey.snoozeForMinutes > minutesElapsed;
+}
+
+/// Due to some limitations for GA4, this function can be used to
+/// truncate fields that we may not care about truncating, such as
+/// the host os details.
+///
+/// [maxLength] represents the maximum length allowed for the string.
+///
+/// Example:
+/// "Linux 6.2.0-1015-azure #15~22.04.1-Ubuntu SMP Fri Oct  6 13:20:44 UTC 2023"
+///
+/// The above string is what is returned by [io.Platform.operatingSystemVersion]
+/// for certain machines running GitHub Actions, this function will truncate
+/// that value down to the maximum length at 36 characters and return the below
+///
+/// Return:
+/// "Linux 6.2.0-1015-azure #15~22."
+///
+/// This should only be used on fields that are okay to be truncated, this
+/// should not be used for parameters on the [Event] constructors.
+String truncateStringToLength(String str, int maxLength) {
+  if (maxLength <= 0) {
+    throw ArgumentError(
+        'The length to truncate a string must be greater than 0');
+  }
+
+  if (maxLength > str.length) return str;
+
+  return str.substring(0, maxLength);
+}
+
+/// Writes the JSON string payload to the provided [sessionFile].
+///
+/// The `last_ping` key:value pair has been deprecated, it remains included
+/// for backward compatibility.
+void writeSessionContents({required File sessionFile}) {
+  final now = clock.now();
+  sessionFile.writeAsStringSync('{"session_id": ${now.millisecondsSinceEpoch}, '
+      '"last_ping": ${now.millisecondsSinceEpoch}}');
+}
+
+/// A UUID generator.
+///
+/// This will generate unique IDs in the format:
+///
+///     f47ac10b-58cc-4372-a567-0e02b2c3d479
+///
+/// The generated uuids are 128 bit numbers encoded in a specific string format.
+/// For more information, see
+/// [en.wikipedia.org/wiki/Universally_unique_identifier](http://en.wikipedia.org/wiki/Universally_unique_identifier).
+///
+/// This class was taken from the previous `usage` package (https://github.com/dart-lang/usage/blob/master/lib/uuid/uuid.dart).
+class Uuid {
+  final Random _random;
+
+  Uuid([int? seed]) : _random = Random(seed);
+
+  /// Generate a version 4 (random) uuid. This is a uuid scheme that only uses
+  /// random numbers as the source of the generated uuid.
+  String generateV4() {
+    // Generate xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx / 8-4-4-4-12.
+    final special = 8 + _random.nextInt(4);
+
+    return '${_bitsDigits(16, 4)}${_bitsDigits(16, 4)}-'
+        '${_bitsDigits(16, 4)}-'
+        '4${_bitsDigits(12, 3)}-'
+        '${_printDigits(special, 1)}${_bitsDigits(12, 3)}-'
+        '${_bitsDigits(16, 4)}${_bitsDigits(16, 4)}${_bitsDigits(16, 4)}';
+  }
+
+  String _bitsDigits(int bitCount, int digitCount) =>
+      _printDigits(_generateBits(bitCount), digitCount);
+
+  int _generateBits(int bitCount) => _random.nextInt(1 << bitCount);
+
+  String _printDigits(int value, int count) =>
+      value.toRadixString(16).padLeft(count, '0');
+}
diff --git a/pkgs/unified_analytics/lib/testing.dart b/pkgs/unified_analytics/lib/testing.dart
new file mode 100644
index 0000000..900212f
--- /dev/null
+++ b/pkgs/unified_analytics/lib/testing.dart
@@ -0,0 +1,5 @@
+// Copyright (c) 2024, 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.
+
+export 'src/enums.dart';
diff --git a/pkgs/unified_analytics/lib/unified_analytics.dart b/pkgs/unified_analytics/lib/unified_analytics.dart
new file mode 100644
index 0000000..7cc4562
--- /dev/null
+++ b/pkgs/unified_analytics/lib/unified_analytics.dart
@@ -0,0 +1,11 @@
+// Copyright (c) 2023, 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.
+
+export 'src/analytics.dart' show Analytics, FakeAnalytics, NoOpAnalytics;
+export 'src/config_handler.dart' show ToolInfo;
+export 'src/enums.dart' show DashTool;
+export 'src/event.dart' show Event;
+export 'src/log_handler.dart' show LogFileStats;
+export 'src/survey_handler.dart' show Survey, SurveyButton, SurveyHandler;
+export 'src/utils.dart' show parseDartSDKVersion;
diff --git a/pkgs/unified_analytics/pubspec.yaml b/pkgs/unified_analytics/pubspec.yaml
new file mode 100644
index 0000000..172f5b2
--- /dev/null
+++ b/pkgs/unified_analytics/pubspec.yaml
@@ -0,0 +1,25 @@
+name: unified_analytics
+description: >-
+  A package for logging analytics for all Dart and Flutter related tooling
+  to Google Analytics.
+# LINT.IfChange
+# When updating this, keep the version consistent with the changelog and the
+# value in lib/src/constants.dart.
+version: 6.1.4
+# LINT.ThenChange(lib/src/constants.dart)
+repository: https://github.com/dart-lang/tools/tree/main/pkgs/unified_analytics
+
+environment:
+  sdk: ^3.4.0
+
+dependencies:
+  clock: ^1.1.1
+  convert: ^3.1.1
+  file: '>=6.1.4 <8.0.0'
+  http: '>=0.13.5 <2.0.0'
+  meta: ^1.9.0
+
+dev_dependencies:
+  dart_flutter_team_lints: ^3.0.0
+  test: ^1.16.6
+  yaml: ^3.1.1
diff --git a/pkgs/unified_analytics/test/asserts_test.dart b/pkgs/unified_analytics/test/asserts_test.dart
new file mode 100644
index 0000000..9230fc6
--- /dev/null
+++ b/pkgs/unified_analytics/test/asserts_test.dart
@@ -0,0 +1,413 @@
+// Copyright (c) 2023, 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.
+
+import 'package:test/test.dart';
+import 'package:unified_analytics/src/asserts.dart';
+
+void main() {
+  test('Failure if client_id top level key is missing', () {
+    final body = <String, Object?>{};
+
+    final expectedErrorMessage = 'client_id missing from top level keys';
+    expect(
+        () => checkBody(body),
+        throwsA(predicate(
+            (AnalyticsException e) => e.message == expectedErrorMessage,
+            expectedErrorMessage)));
+  });
+
+  test('Failure if events top level key is missing', () {
+    final body = <String, Object?>{'client_id': 'xxxxxxx'};
+
+    final expectedErrorMessage = 'events missing from top level keys';
+    expect(
+        () => checkBody(body),
+        throwsA(predicate(
+            (AnalyticsException e) => e.message == expectedErrorMessage,
+            expectedErrorMessage)));
+  });
+
+  test('Failure if user_properties top level key is missing', () {
+    final body = <String, Object?>{'client_id': 'xxxxxxx', 'events': []};
+
+    final expectedErrorMessage = 'user_properties missing from top level keys';
+    expect(
+        () => checkBody(body),
+        throwsA(predicate(
+            (AnalyticsException e) => e.message == expectedErrorMessage,
+            expectedErrorMessage)));
+  });
+
+  test('Failure if more than 25 events found in events list', () {
+    final body = <String, Object?>{
+      'client_id': 'xxxxxxx',
+      'events': <Map<String, Object?>>[],
+      'user_properties': <String, Object?>{}
+    };
+
+    // Add more than the 25 allowed events
+    for (var i = 0; i < 30; i++) {
+      (body['events'] as List).add({'name': i});
+    }
+
+    final expectedErrorMessage = '25 is the max number of events';
+    expect(
+        () => checkBody(body),
+        throwsA(predicate(
+            (AnalyticsException e) => e.message == expectedErrorMessage,
+            expectedErrorMessage)));
+  });
+
+  test('Failure when event name is greater than 40 chars', () {
+    final body = <String, Object?>{
+      'client_id': 'xxxxxxx',
+      'events': <Map<String, Object?>>[
+        {
+          'name':
+              'hot_reload_timehot_reload_timehot_reload_timehot_reload_time',
+          'params': {'time_ms': 133, 'count': 1999000}
+        }
+      ],
+      'user_properties': <String, Object?>{}
+    };
+
+    final expectedErrorMessage = 'Limit event names to 40 chars or less\n'
+        'Event name: '
+        '"hot_reload_timehot_reload_timehot_reload_timehot_reload_time"'
+        ' is too long';
+    expect(
+        () => checkBody(body),
+        throwsA(predicate(
+            (AnalyticsException e) => e.message == expectedErrorMessage,
+            expectedErrorMessage)));
+  });
+
+  test('Failure when event name has invalid chars', () {
+    final body = <String, Object?>{
+      'client_id': 'xxxxxxx',
+      'events': <Map<String, Object?>>[
+        {
+          'name': 'hot_reload_time!!',
+          'params': {'time_ms': 133, 'count': 1999000}
+        }
+      ],
+      'user_properties': <String, Object?>{}
+    };
+
+    final expectedErrorMessage =
+        'Event name can only have alphanumeric chars and underscores\n'
+        'Event name: "hot_reload_time!!" contains invalid characters';
+    expect(
+        () => checkBody(body),
+        throwsA(predicate(
+            (AnalyticsException e) => e.message == expectedErrorMessage,
+            expectedErrorMessage)));
+  });
+
+  test('Failure when event name does not start with alphabetic char', () {
+    final body = <String, Object?>{
+      'client_id': 'xxxxxxx',
+      'events': <Map<String, Object?>>[
+        {
+          'name': '2hot_reload_time',
+          'params': {'time_ms': 133, 'count': 1999000}
+        }
+      ],
+      'user_properties': <String, Object?>{}
+    };
+
+    final expectedErrorMessage =
+        'Event name first char must be alphabetic char\n'
+        'Event name: "2hot_reload_time" must begin with a valid character';
+    expect(
+        () => checkBody(body),
+        throwsA(predicate(
+            (AnalyticsException e) => e.message == expectedErrorMessage,
+            expectedErrorMessage)));
+  });
+
+  test('Failure when an event has more than 25 event params', () {
+    final body = <String, Object?>{
+      'client_id': 'xxxxxxx',
+      'events': <Map<String, Object?>>[
+        {
+          'name': 'hot_reload_time',
+          // 'params': {...} SUBBING THIS VALUE OUT 30 Maps
+        }
+      ],
+      'user_properties': <String, Object?>{}
+    };
+
+    final params = <String, Object?>{};
+    for (var i = 0; i < 30; i++) {
+      params['$i'] = i;
+    }
+
+    // Add the params to the first event in the body
+    ((body['events'] as List).first as Map)['params'] = params;
+
+    final expectedErrorMessage = 'Limit params for each event to less than 25\n'
+        'Event: "hot_reload_time" has too many parameters';
+    expect(
+        () => checkBody(body),
+        throwsA(predicate(
+            (AnalyticsException e) => e.message == expectedErrorMessage,
+            expectedErrorMessage)));
+  });
+
+  test('Failure when an value for event params is not a supported type (list)',
+      () {
+    final body = <String, Object?>{
+      'client_id': 'xxxxxxx',
+      'events': <Map<String, Object?>>[
+        {
+          'name': 'hot_reload_time',
+          'params': {
+            'time_ms': 133,
+            // Lists and Maps are not supported
+            'count': <int>[1999000],
+          }
+        }
+      ],
+      'user_properties': <String, Object?>{}
+    };
+
+    final expectedErrorMessage =
+        'Values for event params have to be String, int, double, or bool\n'
+        'Value for "count" is not a valid type for event: "hot_reload_time"';
+    expect(
+        () => checkBody(body),
+        throwsA(predicate(
+            (AnalyticsException e) => e.message == expectedErrorMessage,
+            expectedErrorMessage)));
+  });
+
+  test('Failure when an value for event params is not a supported type (map)',
+      () {
+    final body = <String, Object?>{
+      'client_id': 'xxxxxxx',
+      'events': <Map<String, Object?>>[
+        {
+          'name': 'hot_reload_time',
+          'params': {
+            'time_ms': 133,
+            // Lists and Maps are not supported
+            'count': <int, int>{5: 20},
+          }
+        }
+      ],
+      'user_properties': <String, Object?>{}
+    };
+
+    final expectedErrorMessage =
+        'Values for event params have to be String, int, double, or bool\n'
+        'Value for "count" is not a valid type for event: "hot_reload_time"';
+    expect(
+        () => checkBody(body),
+        throwsA(predicate(
+            (AnalyticsException e) => e.message == expectedErrorMessage,
+            expectedErrorMessage)));
+  });
+
+  test('Failure when event param name is more than 40 chars', () {
+    final body = <String, Object?>{
+      'client_id': 'xxxxxxx',
+      'events': <Map<String, Object?>>[
+        {
+          'name': 'hot_reload_time',
+          'params': {'time_mstime_mstime_mstime_mstime_mstime_ms': 133}
+        }
+      ],
+      'user_properties': <String, Object?>{}
+    };
+
+    final expectedErrorMessage = 'Limit event param names to 40 chars or less\n'
+        'The key: "time_mstime_mstime_mstime_mstime_mstime_ms" '
+        'under the event: "hot_reload_time" is too long';
+    expect(
+        () => checkBody(body),
+        throwsA(predicate(
+            (AnalyticsException e) => e.message == expectedErrorMessage,
+            expectedErrorMessage)));
+  });
+
+  test('Failure for event param name that has invalid chars', () {
+    final body = <String, Object?>{
+      'client_id': 'xxxxxxx',
+      'events': <Map<String, Object?>>[
+        {
+          'name': 'hot_reload_time',
+          'params': {'time_ns!': 133}
+        }
+      ],
+      'user_properties': <String, Object?>{}
+    };
+
+    final expectedErrorMessage =
+        'Event param name can only have alphanumeric chars and underscores\n'
+        'The key: "time_ns!" under the event: "hot_reload_time" contains '
+        'invalid characters';
+
+    expect(
+        () => checkBody(body),
+        throwsA(predicate(
+            (AnalyticsException e) => e.message == expectedErrorMessage,
+            expectedErrorMessage)));
+  });
+
+  test(
+    'Failure for event param name that does not start with an alphabetic char',
+    () {
+      final body = <String, Object?>{
+        'client_id': 'xxxxxxx',
+        'events': <Map<String, Object?>>[
+          {
+            'name': 'hot_reload_time',
+            'params': {'22time_ns': 133}
+          }
+        ],
+        'user_properties': <String, Object?>{}
+      };
+
+      final expectedErrorMessage =
+          'Event param name first char must be alphabetic char\n'
+          'The key: "22time_ns" under the event: "hot_reload_time" must begin '
+          'in a valid character';
+      expect(
+          () => checkBody(body),
+          throwsA(predicate(
+              (AnalyticsException e) => e.message == expectedErrorMessage,
+              expectedErrorMessage)));
+    },
+  );
+
+  test('Failure for event param values that are greater than 100 chars', () {
+    final body = <String, Object?>{
+      'client_id': 'xxxxxxx',
+      'events': <Map<String, Object?>>[
+        {
+          'name': 'hot_reload_time',
+          'params': {
+            'time_ns': 'dsfjlksdjfajlfdsfjlks'
+                'djfajlfdsfjlksdjfajlfdsfjlksdjfaj'
+                'lfdsfjlksdjfajlfdsfjlksdjfajlfdsf'
+                'jlksdjfajlfdsfjlksdjfajlf'
+          }
+        }
+      ],
+      'user_properties': <String, Object?>{}
+    };
+
+    final expectedErrorMessage =
+        'Limit characters in event param value to 100 chars or less\n'
+        'Value for "time_ns" is too long, value="'
+        'dsfjlksdjfajlfdsfjlks'
+        'djfajlfdsfjlksdjfajlfdsfjlksdjfaj'
+        'lfdsfjlksdjfajlfdsfjlksdjfajlfdsf'
+        'jlksdjfajlfdsfjlksdjfajlf"';
+    expect(
+        () => checkBody(body),
+        throwsA(predicate(
+            (AnalyticsException e) => e.message == expectedErrorMessage,
+            expectedErrorMessage)));
+  });
+
+  test('Failure when body has more than 25 user properties', () {
+    final body = <String, Object?>{
+      'client_id': 'xxxxxxx',
+      'events': <Map<String, Object?>>[
+        {
+          'name': 'hot_reload_time',
+          'params': {'time_ns': 123}
+        }
+      ],
+      'user_properties': <String, Object?>{}
+    };
+
+    for (var i = 0; i < 30; i++) {
+      (body['user_properties']! as Map<String, Object?>)['$i'] = i;
+    }
+
+    final expectedErrorMessage = 'Limit user properties to 25 or less';
+    expect(
+        () => checkBody(body),
+        throwsA(predicate(
+            (AnalyticsException e) => e.message == expectedErrorMessage,
+            expectedErrorMessage)));
+  });
+
+  test('Failure when user properties names are greater than 24 chars', () {
+    final body = <String, Object?>{
+      'client_id': 'xxxxxxx',
+      'events': <Map<String, Object?>>[
+        {
+          'name': 'hot_reload_time',
+          'params': {'time_ns': 123}
+        }
+      ],
+      'user_properties': <String, Object?>{
+        'testtesttesttesttesttesttest': <String, Object?>{}, // TOO LONG
+      }
+    };
+
+    final expectedErrorMessage =
+        'Limit user property names to 24 chars or less\n'
+        'The user property key: "testtesttesttesttesttesttest" is too long';
+    expect(
+        () => checkBody(body),
+        throwsA(predicate(
+            (AnalyticsException e) => e.message == expectedErrorMessage,
+            expectedErrorMessage)));
+  });
+
+  test('Failure when user properties values are greater than 36 chars', () {
+    final body = <String, Object?>{
+      'client_id': 'xxxxxxx',
+      'events': <Map<String, Object?>>[
+        {
+          'name': 'hot_reload_time',
+          'params': {'time_ns': 123}
+        }
+      ],
+      'user_properties': <String, Object?>{
+        'test': <String, Object?>{
+          'value': 'testtesttesttesttesttesttesttesttesttest' // TOO LONG
+        },
+      }
+    };
+
+    final expectedErrorMessage =
+        'Limit user property values to 36 chars or less\n'
+        'For the user property key "test", the value '
+        '"testtesttesttesttesttesttesttesttesttest" is too long';
+    expect(
+        () => checkBody(body),
+        throwsA(predicate(
+            (AnalyticsException e) => e.message == expectedErrorMessage,
+            expectedErrorMessage)));
+  });
+
+  test('Successful body passes all asserts', () {
+    final body = <String, Object?>{
+      'client_id': '46cc0ba6-f604-4fd9-aa2f-8a20beb24cd4',
+      'events': [
+        {
+          'name': 'testing',
+          'params': {'time_ns': 345}
+        }
+      ],
+      'user_properties': {
+        'session_id': {'value': 1673466750423},
+        'flutter_channel': {'value': 'ey-test-channel'},
+        'host': {'value': 'macos'},
+        'flutter_version': {'value': 'Flutter 3.6.0-7.0.pre.47'},
+        'dart_version': {'value': 'Dart 2.19.0'},
+        'tool': {'value': 'flutter-tools'},
+        'local_time': {'value': '2023-01-11 14:53:31.471816 -0500'}
+      }
+    };
+
+    expect(() => checkBody(body), returnsNormally);
+  });
+}
diff --git a/pkgs/unified_analytics/test/error_handler_test.dart b/pkgs/unified_analytics/test/error_handler_test.dart
new file mode 100644
index 0000000..39b2df8
--- /dev/null
+++ b/pkgs/unified_analytics/test/error_handler_test.dart
@@ -0,0 +1,346 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:io' as io;
+
+import 'package:file/file.dart';
+import 'package:file/memory.dart';
+import 'package:test/test.dart';
+
+import 'package:unified_analytics/src/constants.dart';
+import 'package:unified_analytics/src/enums.dart';
+import 'package:unified_analytics/unified_analytics.dart';
+
+void main() {
+  late MemoryFileSystem fs;
+  late Directory home;
+  late FakeAnalytics initializationAnalytics;
+  late FakeAnalytics analytics;
+  late File sessionFile;
+  late File logFile;
+
+  const homeDirName = 'home';
+  const initialTool = DashTool.flutterTool;
+  const toolsMessageVersion = 1;
+  const toolsMessage = 'toolsMessage';
+  const flutterChannel = 'flutterChannel';
+  const flutterVersion = 'flutterVersion';
+  const dartVersion = 'dartVersion';
+  const platform = DevicePlatform.macos;
+  const clientIde = 'VSCode';
+
+  final testEvent = Event.codeSizeAnalysis(platform: 'platform');
+
+  setUp(() {
+    // Setup the filesystem with the home directory
+    final fsStyle =
+        io.Platform.isWindows ? FileSystemStyle.windows : FileSystemStyle.posix;
+    fs = MemoryFileSystem.test(style: fsStyle);
+    home = fs.directory(homeDirName);
+
+    // This is the first analytics instance that will be used to demonstrate
+    // that events will not be sent with the first run of analytics
+    initializationAnalytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+    expect(initializationAnalytics.shouldShowMessage, true);
+    initializationAnalytics.clientShowedMessage();
+    expect(initializationAnalytics.shouldShowMessage, false);
+
+    // The main analytics instance, other instances can be spawned within tests
+    // to test how to instances running together work
+    //
+    // This instance should have the same parameters as the one above for
+    // [initializationAnalytics]
+    analytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+      clientIde: clientIde,
+    );
+    analytics.clientShowedMessage();
+
+    // The files that should have been generated that will be used for tests
+    sessionFile =
+        home.childDirectory(kDartToolDirectoryName).childFile(kSessionFileName);
+    logFile =
+        home.childDirectory(kDartToolDirectoryName).childFile(kLogFileName);
+  });
+
+  group('Session handler:', () {
+    test('no error when opted out already and opting in', () async {
+      // When we opt out from an analytics instance, we clear the contents of
+      // session file, as required by the privacy document. When creating a
+      // second instance of [Analytics], it should not detect that the file is
+      // empty and recreate it, it should remain opted out and no error event
+      // should have been sent
+      await analytics.setTelemetry(false);
+      expect(analytics.telemetryEnabled, false);
+      expect(sessionFile.readAsStringSync(), isEmpty);
+
+      final secondAnalytics = Analytics.fake(
+        tool: initialTool,
+        homeDirectory: home,
+        flutterChannel: flutterChannel,
+        toolsMessageVersion: toolsMessageVersion,
+        toolsMessage: toolsMessage,
+        flutterVersion: flutterVersion,
+        dartVersion: dartVersion,
+        fs: fs,
+        platform: platform,
+        clientIde: clientIde,
+      );
+      expect(sessionFile.readAsStringSync(), isEmpty);
+      expect(secondAnalytics.telemetryEnabled, false);
+
+      expect(
+        analytics.sentEvents.where(
+            (element) => element.eventName == DashEvent.analyticsException),
+        isEmpty,
+      );
+      expect(
+        secondAnalytics.sentEvents.where(
+            (element) => element.eventName == DashEvent.analyticsException),
+        isEmpty,
+      );
+
+      await secondAnalytics.setTelemetry(true);
+      expect(sessionFile.readAsStringSync(), isNotEmpty,
+          reason: 'Toggling telemetry should bring back the session data');
+    });
+    test('only sends one event for FormatException', () {
+      // Begin with the session file empty, it should recreate the file
+      // and send an error event
+      sessionFile.writeAsStringSync('');
+      expect(sessionFile.readAsStringSync(), isEmpty);
+      analytics.send(testEvent);
+      expect(sessionFile.readAsStringSync(), isNotEmpty);
+
+      analytics.sendPendingErrorEvents();
+      expect(
+          analytics.sentEvents.where(
+              (element) => element.eventName == DashEvent.analyticsException),
+          hasLength(1));
+
+      // Making the file empty again and sending an event should not send
+      // an additional event
+      sessionFile.writeAsStringSync('');
+      expect(sessionFile.readAsStringSync(), isEmpty);
+      analytics.send(testEvent);
+      expect(sessionFile.readAsStringSync(), isNotEmpty);
+
+      expect(
+          analytics.sentEvents.where(
+              (element) => element.eventName == DashEvent.analyticsException),
+          hasLength(1),
+          reason: 'We should not have added a new error event');
+    });
+
+    test('only sends one event for FileSystemException', () {
+      // Deleting the session file should cause the file system exception and
+      // sending a new event should log the error the first time and recreate
+      // the file. If we delete the file again and attempt to send an event,
+      // the session file should get recreated without sending a second error.
+      sessionFile.deleteSync();
+      expect(sessionFile.existsSync(), isFalse);
+      analytics.send(testEvent);
+
+      analytics.sendPendingErrorEvents();
+      expect(
+        analytics.sentEvents.where(
+            (element) => element.eventName == DashEvent.analyticsException),
+        hasLength(1),
+      );
+      expect(sessionFile.existsSync(), isTrue);
+      expect(sessionFile.readAsStringSync(), isNotEmpty);
+
+      // Remove the file again and send an event
+      sessionFile.deleteSync();
+      expect(sessionFile.existsSync(), isFalse);
+      analytics.send(testEvent);
+
+      expect(
+        analytics.sentEvents.where(
+            (element) => element.eventName == DashEvent.analyticsException),
+        hasLength(1),
+        reason: 'Only the first error event should exist',
+      );
+      expect(sessionFile.existsSync(), isTrue);
+      expect(sessionFile.readAsStringSync(), isNotEmpty);
+    });
+
+    test('sends two unique errors', () {
+      // Begin with the session file empty, it should recreate the file
+      // and send an error event
+      sessionFile.writeAsStringSync('');
+      expect(sessionFile.readAsStringSync(), isEmpty);
+      analytics.send(testEvent);
+      expect(sessionFile.readAsStringSync(), isNotEmpty);
+
+      analytics.sendPendingErrorEvents();
+      expect(
+          analytics.sentEvents.where(
+              (element) => element.eventName == DashEvent.analyticsException),
+          hasLength(1));
+
+      // Deleting the file now before sending an additional event should
+      // cause a different test error
+      sessionFile.deleteSync();
+      expect(sessionFile.existsSync(), isFalse);
+
+      analytics.send(testEvent);
+      expect(sessionFile.readAsStringSync(), isNotEmpty);
+      analytics.sendPendingErrorEvents();
+      expect(
+          analytics.sentEvents.where(
+              (element) => element.eventName == DashEvent.analyticsException),
+          hasLength(2));
+      expect(analytics.sentEvents, hasLength(4));
+
+      sessionFile.deleteSync();
+      expect(sessionFile.existsSync(), isFalse);
+
+      analytics.send(testEvent);
+      expect(sessionFile.readAsStringSync(), isNotEmpty);
+      expect(
+          analytics.sentEvents.where(
+              (element) => element.eventName == DashEvent.analyticsException),
+          hasLength(2));
+    });
+  });
+
+  group('Log handler:', () {
+    test('only sends one event for FormatException', () {
+      expect(logFile.existsSync(), isTrue);
+
+      // Write invalid lines to the log file to have a FormatException
+      // thrown when trying to parse the log file
+      logFile.writeAsStringSync('''
+{{}
+{{}
+''');
+
+      // Send one event so that the logFileStats method returns a valid value
+      analytics.send(testEvent);
+      expect(analytics.sentEvents, hasLength(1));
+      expect(logFile.readAsLinesSync(), hasLength(3));
+      analytics.sendPendingErrorEvents();
+      expect(
+        analytics.sentEvents.where(
+            (element) => element.eventName == DashEvent.analyticsException),
+        isEmpty,
+      );
+
+      // This call below will cause a FormatException while parsing the log file
+      final logFileStats = analytics.logFileStats();
+      expect(logFileStats, isNotNull);
+      expect(logFileStats!.recordCount, 1,
+          reason: 'The error event is not counted');
+      analytics.sendPendingErrorEvents();
+      expect(
+        analytics.sentEvents.where(
+            (element) => element.eventName == DashEvent.analyticsException),
+        hasLength(1),
+      );
+      expect(logFile.readAsLinesSync(), hasLength(4));
+    });
+
+    test('only sends one event for TypeError', () {
+      expect(logFile.existsSync(), isTrue);
+      // Write valid json but have one of the types wrong for
+      // the keys so that we throw a TypeError while casting the values
+      //
+      // In the json below, we have made the session id value a string when
+      // it should be an integer
+      logFile.writeAsStringSync('''
+{"client_id":"fcd6c0d5-6582-4c36-b09e-3ecedee9145c","events":[{"name":"command_usage_values","params":{"workflow":"doctor","commandHasTerminal":true}}],"user_properties":{"session_id":{"value":"this should be a string"},"flutter_channel":{"value":"master"},"host":{"value":"macOS"},"flutter_version":{"value":"3.20.0-2.0.pre.9"},"dart_version":{"value":"3.4.0 (build 3.4.0-99.0.dev)"},"analytics_pkg_version":{"value":"5.8.1"},"tool":{"value":"flutter-tool"},"local_time":{"value":"2024-02-07 15:46:19.920784 -0500"},"host_os_version":{"value":"Version 14.3 (Build 23D56)"},"locale":{"value":"en"},"client_ide":{"value":null},"enabled_features":{"value":"enable-native-assets"}}}
+''');
+      expect(logFile.readAsLinesSync(), hasLength(1));
+
+      // Send the test event so that the LogFileStats object is not null
+      analytics.send(testEvent);
+
+      final logFileStats = analytics.logFileStats();
+      analytics.sendPendingErrorEvents();
+      expect(
+        analytics.sentEvents.where(
+            (element) => element.eventName == DashEvent.analyticsException),
+        hasLength(1),
+      );
+      expect(logFileStats, isNotNull);
+      expect(logFileStats!.recordCount, 1);
+    });
+
+    test('sends two unique errors', () {
+      expect(logFile.existsSync(), isTrue);
+
+      // Write invalid lines to the log file to have a FormatException
+      // thrown when trying to parse the log file
+      logFile.writeAsStringSync('''
+{{}
+{{}
+''');
+
+      // Send one event so that the logFileStats method returns a valid value
+      analytics.send(testEvent);
+      expect(analytics.sentEvents, hasLength(1));
+      expect(logFile.readAsLinesSync(), hasLength(3));
+      analytics.sendPendingErrorEvents();
+      expect(
+        analytics.sentEvents.where(
+            (element) => element.eventName == DashEvent.analyticsException),
+        isEmpty,
+      );
+
+      // This will cause the first error
+      analytics.logFileStats();
+      analytics.sendPendingErrorEvents();
+      expect(
+        analytics.sentEvents.where(
+            (element) => element.eventName == DashEvent.analyticsException),
+        hasLength(1),
+      );
+
+      // Overwrite the contents of the log file now to include something that
+      // will cause a TypeError by changing the expected value for session id
+      // from integer to a string
+      logFile.writeAsStringSync('''
+{"client_id":"fcd6c0d5-6582-4c36-b09e-3ecedee9145c","events":[{"name":"command_usage_values","params":{"workflow":"doctor","commandHasTerminal":true}}],"user_properties":{"session_id":{"value":"this should be a string"},"flutter_channel":{"value":"master"},"host":{"value":"macOS"},"flutter_version":{"value":"3.20.0-2.0.pre.9"},"dart_version":{"value":"3.4.0 (build 3.4.0-99.0.dev)"},"analytics_pkg_version":{"value":"5.8.1"},"tool":{"value":"flutter-tool"},"local_time":{"value":"2024-02-07 15:46:19.920784 -0500"},"host_os_version":{"value":"Version 14.3 (Build 23D56)"},"locale":{"value":"en"},"client_ide":{"value":null},"enabled_features":{"value":"enable-native-assets"}}}
+''');
+      expect(logFile.readAsLinesSync(), hasLength(1));
+
+      // This will cause the second error
+      analytics.logFileStats();
+      analytics.sendPendingErrorEvents();
+      expect(
+        analytics.sentEvents.where(
+            (element) => element.eventName == DashEvent.analyticsException),
+        hasLength(2),
+      );
+
+      // Attempting to cause the same error won't send another error event
+      analytics.logFileStats();
+      analytics.sendPendingErrorEvents();
+      expect(
+        analytics.sentEvents.where(
+            (element) => element.eventName == DashEvent.analyticsException),
+        hasLength(2),
+      );
+    });
+  });
+}
diff --git a/pkgs/unified_analytics/test/event_test.dart b/pkgs/unified_analytics/test/event_test.dart
new file mode 100644
index 0000000..1e9344f
--- /dev/null
+++ b/pkgs/unified_analytics/test/event_test.dart
@@ -0,0 +1,702 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:mirrors';
+
+import 'package:test/test.dart';
+import 'package:unified_analytics/src/enums.dart';
+import 'package:unified_analytics/unified_analytics.dart';
+
+void main() {
+  test('Event.analyticsCollectionEnabled constructed', () {
+    Event generateEvent() => Event.analyticsCollectionEnabled(status: false);
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.analyticsCollectionEnabled);
+    expect(constructedEvent.eventData['status'], false);
+    expect(constructedEvent.eventData.length, 1);
+  });
+
+  test('Event.clientNotification constructed', () {
+    Event generateEvent() => Event.clientNotification(
+          duration: 'duration',
+          latency: 'latency',
+          method: 'method',
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.clientNotification);
+    expect(constructedEvent.eventData['duration'], 'duration');
+    expect(constructedEvent.eventData['latency'], 'latency');
+    expect(constructedEvent.eventData['method'], 'method');
+    expect(constructedEvent.eventData.length, 3);
+  });
+
+  test('Event.clientRequest constructed', () {
+    Event generateEvent() => Event.clientRequest(
+          duration: 'duration',
+          latency: 'latency',
+          method: 'method',
+          added: 'added',
+          excluded: 'excluded',
+          files: 'files',
+          included: 'included',
+          openWorkspacePaths: 'openWorkspacePaths',
+          removed: 'removed',
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.clientRequest);
+    expect(constructedEvent.eventData['duration'], 'duration');
+    expect(constructedEvent.eventData['latency'], 'latency');
+    expect(constructedEvent.eventData['method'], 'method');
+    expect(constructedEvent.eventData['added'], 'added');
+    expect(constructedEvent.eventData['excluded'], 'excluded');
+    expect(constructedEvent.eventData['files'], 'files');
+    expect(constructedEvent.eventData['included'], 'included');
+    expect(
+        constructedEvent.eventData['openWorkspacePaths'], 'openWorkspacePaths');
+    expect(constructedEvent.eventData['removed'], 'removed');
+    expect(constructedEvent.eventData.length, 9);
+  });
+
+  test('Event.commandExecuted constructed', () {
+    Event generateEvent() => Event.commandExecuted(
+          count: 5,
+          name: 'name',
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.commandExecuted);
+    expect(constructedEvent.eventData['count'], 5);
+    expect(constructedEvent.eventData['name'], 'name');
+    expect(constructedEvent.eventData.length, 2);
+  });
+
+  test('Event.contextStructure constructed', () {
+    Event generateEvent() => Event.contextStructure(
+          contextsFromBothFiles: 1,
+          contextsFromOptionsFiles: 2,
+          contextsFromPackagesFiles: 3,
+          contextsWithoutFiles: 4,
+          immediateFileCount: 5,
+          immediateFileLineCount: 6,
+          numberOfContexts: 7,
+          transitiveFileCount: 8,
+          transitiveFileLineCount: 9,
+          transitiveFileUniqueCount: 10,
+          transitiveFileUniqueLineCount: 11,
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.contextStructure);
+    expect(constructedEvent.eventData['contextsFromBothFiles'], 1);
+    expect(constructedEvent.eventData['contextsFromOptionsFiles'], 2);
+    expect(constructedEvent.eventData['contextsFromPackagesFiles'], 3);
+    expect(constructedEvent.eventData['contextsWithoutFiles'], 4);
+    expect(constructedEvent.eventData['immediateFileCount'], 5);
+    expect(constructedEvent.eventData['immediateFileLineCount'], 6);
+    expect(constructedEvent.eventData['numberOfContexts'], 7);
+    expect(constructedEvent.eventData['transitiveFileCount'], 8);
+    expect(constructedEvent.eventData['transitiveFileLineCount'], 9);
+    expect(constructedEvent.eventData['transitiveFileUniqueCount'], 10);
+    expect(constructedEvent.eventData['transitiveFileUniqueLineCount'], 11);
+    expect(constructedEvent.eventData.length, 11);
+  });
+
+  test('Event.dartCliCommandExecuted constructed', () {
+    Event generateEvent() => Event.dartCliCommandExecuted(
+          name: 'name',
+          enabledExperiments: 'enabledExperiments',
+          exitCode: 0,
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.dartCliCommandExecuted);
+    expect(constructedEvent.eventData['name'], 'name');
+    expect(
+        constructedEvent.eventData['enabledExperiments'], 'enabledExperiments');
+    expect(constructedEvent.eventData['exitCode'], 0);
+    expect(constructedEvent.eventData.length, 3);
+  });
+
+  test('Event.doctorValidatorResult constructed', () {
+    Event generateEvent() => Event.doctorValidatorResult(
+          validatorName: 'validatorName',
+          result: 'success',
+          partOfGroupedValidator: false,
+          doctorInvocationId: 123,
+          statusInfo: 'statusInfo',
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.doctorValidatorResult);
+    expect(constructedEvent.eventData['validatorName'], 'validatorName');
+    expect(constructedEvent.eventData['result'], 'success');
+    expect(constructedEvent.eventData['partOfGroupedValidator'], false);
+    expect(constructedEvent.eventData['doctorInvocationId'], 123);
+    expect(constructedEvent.eventData['statusInfo'], 'statusInfo');
+    expect(constructedEvent.eventData.length, 5);
+  });
+
+  test('Event.hotReloadTime constructed', () {
+    Event generateEvent() => Event.hotReloadTime(timeMs: 500);
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.hotReloadTime);
+    expect(constructedEvent.eventData['timeMs'], 500);
+    expect(constructedEvent.eventData.length, 1);
+  });
+
+  test('Event.lintUsageCount constructed', () {
+    Event generateEvent() => Event.lintUsageCount(
+          count: 5,
+          name: 'name',
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.lintUsageCount);
+    expect(constructedEvent.eventData['count'], 5);
+    expect(constructedEvent.eventData['name'], 'name');
+    expect(constructedEvent.eventData.length, 2);
+  });
+
+  test('Event.memoryInfo constructed', () {
+    Event generateEvent() => Event.memoryInfo(
+          rss: 4,
+          periodSec: 5,
+          mbPerSec: 5.55,
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.memoryInfo);
+    expect(constructedEvent.eventData['rss'], 4);
+    expect(constructedEvent.eventData['periodSec'], 5);
+    expect(constructedEvent.eventData['mbPerSec'], 5.55);
+    expect(constructedEvent.eventData.length, 3);
+  });
+
+  test('Event.pluginRequest constructed', () {
+    Event generateEvent() => Event.pluginRequest(
+          duration: 'duration',
+          method: 'method',
+          pluginId: 'pluginId',
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.pluginRequest);
+    expect(constructedEvent.eventData['duration'], 'duration');
+    expect(constructedEvent.eventData['method'], 'method');
+    expect(constructedEvent.eventData['pluginId'], 'pluginId');
+    expect(constructedEvent.eventData.length, 3);
+  });
+
+  test('Event.pluginUse constructed', () {
+    Event generateEvent() => Event.pluginUse(
+          count: 5,
+          enabled: 'enabled',
+          pluginId: 'pluginId',
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.pluginUse);
+    expect(constructedEvent.eventData['count'], 5);
+    expect(constructedEvent.eventData['enabled'], 'enabled');
+    expect(constructedEvent.eventData['pluginId'], 'pluginId');
+    expect(constructedEvent.eventData.length, 3);
+  });
+
+  test('Event.pubGet constructed', () {
+    Event generateEvent() => Event.pubGet(
+          packageName: 'packageName',
+          version: 'version',
+          dependencyType: 'dependencyType',
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.pubGet);
+    expect(constructedEvent.eventData['packageName'], 'packageName');
+    expect(constructedEvent.eventData['version'], 'version');
+    expect(constructedEvent.eventData['dependencyType'], 'dependencyType');
+    expect(constructedEvent.eventData.length, 3);
+  });
+
+  test('Event.serverSession constructed', () {
+    Event generateEvent() => Event.serverSession(
+          clientId: 'clientId',
+          clientVersion: 'clientVersion',
+          duration: 5,
+          flags: 'flags',
+          parameters: 'parameters',
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.serverSession);
+    expect(constructedEvent.eventData['clientId'], 'clientId');
+    expect(constructedEvent.eventData['clientVersion'], 'clientVersion');
+    expect(constructedEvent.eventData['duration'], 5);
+    expect(constructedEvent.eventData['flags'], 'flags');
+    expect(constructedEvent.eventData['parameters'], 'parameters');
+    expect(constructedEvent.eventData.length, 5);
+  });
+
+  test('Event.severityAdjustment constructed', () {
+    Event generateEvent() => Event.severityAdjustment(
+          diagnostic: 'diagnostic',
+          adjustments: 'adjustments',
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.severityAdjustment);
+    expect(constructedEvent.eventData['diagnostic'], 'diagnostic');
+    expect(constructedEvent.eventData['adjustments'], 'adjustments');
+    expect(constructedEvent.eventData.length, 2);
+  });
+
+  test('Event.surveyAction constructed', () {
+    Event generateEvent() => Event.surveyAction(
+          surveyId: 'surveyId',
+          status: 'status',
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.surveyAction);
+    expect(constructedEvent.eventData['surveyId'], 'surveyId');
+    expect(constructedEvent.eventData['status'], 'status');
+    expect(constructedEvent.eventData.length, 2);
+  });
+
+  test('Event.surveyShown constructed', () {
+    Event generateEvent() => Event.surveyShown(surveyId: 'surveyId');
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.surveyShown);
+    expect(constructedEvent.eventData['surveyId'], 'surveyId');
+    expect(constructedEvent.eventData.length, 1);
+  });
+
+  test('Event.flutterBuildInfo constructed', () {
+    Event generateEvent() => Event.flutterBuildInfo(
+          label: 'label',
+          buildType: 'buildType',
+          command: 'command',
+          settings: 'settings',
+          error: 'error',
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.flutterBuildInfo);
+    expect(constructedEvent.eventData['label'], 'label');
+    expect(constructedEvent.eventData['buildType'], 'buildType');
+    expect(constructedEvent.eventData['command'], 'command');
+    expect(constructedEvent.eventData['settings'], 'settings');
+    expect(constructedEvent.eventData['error'], 'error');
+    expect(constructedEvent.eventData.length, 5);
+  });
+
+  test('Event.hotRunnerInfo constructed', () {
+    Event generateEvent() => Event.hotRunnerInfo(
+          label: 'label',
+          targetPlatform: 'targetPlatform',
+          sdkName: 'sdkName',
+          emulator: false,
+          fullRestart: true,
+          reason: 'reason',
+          finalLibraryCount: 5,
+          syncedLibraryCount: 6,
+          syncedClassesCount: 7,
+          syncedProceduresCount: 8,
+          syncedBytes: 9,
+          invalidatedSourcesCount: 10,
+          transferTimeInMs: 11,
+          overallTimeInMs: 12,
+          compileTimeInMs: 13,
+          findInvalidatedTimeInMs: 14,
+          scannedSourcesCount: 15,
+          reassembleTimeInMs: 16,
+          reloadVMTimeInMs: 17,
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.hotRunnerInfo);
+    expect(constructedEvent.eventData['label'], 'label');
+    expect(constructedEvent.eventData['targetPlatform'], 'targetPlatform');
+    expect(constructedEvent.eventData['sdkName'], 'sdkName');
+    expect(constructedEvent.eventData['emulator'], false);
+    expect(constructedEvent.eventData['fullRestart'], true);
+    expect(constructedEvent.eventData['reason'], 'reason');
+    expect(constructedEvent.eventData['finalLibraryCount'], 5);
+    expect(constructedEvent.eventData['syncedLibraryCount'], 6);
+    expect(constructedEvent.eventData['syncedClassesCount'], 7);
+    expect(constructedEvent.eventData['syncedProceduresCount'], 8);
+    expect(constructedEvent.eventData['syncedBytes'], 9);
+    expect(constructedEvent.eventData['invalidatedSourcesCount'], 10);
+    expect(constructedEvent.eventData['transferTimeInMs'], 11);
+    expect(constructedEvent.eventData['overallTimeInMs'], 12);
+    expect(constructedEvent.eventData['compileTimeInMs'], 13);
+    expect(constructedEvent.eventData['findInvalidatedTimeInMs'], 14);
+    expect(constructedEvent.eventData['scannedSourcesCount'], 15);
+    expect(constructedEvent.eventData['reassembleTimeInMs'], 16);
+    expect(constructedEvent.eventData['reloadVMTimeInMs'], 17);
+    expect(constructedEvent.eventData.length, 19);
+  });
+
+  test('Event.flutterCommandResult constructed', () {
+    Event generateEvent() => Event.flutterCommandResult(
+          commandPath: 'commandPath',
+          result: 'result',
+          commandHasTerminal: true,
+          maxRss: 123,
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.flutterCommandResult);
+    expect(constructedEvent.eventData['commandPath'], 'commandPath');
+    expect(constructedEvent.eventData['result'], 'result');
+    expect(constructedEvent.eventData['commandHasTerminal'], true);
+    expect(constructedEvent.eventData['maxRss'], 123);
+    expect(constructedEvent.eventData.length, 4);
+  });
+
+  test('Event.codeSizeAnalysis constructed', () {
+    Event generateEvent() => Event.codeSizeAnalysis(platform: 'platform');
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.codeSizeAnalysis);
+    expect(constructedEvent.eventData['platform'], 'platform');
+    expect(constructedEvent.eventData.length, 1);
+  });
+
+  test('Event.appleUsageEvent constructed', () {
+    Event generateEvent() => Event.appleUsageEvent(
+          workflow: 'workflow',
+          parameter: 'parameter',
+          result: 'result',
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.appleUsageEvent);
+    expect(constructedEvent.eventData['workflow'], 'workflow');
+    expect(constructedEvent.eventData['parameter'], 'parameter');
+    expect(constructedEvent.eventData['result'], 'result');
+    expect(constructedEvent.eventData.length, 3);
+  });
+
+  test('Event.exception constructed', () {
+    Event generateEvent() => Event.exception(
+          exception: 'exception',
+          data: {'foo': 'bar', 'baz': 1},
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.exception);
+    expect(constructedEvent.eventData['exception'], 'exception');
+    expect(constructedEvent.eventData['foo'], 'bar');
+    expect(constructedEvent.eventData['baz'], 1);
+    expect(constructedEvent.eventData.length, 3);
+  });
+
+  test('Event.timing constructed', () {
+    Event generateEvent() => Event.timing(
+          workflow: 'workflow',
+          variableName: 'variableName',
+          elapsedMilliseconds: 123,
+          label: 'label',
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.timing);
+    expect(constructedEvent.eventData['workflow'], 'workflow');
+    expect(constructedEvent.eventData['variableName'], 'variableName');
+    expect(constructedEvent.eventData['elapsedMilliseconds'], 123);
+    expect(constructedEvent.eventData['label'], 'label');
+    expect(constructedEvent.eventData.length, 4);
+  });
+
+  test('Event.commandUsageValues constructed', () {
+    Event generateEvent() => Event.commandUsageValues(
+          workflow: 'workflow',
+          commandHasTerminal: true,
+          buildBundleTargetPlatform: 'buildBundleTargetPlatform',
+          buildBundleIsModule: true,
+          buildAarProjectType: 'buildAarProjectType',
+          buildAarTargetPlatform: 'buildAarTargetPlatform',
+          buildApkTargetPlatform: 'buildApkTargetPlatform',
+          buildApkBuildMode: 'buildApkBuildMode',
+          buildApkSplitPerAbi: true,
+          buildAppBundleTargetPlatform: 'buildAppBundleTargetPlatform',
+          buildAppBundleBuildMode: 'buildAppBundleBuildMode',
+          createProjectType: 'createProjectType',
+          createAndroidLanguage: 'createAndroidLanguage',
+          createIosLanguage: 'createIosLanguage',
+          packagesNumberPlugins: 123,
+          packagesProjectModule: true,
+          packagesAndroidEmbeddingVersion: 'packagesAndroidEmbeddingVersion',
+          runIsEmulator: true,
+          runTargetName: 'runTargetName',
+          runTargetOsVersion: 'runTargetOsVersion',
+          runModeName: 'runModeName',
+          runProjectModule: true,
+          runProjectHostLanguage: 'runProjectHostLanguage',
+          runAndroidEmbeddingVersion: 'runAndroidEmbeddingVersion',
+          runEnableImpeller: true,
+          runIOSInterfaceType: 'runIOSInterfaceType',
+          runIsTest: true,
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.commandUsageValues);
+    expect(constructedEvent.eventData['workflow'], 'workflow');
+    expect(constructedEvent.eventData['buildBundleTargetPlatform'],
+        'buildBundleTargetPlatform');
+    expect(constructedEvent.eventData['buildBundleIsModule'], true);
+    expect(constructedEvent.eventData['buildAarProjectType'],
+        'buildAarProjectType');
+    expect(constructedEvent.eventData['buildAarTargetPlatform'],
+        'buildAarTargetPlatform');
+    expect(constructedEvent.eventData['buildApkTargetPlatform'],
+        'buildApkTargetPlatform');
+    expect(
+        constructedEvent.eventData['buildApkBuildMode'], 'buildApkBuildMode');
+    expect(constructedEvent.eventData['buildApkSplitPerAbi'], true);
+    expect(constructedEvent.eventData['buildAppBundleTargetPlatform'],
+        'buildAppBundleTargetPlatform');
+    expect(constructedEvent.eventData['buildAppBundleBuildMode'],
+        'buildAppBundleBuildMode');
+    expect(
+        constructedEvent.eventData['createProjectType'], 'createProjectType');
+    expect(constructedEvent.eventData['createAndroidLanguage'],
+        'createAndroidLanguage');
+    expect(
+        constructedEvent.eventData['createIosLanguage'], 'createIosLanguage');
+    expect(constructedEvent.eventData['packagesNumberPlugins'], 123);
+    expect(constructedEvent.eventData['packagesProjectModule'], true);
+    expect(constructedEvent.eventData['packagesAndroidEmbeddingVersion'],
+        'packagesAndroidEmbeddingVersion');
+    expect(constructedEvent.eventData['runIsEmulator'], true);
+    expect(constructedEvent.eventData['runTargetName'], 'runTargetName');
+    expect(
+        constructedEvent.eventData['runTargetOsVersion'], 'runTargetOsVersion');
+    expect(constructedEvent.eventData['runModeName'], 'runModeName');
+    expect(constructedEvent.eventData['runProjectModule'], true);
+    expect(constructedEvent.eventData['runProjectHostLanguage'],
+        'runProjectHostLanguage');
+    expect(constructedEvent.eventData['runAndroidEmbeddingVersion'],
+        'runAndroidEmbeddingVersion');
+    expect(constructedEvent.eventData['runEnableImpeller'], true);
+    expect(constructedEvent.eventData['runIOSInterfaceType'],
+        'runIOSInterfaceType');
+    expect(constructedEvent.eventData.length, 27);
+  });
+
+  test('Event.analyticsException constructed', () {
+    Event generateEvent() => Event.analyticsException(
+          workflow: 'workflow',
+          error: 'error',
+          description: 'description',
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventName, DashEvent.analyticsException);
+    expect(constructedEvent.eventData['workflow'], 'workflow');
+    expect(constructedEvent.eventData['error'], 'error');
+    expect(constructedEvent.eventData['description'], 'description');
+    expect(constructedEvent.eventData.length, 3);
+  });
+
+  test('Event.devtoolsEvent constructed', () {
+    Event generateEvent() => Event.devtoolsEvent(
+          eventCategory: 'eventCategory',
+          label: 'label',
+          value: 1,
+          userInitiatedInteraction: true,
+          g3Username: 'g3Username',
+          userApp: 'userApp',
+          userBuild: 'userBuild',
+          userPlatform: 'userPlatform',
+          devtoolsPlatform: 'devtoolsPlatform',
+          devtoolsChrome: 'devtoolsChrome',
+          devtoolsVersion: 'devtoolsVersion',
+          ideLaunched: 'ideLaunched',
+          isExternalBuild: 'isExternalBuild',
+          isEmbedded: 'isEmbedded',
+          ideLaunchedFeature: 'ideLaunchedFeature',
+          isWasm: 'true',
+          uiDurationMicros: 123,
+          rasterDurationMicros: 123,
+          shaderCompilationDurationMicros: 123,
+          traceEventCount: 123,
+          cpuSampleCount: 123,
+          cpuStackDepth: 123,
+          heapDiffObjectsBefore: 123,
+          heapDiffObjectsAfter: 123,
+          heapObjectsTotal: 123,
+          rootSetCount: 123,
+          rowCount: 123,
+          inspectorTreeControllerId: 123,
+          androidAppId: 'androidAppId',
+          iosBundleId: 'iosBundleId',
+        );
+
+    final constructedEvent = generateEvent();
+
+    expect(generateEvent, returnsNormally);
+    expect(constructedEvent.eventData['eventCategory'], 'eventCategory');
+    expect(constructedEvent.eventData['label'], 'label');
+    expect(constructedEvent.eventData['value'], 1);
+    expect(constructedEvent.eventData['userInitiatedInteraction'], true);
+    expect(constructedEvent.eventData['g3Username'], 'g3Username');
+    expect(constructedEvent.eventData['userApp'], 'userApp');
+    expect(constructedEvent.eventData['userBuild'], 'userBuild');
+    expect(constructedEvent.eventData['userPlatform'], 'userPlatform');
+    expect(constructedEvent.eventData['devtoolsPlatform'], 'devtoolsPlatform');
+    expect(constructedEvent.eventData['devtoolsChrome'], 'devtoolsChrome');
+    expect(constructedEvent.eventData['devtoolsVersion'], 'devtoolsVersion');
+    expect(constructedEvent.eventData['ideLaunched'], 'ideLaunched');
+    expect(constructedEvent.eventData['isExternalBuild'], 'isExternalBuild');
+    expect(constructedEvent.eventData['isEmbedded'], 'isEmbedded');
+    expect(
+        constructedEvent.eventData['ideLaunchedFeature'], 'ideLaunchedFeature');
+    expect(constructedEvent.eventData['isWasm'], 'true');
+
+    expect(constructedEvent.eventData['uiDurationMicros'], 123);
+    expect(constructedEvent.eventData['rasterDurationMicros'], 123);
+    expect(constructedEvent.eventData['shaderCompilationDurationMicros'], 123);
+    expect(constructedEvent.eventData['traceEventCount'], 123);
+    expect(constructedEvent.eventData['cpuSampleCount'], 123);
+    expect(constructedEvent.eventData['cpuStackDepth'], 123);
+    expect(constructedEvent.eventData['heapDiffObjectsBefore'], 123);
+    expect(constructedEvent.eventData['heapDiffObjectsAfter'], 123);
+    expect(constructedEvent.eventData['heapObjectsTotal'], 123);
+    expect(constructedEvent.eventData['rootSetCount'], 123);
+    expect(constructedEvent.eventData['rowCount'], 123);
+    expect(constructedEvent.eventData['inspectorTreeControllerId'], 123);
+    expect(constructedEvent.eventData['androidAppId'], 'androidAppId');
+    expect(constructedEvent.eventData['iosBundleId'], 'iosBundleId');
+    expect(constructedEvent.eventData.length, 30);
+  });
+
+  test('Confirm all constructors were checked', () {
+    var constructorCount = 0;
+    for (final declaration in reflectClass(Event).declarations.keys) {
+      // Count public constructors but omit private constructors
+      if (declaration.toString().contains('Event.') &&
+          !declaration.toString().contains('Event._')) {
+        constructorCount++;
+      }
+    }
+
+    // Change this integer below if your PR either adds or removes
+    // an Event constructor
+    final eventsAccountedForInTests = 27;
+    expect(eventsAccountedForInTests, constructorCount,
+        reason: 'If you added or removed an event constructor, '
+            'ensure you have updated '
+            '`pkgs/unified_analytics/test/event_test.dart` '
+            'to reflect the changes made');
+  });
+
+  test('Serializing event to json successful', () {
+    final event = Event.analyticsException(
+      workflow: 'workflow',
+      error: 'error',
+      description: 'description',
+    );
+
+    final expectedResult = '{"eventName":"analytics_exception",'
+        '"eventData":{"workflow":"workflow",'
+        '"error":"error",'
+        '"description":"description"}}';
+
+    expect(event.toJson(), expectedResult);
+  });
+
+  test('Deserializing string to event successful', () {
+    final eventJson = '{"eventName":"analytics_exception",'
+        '"eventData":{"workflow":"workflow",'
+        '"error":"error",'
+        '"description":"description"}}';
+
+    final eventConstructed = Event.fromJson(eventJson);
+    expect(eventConstructed, isNotNull);
+    eventConstructed!;
+
+    expect(eventConstructed.eventName, DashEvent.analyticsException);
+    expect(eventConstructed.eventData, {
+      'workflow': 'workflow',
+      'error': 'error',
+      'description': 'description',
+    });
+  });
+
+  test('Deserializing string to event unsuccessful for invalid eventName', () {
+    final eventJson = '{"eventName":"NOT_VALID_NAME",'
+        '"eventData":{"workflow":"workflow",'
+        '"error":"error",'
+        '"description":"description"}}';
+
+    final eventConstructed = Event.fromJson(eventJson);
+    expect(eventConstructed, isNull);
+  });
+
+  test('Deserializing string to event unsuccessful for invalid eventData', () {
+    final eventJson = '{"eventName":"analytics_exception",'
+        '"eventData": "not_valid_event_data"}';
+
+    final eventConstructed = Event.fromJson(eventJson);
+    expect(eventConstructed, isNull);
+  });
+}
diff --git a/pkgs/unified_analytics/test/events_with_fake_test.dart b/pkgs/unified_analytics/test/events_with_fake_test.dart
new file mode 100644
index 0000000..9794275
--- /dev/null
+++ b/pkgs/unified_analytics/test/events_with_fake_test.dart
@@ -0,0 +1,146 @@
+// Copyright (c) 2023, 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.
+
+import 'package:clock/clock.dart';
+import 'package:file/file.dart';
+import 'package:file/memory.dart';
+import 'package:test/test.dart';
+
+import 'package:unified_analytics/src/constants.dart';
+import 'package:unified_analytics/src/enums.dart';
+import 'package:unified_analytics/src/survey_handler.dart';
+import 'package:unified_analytics/unified_analytics.dart';
+
+void main() {
+  // The fake analytics instance can be used to ensure events
+  // are being sent when invoking methods on the `Analytics` instance
+
+  late FakeAnalytics fakeAnalytics;
+  late MemoryFileSystem fs;
+  late Directory homeDirectory;
+  late File dismissedSurveyFile;
+
+  /// Survey to load into the fake instance to fetch
+  ///
+  /// The 1.0 sample rate means that this will always show
+  /// up from the method to fetch available surveys
+  final testSurvey = Survey(
+    uniqueId: 'uniqueId',
+    startDate: DateTime(2022, 1, 1),
+    endDate: DateTime(2022, 12, 31),
+    description: 'description',
+    snoozeForMinutes: 10,
+    samplingRate: 1.0, // 100% sample rate
+    excludeDashToolList: [],
+    conditionList: <Condition>[],
+    buttonList: [
+      SurveyButton(
+        buttonText: 'buttonText',
+        action: 'accept',
+        promptRemainsVisible: false,
+      ),
+      SurveyButton(
+        buttonText: 'buttonText',
+        action: 'dismiss',
+        promptRemainsVisible: false,
+      ),
+    ],
+  );
+
+  setUp(() async {
+    fs = MemoryFileSystem.test(style: FileSystemStyle.posix);
+    homeDirectory = fs.directory('home');
+    dismissedSurveyFile = homeDirectory
+        .childDirectory(kDartToolDirectoryName)
+        .childFile(kDismissedSurveyFileName);
+
+    final initialAnalytics = Analytics.fake(
+      tool: DashTool.flutterTool,
+      homeDirectory: homeDirectory,
+      dartVersion: 'dartVersion',
+      toolsMessageVersion: 1,
+      fs: fs,
+      platform: DevicePlatform.macos,
+    );
+    initialAnalytics.clientShowedMessage();
+
+    // Recreate a second instance since events cannot be sent on
+    // the first run
+    withClock(Clock.fixed(DateTime(2022, 3, 3)), () {
+      final toolsMessageVersion = kToolsMessageVersion;
+      fakeAnalytics = Analytics.fake(
+        tool: DashTool.flutterTool,
+        homeDirectory: homeDirectory,
+        dartVersion: 'dartVersion',
+        platform: DevicePlatform.macos,
+        fs: fs,
+        toolsMessageVersion: toolsMessageVersion,
+        surveyHandler: FakeSurveyHandler.fromList(
+          dismissedSurveyFile: dismissedSurveyFile,
+          initializedSurveys: [testSurvey],
+        ),
+      );
+    });
+  });
+
+  test('event sent when survey shown', () async {
+    final surveyList = await fakeAnalytics.fetchAvailableSurveys();
+    expect(surveyList.length, 1);
+    expect(fakeAnalytics.sentEvents.length, 0);
+
+    final survey = surveyList.first;
+    expect(survey.uniqueId, 'uniqueId');
+
+    // Simulate the survey being shown
+    fakeAnalytics.surveyShown(survey);
+
+    expect(fakeAnalytics.sentEvents.length, 1);
+    expect(fakeAnalytics.sentEvents.last.eventName, DashEvent.surveyShown);
+    expect(fakeAnalytics.sentEvents.last.eventData, {'surveyId': 'uniqueId'});
+  });
+
+  test('event sent when survey accepted', () async {
+    final surveyList = await fakeAnalytics.fetchAvailableSurveys();
+    expect(surveyList.length, 1);
+    expect(fakeAnalytics.sentEvents.length, 0);
+
+    final survey = surveyList.first;
+    expect(survey.uniqueId, 'uniqueId');
+
+    // Simulate the survey being shown
+    //
+    // The first button is the accept button
+    fakeAnalytics.surveyInteracted(
+      survey: survey,
+      surveyButton: survey.buttonList.first,
+    );
+
+    expect(fakeAnalytics.sentEvents.length, 1);
+    expect(fakeAnalytics.sentEvents.last.eventName, DashEvent.surveyAction);
+    expect(fakeAnalytics.sentEvents.last.eventData,
+        {'surveyId': 'uniqueId', 'status': 'accept'});
+  });
+
+  test('event sent when survey rejected', () async {
+    final surveyList = await fakeAnalytics.fetchAvailableSurveys();
+    expect(surveyList.length, 1);
+    expect(fakeAnalytics.sentEvents.length, 0);
+
+    final survey = surveyList.first;
+    expect(survey.uniqueId, 'uniqueId');
+
+    // Simulate the survey being shown
+    //
+    // The last button is the reject button
+    fakeAnalytics.surveyInteracted(
+      survey: survey,
+      surveyButton: survey.buttonList.last,
+    );
+
+    expect(fakeAnalytics.sentEvents.length, 1);
+    expect(fakeAnalytics.sentEvents.last.eventName, DashEvent.surveyAction);
+    expect(fakeAnalytics.sentEvents.last.eventData,
+        {'surveyId': 'uniqueId', 'status': 'dismiss'});
+  });
+}
diff --git a/pkgs/unified_analytics/test/legacy_analytics_test.dart b/pkgs/unified_analytics/test/legacy_analytics_test.dart
new file mode 100644
index 0000000..36acee9
--- /dev/null
+++ b/pkgs/unified_analytics/test/legacy_analytics_test.dart
@@ -0,0 +1,325 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:io' as io;
+
+import 'package:file/file.dart';
+import 'package:file/memory.dart';
+import 'package:test/test.dart';
+
+import 'package:unified_analytics/src/enums.dart';
+import 'package:unified_analytics/unified_analytics.dart';
+
+void main() {
+  late MemoryFileSystem fs;
+  late Directory home;
+  late Analytics analytics;
+
+  const homeDirName = 'home';
+  const initialTool = DashTool.flutterTool;
+  const toolsMessageVersion = 1;
+  const toolsMessage = 'toolsMessage';
+  const flutterChannel = 'flutterChannel';
+  const flutterVersion = 'flutterVersion';
+  const dartVersion = 'dartVersion';
+  const platform = DevicePlatform.macos;
+
+  setUp(() {
+    // Setup the filesystem with the home directory
+    final fsStyle =
+        io.Platform.isWindows ? FileSystemStyle.windows : FileSystemStyle.posix;
+    fs = MemoryFileSystem.test(style: fsStyle);
+    home = fs.directory(homeDirName);
+  });
+
+  test('Honor legacy dart analytics opt out', () {
+    // Create the file for the dart legacy opt out
+    final dartLegacyConfigFile =
+        home.childDirectory('.dart').childFile('dartdev.json');
+    dartLegacyConfigFile.createSync(recursive: true);
+    dartLegacyConfigFile.writeAsStringSync('''
+{
+  "firstRun": false,
+  "enabled": false,
+  "disclosureShown": true,
+  "clientId": "52710e60-7c70-4335-b3a4-9d922630f12a"
+}
+''');
+
+    // The main analytics instance, other instances can be spawned within tests
+    // to test how to instances running together work
+    analytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    expect(analytics.telemetryEnabled, false);
+  });
+
+  test('Telemetry enabled if legacy dart analytics is enabled', () {
+    // Create the file for the dart legacy opt out
+    final dartLegacyConfigFile =
+        home.childDirectory('.dart').childFile('dartdev.json');
+    dartLegacyConfigFile.createSync(recursive: true);
+    dartLegacyConfigFile.writeAsStringSync('''
+{
+  "firstRun": false,
+  "enabled": true,
+  "disclosureShown": true,
+  "clientId": "52710e60-7c70-4335-b3a4-9d922630f12a"
+}
+''');
+
+    // The main analytics instance, other instances can be spawned within tests
+    // to test how to instances running together work
+    analytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    expect(analytics.telemetryEnabled, true);
+  });
+
+  test('Honor legacy flutter analytics opt out', () {
+    // Create the file for the flutter legacy opt out
+    final flutterLegacyConfigFile =
+        home.childDirectory('.dart').childFile('dartdev.json');
+    flutterLegacyConfigFile.createSync(recursive: true);
+    flutterLegacyConfigFile.writeAsStringSync('''
+{
+  "firstRun": false,
+  "clientId": "4c3a3d1e-e545-47e7-b4f8-10129f6ab169",
+  "enabled": false
+}
+''');
+
+    // The main analytics instance, other instances can be spawned within tests
+    // to test how to instances running together work
+    analytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    expect(analytics.telemetryEnabled, false);
+  });
+
+  test('Telemetry enabled if legacy flutter analytics is enabled', () {
+    // Create the file for the flutter legacy opt out
+    final flutterLegacyConfigFile =
+        home.childDirectory('.dart').childFile('dartdev.json');
+    flutterLegacyConfigFile.createSync(recursive: true);
+    flutterLegacyConfigFile.writeAsStringSync('''
+{
+  "firstRun": false,
+  "clientId": "4c3a3d1e-e545-47e7-b4f8-10129f6ab169",
+  "enabled": true
+}
+''');
+
+    // The main analytics instance, other instances can be spawned within tests
+    // to test how to instances running together work
+    analytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    expect(analytics.telemetryEnabled, true);
+  });
+
+  test('Honor legacy devtools analytics opt out', () {
+    // Create the file for the devtools legacy opt out
+    final devtoolsLegacyConfigFile =
+        home.childDirectory('.flutter-devtools').childFile('.devtools');
+    devtoolsLegacyConfigFile.createSync(recursive: true);
+    devtoolsLegacyConfigFile.writeAsStringSync('''
+{
+  "analyticsEnabled": false,
+  "isFirstRun": false,
+  "lastReleaseNotesVersion": "2.31.0",
+  "2023-Q4": {
+    "surveyActionTaken": false,
+    "surveyShownCount": 0
+  }
+}
+''');
+
+    // The main analytics instance, other instances can be spawned within tests
+    // to test how to instances running together work
+    analytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    expect(analytics.telemetryEnabled, false);
+  });
+
+  test('Telemetry enabled if legacy devtools analytics is enabled', () {
+    // Create the file for the devtools legacy opt out
+    final devtoolsLegacyConfigFile =
+        home.childDirectory('.flutter-devtools').childFile('.devtools');
+    devtoolsLegacyConfigFile.createSync(recursive: true);
+    devtoolsLegacyConfigFile.writeAsStringSync('''
+{
+  "analyticsEnabled": true,
+  "isFirstRun": false,
+  "lastReleaseNotesVersion": "2.31.0",
+  "2023-Q4": {
+    "surveyActionTaken": false,
+    "surveyShownCount": 0
+  }
+}
+''');
+
+    // The main analytics instance, other instances can be spawned within tests
+    // to test how to instances running together work
+    analytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    expect(analytics.telemetryEnabled, true);
+  });
+
+  test('Telemetry disabled if dart config file corrupted', () {
+    // Create the file for the dart legacy opt out with text that
+    // is not valid JSON
+    final dartLegacyConfigFile =
+        home.childDirectory('.dart').childFile('dartdev.json');
+    dartLegacyConfigFile.createSync(recursive: true);
+    dartLegacyConfigFile.writeAsStringSync('''
+NOT VALID JSON
+{
+  "firstRun": false,
+  "clientId": "4c3a3d1e-e545-47e7-b4f8-10129f6ab169",
+  "enabled": true
+}
+''');
+
+    // The main analytics instance, other instances can be spawned within tests
+    // to test how to instances running together work
+    analytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    expect(analytics.telemetryEnabled, false);
+  });
+
+  test('Telemetry disabled if devtools config file corrupted', () {
+    // Create the file for the devtools legacy opt out with text that
+    // is not valid JSON
+    final devtoolsLegacyConfigFile =
+        home.childDirectory('.flutter-devtools').childFile('.devtools');
+    devtoolsLegacyConfigFile.createSync(recursive: true);
+    devtoolsLegacyConfigFile.writeAsStringSync('''
+NOT VALID JSON
+{
+  "analyticsEnabled": true,
+  "isFirstRun": false,
+  "lastReleaseNotesVersion": "2.31.0",
+  "2023-Q4": {
+    "surveyActionTaken": false,
+    "surveyShownCount": 0
+  }
+}
+''');
+
+    // The main analytics instance, other instances can be spawned within tests
+    // to test how to instances running together work
+    analytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    expect(analytics.telemetryEnabled, false);
+  });
+
+  test('Telemetry disabled if flutter config file corrupted', () {
+    // Create the file for the flutter legacy opt out with text that
+    // is not valid JSON
+    final fluttterLegacyConfigFile =
+        home.childDirectory('.dart').childFile('dartdev.json');
+    fluttterLegacyConfigFile.createSync(recursive: true);
+    fluttterLegacyConfigFile.writeAsStringSync('''
+NOT VALID JSON
+{
+  "firstRun": false,
+  "clientId": "4c3a3d1e-e545-47e7-b4f8-10129f6ab169",
+  "enabled": true
+}
+''');
+
+    // The main analytics instance, other instances can be spawned within tests
+    // to test how to instances running together work
+    analytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    expect(analytics.telemetryEnabled, false);
+  });
+}
diff --git a/pkgs/unified_analytics/test/log_handler_test.dart b/pkgs/unified_analytics/test/log_handler_test.dart
new file mode 100644
index 0000000..db14d96
--- /dev/null
+++ b/pkgs/unified_analytics/test/log_handler_test.dart
@@ -0,0 +1,381 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:convert';
+
+import 'package:file/file.dart';
+import 'package:file/memory.dart';
+import 'package:test/fake.dart';
+import 'package:test/test.dart';
+
+import 'package:unified_analytics/src/constants.dart';
+import 'package:unified_analytics/src/enums.dart';
+import 'package:unified_analytics/src/log_handler.dart';
+import 'package:unified_analytics/src/utils.dart';
+import 'package:unified_analytics/unified_analytics.dart';
+
+void main() {
+  late FakeAnalytics analytics;
+  late Directory homeDirectory;
+  late MemoryFileSystem fs;
+  late File logFile;
+
+  final testEvent = Event.hotReloadTime(timeMs: 10);
+
+  setUp(() {
+    fs = MemoryFileSystem.test(style: FileSystemStyle.posix);
+    homeDirectory = fs.directory('home');
+    logFile = homeDirectory
+        .childDirectory(kDartToolDirectoryName)
+        .childFile(kLogFileName);
+
+    // Create the initialization analytics instance to onboard the tool
+    final initializationAnalytics = Analytics.fake(
+      tool: DashTool.flutterTool,
+      homeDirectory: homeDirectory,
+      dartVersion: 'dartVersion',
+      fs: fs,
+      platform: DevicePlatform.macos,
+    );
+    initializationAnalytics.clientShowedMessage();
+
+    // This instance is free to send events since the instance above
+    // has confirmed that the client has shown the message
+    analytics = Analytics.fake(
+      tool: DashTool.flutterTool,
+      homeDirectory: homeDirectory,
+      dartVersion: 'dartVersion',
+      fs: fs,
+      platform: DevicePlatform.macos,
+    );
+  });
+
+  test('Ensure that log file is created', () {
+    expect(logFile.existsSync(), true);
+  });
+
+  test('LogFileStats is null before events are sent', () {
+    expect(analytics.logFileStats(), isNull);
+  });
+
+  test('LogFileStats returns valid response after sent events', () async {
+    final countOfEventsToSend = 10;
+
+    for (var i = 0; i < countOfEventsToSend; i++) {
+      analytics.send(testEvent);
+    }
+
+    expect(analytics.logFileStats(), isNotNull);
+    expect(logFile.readAsLinesSync().length, countOfEventsToSend);
+    expect(analytics.logFileStats()!.recordCount, countOfEventsToSend);
+  });
+
+  test('The only record in the log file is malformed', () async {
+    // Write invalid json for the only log record
+    logFile.writeAsStringSync('{{\n');
+
+    expect(logFile.readAsLinesSync().length, 1);
+    final logFileStats = analytics.logFileStats();
+    expect(logFileStats, isNull,
+        reason: 'Null should be returned since only '
+            'one record is in there and it is malformed');
+
+    analytics.sendPendingErrorEvents();
+    expect(
+        analytics.sentEvents,
+        contains(
+          Event.analyticsException(
+            workflow: 'LogFileStats.logFileStats',
+            error: 'FormatException',
+            description: 'message: Unexpected character\nsource: {{',
+          ),
+        ));
+  });
+
+  test('The first record is malformed, but rest are valid', () async {
+    // Write invalid json for the only log record
+    logFile.writeAsStringSync('{{\n');
+
+    final countOfEventsToSend = 10;
+
+    for (var i = 0; i < countOfEventsToSend; i++) {
+      analytics.send(testEvent);
+    }
+    expect(logFile.readAsLinesSync().length, countOfEventsToSend + 1);
+    final logFileStats = analytics.logFileStats();
+
+    expect(logFileStats, isNotNull);
+    expect(logFileStats!.recordCount, countOfEventsToSend);
+  });
+
+  test('Several records are malformed', () async {
+    final countOfMalformedRecords = 4;
+    for (var i = 0; i < countOfMalformedRecords; i++) {
+      final currentContents = logFile.readAsStringSync();
+      logFile.writeAsStringSync('$currentContents{{\n');
+    }
+
+    final countOfEventsToSend = 10;
+
+    for (var i = 0; i < countOfEventsToSend; i++) {
+      analytics.send(testEvent);
+    }
+
+    expect(logFile.readAsLinesSync().length,
+        countOfEventsToSend + countOfMalformedRecords);
+    final logFileStats = analytics.logFileStats();
+
+    analytics.sendPendingErrorEvents();
+    expect(logFile.readAsLinesSync().length,
+        countOfEventsToSend + countOfMalformedRecords + 1,
+        reason:
+            'There should have been on error event sent when getting stats');
+
+    expect(logFileStats, isNotNull);
+    expect(logFileStats!.recordCount, countOfEventsToSend);
+  });
+
+  test('Valid json but invalid keys', () {
+    // The second line here is missing the "events" top level
+    // key which should cause an error for that record only
+    //
+    // Important to note that this won't actually cause a FormatException
+    // like the other malformed records, instead the LogItem.fromRecord
+    // constructor will return null if all the keys are not available
+    final contents = '''
+{"client_id":"ffcea97b-db5e-4c66-98c2-3942de4fac40","events":[{"name":"hot_reload_time","params":{"timeMs":136}}],"user_properties":{"session_id":{"value":1699385899950},"flutter_channel":{"value":"ey-test-channel"},"host":{"value":"macOS"},"flutter_version":{"value":"Flutter 3.6.0-7.0.pre.47"},"dart_version":{"value":"Dart 2.19.0"},"analytics_pkg_version":{"value":"5.2.0"},"tool":{"value":"flutter-tool"},"local_time":{"value":"2023-11-07 15:37:26.685761 -0500"},"host_os_version":{"value":"Version 14.1 (Build 23B74)"},"locale":{"value":"en"},"client_ide":{"value":"VSCode"}}}
+{"client_id":"ffcea97b-db5e-4c66-98c2-3942de4fac40","WRONG_EVENT_KEY":[{"name":"hot_reload_time","params":{"timeMs":136}}],"user_properties":{"session_id":{"value":1699385899950},"flutter_channel":{"value":"ey-test-channel"},"host":{"value":"macOS"},"flutter_version":{"value":"Flutter 3.6.0-7.0.pre.47"},"dart_version":{"value":"Dart 2.19.0"},"analytics_pkg_version":{"value":"5.2.0"},"tool":{"value":"flutter-tool"},"local_time":{"value":"2023-11-07 15:37:26.685761 -0500"},"host_os_version":{"value":"Version 14.1 (Build 23B74)"},"locale":{"value":"en"},"client_ide":{"value":"VSCode"}}}
+{"client_id":"ffcea97b-db5e-4c66-98c2-3942de4fac40","events":[{"name":"hot_reload_time","params":{"timeMs":136}}],"user_properties":{"session_id":{"value":1699385899950},"flutter_channel":{"value":"ey-test-channel"},"host":{"value":"macOS"},"flutter_version":{"value":"Flutter 3.6.0-7.0.pre.47"},"dart_version":{"value":"Dart 2.19.0"},"analytics_pkg_version":{"value":"5.2.0"},"tool":{"value":"flutter-tool"},"local_time":{"value":"2023-11-07 15:37:26.685761 -0500"},"host_os_version":{"value":"Version 14.1 (Build 23B74)"},"locale":{"value":"en"},"client_ide":{"value":"VSCode"}}}
+''';
+    logFile.writeAsStringSync(contents);
+
+    final logFileStats = analytics.logFileStats();
+
+    expect(logFile.readAsLinesSync().length, 3);
+    expect(logFileStats, isNotNull);
+    expect(logFileStats!.recordCount, 2);
+  });
+
+  test('Malformed record gets phased out after several events', () async {
+    // Write invalid json for the only log record
+    logFile.writeAsStringSync('{{\n');
+
+    // Send the max number of events minus two so that we have
+    // one malformed record on top of the logs and the rest
+    // are valid log records
+    //
+    // We need to account for the event that is sent when
+    // calling [logFileStats()] fails and sends an instance
+    // of [Event.analyticsException]
+    final recordsToSendInitially = kLogFileLength - 2;
+    for (var i = 0; i < recordsToSendInitially; i++) {
+      analytics.send(testEvent);
+    }
+    final logFileStats = analytics.logFileStats();
+    analytics.sendPendingErrorEvents();
+    expect(analytics.sentEvents.last.eventName, DashEvent.analyticsException,
+        reason: 'Calling for the stats should have caused an error');
+    expect(logFile.readAsLinesSync().length, kLogFileLength);
+    expect(logFileStats, isNotNull);
+    expect(logFileStats!.recordCount, recordsToSendInitially,
+        reason: 'The first record should be malformed');
+    expect(logFile.readAsLinesSync()[0].trim(), '{{');
+
+    // Sending one more event should flush out the malformed record
+    analytics.send(testEvent);
+
+    final secondLogFileStats = analytics.logFileStats();
+    expect(analytics.sentEvents.last, testEvent);
+    expect(secondLogFileStats, isNotNull);
+    expect(secondLogFileStats!.recordCount, kLogFileLength);
+    expect(logFile.readAsLinesSync()[0].trim(), isNot('{{'));
+  });
+
+  test(
+      'Catches and discards any FileSystemException raised from attempting '
+      'to write to the log file', () async {
+    final logFilePath = 'log.txt';
+    final fs = MemoryFileSystem.test(opHandle: (context, operation) {
+      if (context == logFilePath && operation == FileSystemOp.write) {
+        throw FileSystemException(
+          'writeFrom failed',
+          logFilePath,
+          const OSError('No space left on device', 28),
+        );
+      }
+    });
+    final logFile = fs.file(logFilePath);
+    logFile.createSync();
+    final logHandler = LogHandler(logFile: logFile);
+
+    logHandler.save(data: {});
+  });
+
+  test('deletes log file larger than kMaxLogFileSize', () async {
+    var deletedLargeLogFile = false;
+    var wroteDataToLogFile = false;
+    const data = <String, Object?>{};
+    final logFile = _FakeFile('log.txt')
+      .._deleteSyncImpl = (() => deletedLargeLogFile = true)
+      .._createSyncImpl = () {}
+      .._statSyncImpl = (() => _FakeFileStat(kMaxLogFileSize + 1))
+      .._writeAsStringSync = (contents, {mode = FileMode.append}) {
+        expect(contents.trim(), data.toString());
+        expect(mode, FileMode.writeOnlyAppend);
+        wroteDataToLogFile = true;
+      };
+    final logHandler = LogHandler(logFile: logFile);
+
+    logHandler.save(data: data);
+    expect(deletedLargeLogFile, isTrue);
+    expect(wroteDataToLogFile, isTrue);
+  });
+
+  test('does not delete log file if smaller than kMaxLogFileSize', () async {
+    var wroteDataToLogFile = false;
+    const data = <String, Object?>{};
+    final logFile = _FakeFile('log.txt')
+      .._deleteSyncImpl =
+          (() => fail('called logFile.deleteSync() when file was less than '
+              'kMaxLogFileSize'))
+      .._createSyncImpl = () {}
+      .._readAsLinesSyncImpl = (() => ['three', 'previous', 'lines'])
+      .._statSyncImpl = (() => _FakeFileStat(kMaxLogFileSize - 1))
+      .._writeAsStringSync = (contents, {mode = FileMode.append}) {
+        expect(contents.trim(), data.toString());
+        expect(mode, FileMode.writeOnlyAppend);
+        wroteDataToLogFile = true;
+      };
+    final logHandler = LogHandler(logFile: logFile);
+
+    logHandler.save(data: data);
+    expect(wroteDataToLogFile, isTrue);
+  });
+
+  test('Catching cast errors for each log record silently', () async {
+    // Write a json array to the log file which will cause
+    // a cast error when parsing each line
+    logFile.writeAsStringSync('[{}, 1, 2, 3]\n');
+
+    final logFileStats = analytics.logFileStats();
+    expect(logFileStats, isNull);
+
+    // Ensure it will work as expected after writing correct logs
+    final countOfEventsToSend = 10;
+    for (var i = 0; i < countOfEventsToSend; i++) {
+      analytics.send(testEvent);
+    }
+    analytics.sendPendingErrorEvents();
+    final secondLogFileStats = analytics.logFileStats();
+
+    expect(secondLogFileStats, isNotNull);
+    expect(secondLogFileStats!.recordCount, countOfEventsToSend + 1,
+        reason: 'Plus one for the error event that is sent '
+            'from the first logFileStats call');
+  });
+
+  test(
+      'truncateStringToLength returns same string when '
+      'max length greater than string length', () {
+    final testString = 'Version 14.1 (Build 23B74)';
+    final maxLength = 100;
+
+    expect(testString.length < maxLength, true);
+
+    String runTruncateString() => truncateStringToLength(testString, maxLength);
+
+    expect(runTruncateString, returnsNormally);
+
+    final newString = runTruncateString();
+    expect(newString, testString);
+  });
+
+  test(
+      'truncateStringToLength returns truncated string when '
+      'max length less than string length', () {
+    final testString = 'Version 14.1 (Build 23B74)';
+    final maxLength = 10;
+
+    expect(testString.length > maxLength, true);
+
+    String runTruncateString() => truncateStringToLength(testString, maxLength);
+
+    expect(runTruncateString, returnsNormally);
+
+    final newString = runTruncateString();
+    expect(newString.length, maxLength);
+    expect(newString, 'Version 14');
+  });
+
+  test('truncateStringToLength handle errors for invalid max length', () {
+    final testString = 'Version 14.1 (Build 23B74)';
+    var maxLength = 0;
+    String runTruncateString() => truncateStringToLength(testString, maxLength);
+
+    expect(runTruncateString, throwsArgumentError);
+
+    maxLength = -1;
+    expect(runTruncateString, throwsArgumentError);
+  });
+
+  test('truncateStringToLength same string when max length is the same', () {
+    final testString = 'Version 14.1 (Build 23B74)';
+    final maxLength = testString.length;
+
+    String runTruncateString() => truncateStringToLength(testString, maxLength);
+    expect(runTruncateString, returnsNormally);
+
+    final newString = runTruncateString();
+    expect(newString.length, maxLength);
+    expect(newString, testString);
+  });
+}
+
+class _FakeFileStat extends Fake implements FileStat {
+  _FakeFileStat(this.size);
+
+  @override
+  final int size;
+}
+
+class _FakeFile extends Fake implements File {
+  _FakeFile(this.path);
+
+  List<String> Function()? _readAsLinesSyncImpl;
+
+  @override
+  List<String> readAsLinesSync({Encoding encoding = utf8}) =>
+      _readAsLinesSyncImpl!();
+
+  @override
+  final String path;
+
+  FileStat Function()? _statSyncImpl;
+
+  @override
+  FileStat statSync() => _statSyncImpl!();
+
+  void Function()? _deleteSyncImpl;
+
+  @override
+  void deleteSync({bool recursive = false}) => _deleteSyncImpl!();
+
+  void Function()? _createSyncImpl;
+
+  @override
+  void createSync({bool recursive = false, bool exclusive = false}) {
+    return _createSyncImpl!();
+  }
+
+  void Function(String contents, {FileMode mode})? _writeAsStringSync;
+
+  @override
+  void writeAsStringSync(
+    String contents, {
+    FileMode mode = FileMode.write,
+    Encoding encoding = utf8,
+    bool flush = false,
+  }) =>
+      _writeAsStringSync!(contents, mode: mode);
+}
diff --git a/pkgs/unified_analytics/test/no_op_analytics_test.dart b/pkgs/unified_analytics/test/no_op_analytics_test.dart
new file mode 100644
index 0000000..66c1ef6
--- /dev/null
+++ b/pkgs/unified_analytics/test/no_op_analytics_test.dart
@@ -0,0 +1,103 @@
+// Copyright (c) 2023, 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.
+
+import 'package:file/file.dart';
+import 'package:test/fake.dart';
+import 'package:test/test.dart';
+
+import 'package:unified_analytics/src/utils.dart';
+import 'package:unified_analytics/unified_analytics.dart';
+
+void main() {
+  final testEvent = Event.hotReloadTime(timeMs: 50);
+
+  test('NoOpAnalytics.telemetryEnabled is always false', () async {
+    final analytics = const NoOpAnalytics();
+
+    expect(analytics.telemetryEnabled, isFalse);
+    await analytics.setTelemetry(true);
+    expect(analytics.telemetryEnabled, isFalse);
+  });
+
+  test('NoOpAnalytics.shouldShowMessage is always false', () async {
+    final analytics = const NoOpAnalytics();
+
+    expect(analytics.shouldShowMessage, isFalse);
+    analytics.clientShowedMessage();
+    expect(analytics.shouldShowMessage, isFalse);
+  });
+
+  test('NoOpAnalytics.sendEvent() always returns null', () async {
+    final analytics = const NoOpAnalytics();
+
+    await analytics.setTelemetry(true);
+    analytics.clientShowedMessage();
+    expect(
+      analytics.send(testEvent),
+      isNull,
+    );
+  });
+
+  test('NoOpAnalytics.logFileStats() always returns null', () async {
+    final analytics = const NoOpAnalytics();
+
+    expect(analytics.logFileStats(), isNull);
+
+    await analytics.setTelemetry(true);
+    analytics.clientShowedMessage();
+    await analytics.send(testEvent);
+
+    expect(analytics.logFileStats(), isNull);
+  });
+
+  test('Home directory without write permissions', () {
+    final home = FakeDirectory(writeEnabled: false);
+
+    expect(checkDirectoryForWritePermissions(home), false);
+  });
+
+  test('Home directory with write permissions', () {
+    final home = FakeDirectory(writeEnabled: true);
+
+    expect(checkDirectoryForWritePermissions(home), true);
+  });
+
+  test('Fetching the client id', () {
+    final analytics = const NoOpAnalytics();
+    expect(analytics.clientId, 'xxxx-xxxx');
+  });
+}
+
+class FakeDirectory extends Fake implements Directory {
+  final String _fakeModeString;
+
+  /// This fake directory class allows you to pass the permissions for
+  /// the user level, the group and global permissions will default to
+  /// being denied as indicated by the last 6 characters in the mode string.
+  FakeDirectory({
+    required bool writeEnabled,
+    bool readEnabled = true,
+    bool executeEnabled = true,
+  }) : _fakeModeString = '${readEnabled ? "r" : "-"}'
+            '${writeEnabled ? "w" : "-"}'
+            '${executeEnabled ? "x" : "-"}'
+            '------' {
+    assert(_fakeModeString.length == 9);
+  }
+
+  @override
+  bool existsSync() => true;
+
+  @override
+  FileStat statSync() => FakeFileStat(_fakeModeString);
+}
+
+class FakeFileStat extends Fake implements FileStat {
+  final String _fakeModeString;
+
+  FakeFileStat(this._fakeModeString);
+
+  @override
+  String modeString() => _fakeModeString;
+}
diff --git a/pkgs/unified_analytics/test/suppression_test.dart b/pkgs/unified_analytics/test/suppression_test.dart
new file mode 100644
index 0000000..05fab15
--- /dev/null
+++ b/pkgs/unified_analytics/test/suppression_test.dart
@@ -0,0 +1,132 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:io' as io;
+
+import 'package:file/file.dart';
+import 'package:file/memory.dart';
+import 'package:test/test.dart';
+import 'package:unified_analytics/src/enums.dart';
+import 'package:unified_analytics/unified_analytics.dart';
+
+void main() {
+  late MemoryFileSystem fs;
+  late Directory home;
+  late Analytics initializationAnalytics;
+  late Analytics analytics;
+
+  const homeDirName = 'home';
+  const initialTool = DashTool.flutterTool;
+  const toolsMessageVersion = 1;
+  const toolsMessage = 'toolsMessage';
+  const flutterChannel = 'flutterChannel';
+  const flutterVersion = 'flutterVersion';
+  const dartVersion = 'dartVersion';
+  const platform = DevicePlatform.macos;
+
+  final testEvent = Event.hotReloadTime(timeMs: 50);
+
+  setUp(() {
+    // Setup the filesystem with the home directory
+    final fsStyle =
+        io.Platform.isWindows ? FileSystemStyle.windows : FileSystemStyle.posix;
+    fs = MemoryFileSystem.test(style: fsStyle);
+    home = fs.directory(homeDirName);
+
+    // This is the first analytics instance that will be used to demonstrate
+    // that events will not be sent with the first run of analytics
+    initializationAnalytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+    initializationAnalytics.clientShowedMessage();
+
+    // The main analytics instance, other instances can be spawned within tests
+    // to test how to instances running together work
+    //
+    // This instance should have the same parameters as the one above for
+    // [initializationAnalytics]
+    analytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+    analytics.clientShowedMessage();
+  });
+
+  test('Suppression works as expected', () async {
+    analytics.suppressTelemetry();
+    analytics.send(testEvent);
+
+    final logFileStats = analytics.logFileStats();
+
+    expect(logFileStats, isNull,
+        reason: 'Returns null because no records have been recorded');
+  });
+
+  test('Second instance is not suppressed', () async {
+    analytics.suppressTelemetry();
+    analytics.send(testEvent);
+
+    final logFileStats = analytics.logFileStats();
+
+    expect(logFileStats, isNull,
+        reason: 'Returns null because no records have been recorded');
+
+    // The newly created instance will not be suppressed
+    final secondAnalytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    // Using a new event here to differentiate from the first one
+    final newEvent = Event.commandExecuted(count: 2, name: 'commandName');
+    secondAnalytics.send(newEvent);
+
+    // Both instances of `Analytics` should now have data retrieved
+    // from `LogFileStats()` even though only the second instance
+    // was the instance to send an event
+    final secondLogFileStats = analytics.logFileStats()!;
+    final thirdLogFileStats = secondAnalytics.logFileStats()!;
+
+    // Series of checks for each parameter in logFileStats
+    expect(secondLogFileStats.startDateTime, thirdLogFileStats.startDateTime);
+    expect(secondLogFileStats.minsFromStartDateTime,
+        thirdLogFileStats.minsFromStartDateTime);
+    expect(secondLogFileStats.endDateTime, thirdLogFileStats.endDateTime);
+    expect(secondLogFileStats.minsFromEndDateTime,
+        thirdLogFileStats.minsFromEndDateTime);
+    expect(secondLogFileStats.sessionCount, thirdLogFileStats.sessionCount);
+    expect(secondLogFileStats.flutterChannelCount,
+        thirdLogFileStats.flutterChannelCount);
+    expect(secondLogFileStats.toolCount, thirdLogFileStats.toolCount);
+    expect(secondLogFileStats.recordCount, thirdLogFileStats.recordCount);
+    expect(secondLogFileStats.eventCount, thirdLogFileStats.eventCount);
+
+    // Ensure the correct data is in the object
+    expect(secondLogFileStats.eventCount.containsKey(newEvent.eventName.label),
+        true);
+    expect(secondLogFileStats.eventCount[newEvent.eventName.label], 1);
+  });
+}
diff --git a/pkgs/unified_analytics/test/survey_handler_test.dart b/pkgs/unified_analytics/test/survey_handler_test.dart
new file mode 100644
index 0000000..3d8c8dd
--- /dev/null
+++ b/pkgs/unified_analytics/test/survey_handler_test.dart
@@ -0,0 +1,1229 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:convert';
+
+import 'package:clock/clock.dart';
+import 'package:file/file.dart';
+import 'package:file/memory.dart';
+import 'package:test/test.dart';
+
+import 'package:unified_analytics/src/constants.dart';
+import 'package:unified_analytics/src/enums.dart';
+import 'package:unified_analytics/src/survey_handler.dart';
+import 'package:unified_analytics/src/utils.dart';
+import 'package:unified_analytics/unified_analytics.dart';
+
+void main() {
+  final testEvent = Event.hotReloadTime(timeMs: 10);
+
+  group('Unit testing function sampleRate:', () {
+    // Set a string that can be used in place of a survey's unique ID
+    final iterations = 1000;
+    final uuid = Uuid(123);
+    final uniqueSurveyId = uuid.generateV4();
+
+    // Set how much the actual sampled rate can be (allowing 5% of variability)
+    final marginOfError = 0.05;
+
+    test('Unit testing the sampleRate method', () {
+      // These strings had a predetermined output from the utility function
+      final string1 = 'string1';
+      final string2 = 'string2';
+      expect(sampleRate(string1, string2), 0.40);
+    });
+
+    test('Simulating with various sample rates', () {
+      final sampleRateToTestList = [
+        0.10,
+        0.25,
+        0.50,
+        0.75,
+        0.80,
+        0.95,
+      ];
+      for (final sampleRateToTest in sampleRateToTestList) {
+        var count = 0;
+        for (var i = 0; i < iterations; i++) {
+          // Regenerate the client id to simulate a unique user
+          final generatedClientId = uuid.generateV4();
+          if (sampleRate(uniqueSurveyId, generatedClientId) <=
+              sampleRateToTest) {
+            count += 1;
+          }
+        }
+
+        final actualSampledRate = count / iterations;
+        final actualMarginOfError =
+            (sampleRateToTest - actualSampledRate).abs();
+
+        expect(actualMarginOfError < marginOfError, true,
+            reason: 'Failed on sample rate = $sampleRateToTest with'
+                ' actual rate $actualMarginOfError '
+                'and a margin of error = $marginOfError');
+      }
+    });
+  });
+
+  group('Unit testing function checkSurveyDate:', () {
+    final date = DateTime(2023, 5, 1);
+    // Two surveys created, one that is within the survey date
+    // range, and one that is not
+    final validSurvey = Survey(
+      uniqueId: 'uniqueId',
+      startDate: DateTime(2023, 1, 1),
+      endDate: DateTime(2023, 12, 31),
+      description: 'description',
+      snoozeForMinutes: 10,
+      samplingRate: 1.0,
+      excludeDashToolList: [],
+      conditionList: <Condition>[],
+      buttonList: [],
+    );
+    final invalidSurvey = Survey(
+      uniqueId: 'uniqueId',
+      startDate: DateTime(2022, 1, 1),
+      endDate: DateTime(2022, 12, 31),
+      description: 'description',
+      snoozeForMinutes: 10,
+      samplingRate: 1.0,
+      excludeDashToolList: [],
+      conditionList: <Condition>[],
+      buttonList: [],
+    );
+
+    test('expired survey', () {
+      final clock = Clock.fixed(date);
+      withClock(clock, () {
+        expect(SurveyHandler.checkSurveyDate(invalidSurvey), false);
+      });
+    });
+
+    test('valid survey', () {
+      final clock = Clock.fixed(date);
+      withClock(clock, () {
+        expect(SurveyHandler.checkSurveyDate(validSurvey), true);
+      });
+    });
+  });
+
+  group('Unit testing function parseSurveysFromJson', () {
+    final validContents = '''
+[
+  {
+    "uniqueId": "xxxxx",
+    "startDate": "2023-06-01T09:00:00-07:00",
+    "endDate": "2023-06-30T09:00:00-07:00",
+    "description": "xxxxxxx",
+    "snoozeForMinutes": "10",
+    "samplingRate": "1.0",
+    "excludeDashTools": [],
+    "conditions": [
+      {
+        "field": "logFileStats.recordCount",
+        "operator": ">=",
+        "value": 1000
+      },
+      {
+        "field": "logFileStats.toolCount.flutter-tool",
+        "operator": "<",
+        "value": 3
+      }
+    ],
+    "buttons": [
+        {
+            "buttonText": "Take Survey",
+            "action": "accept",
+            "url": "https://google.qualtrics.com/jfe/form/SV_5gsB2EuG324y2",
+            "promptRemainsVisible": false
+        }
+    ]
+  }
+]
+''';
+
+    // The value for the condition is not a valid integer
+    final invalidConditionValueContents = '''
+[
+  {
+    "uniqueId": "xxxxx",
+    "startDate": "2023-06-01T09:00:00-07:00",
+    "endDate": "2023-06-30T09:00:00-07:00",
+    "description": "xxxxxxx",
+    "snoozeForMinutes": "10",
+    "samplingRate": "1.0",
+    "excludeDashTools": [],
+    "conditions": [
+      {
+        "field": "logFileStats.recordCount",
+        "operator": ">=",
+        "value": "1000xxxx"
+      }
+    ],
+    "buttons": [
+        {
+            "buttonText": "Take Survey",
+            "action": "accept",
+            "url": "https://google.qualtrics.com/jfe/form/SV_5gsB2EuG324y2",
+            "promptRemainsVisible": false
+        }
+    ]
+  }
+]
+''';
+
+    // Using a dash tool in the excludeDashTools array that is not a valid
+    // DashTool label
+    final invalidDashToolContents = '''
+[
+  {
+    "uniqueId": "xxxxx",
+    "startDate": "2023-06-01T09:00:00-07:00",
+    "endDate": "2023-06-30T09:00:00-07:00",
+    "description": "xxxxxxx",
+    "snoozeForMinutes": "10",
+    "samplingRate": "1.0",
+    "excludeDashTools": [
+      "not-a-valid-dash-tool"
+    ],
+    "conditions": [
+      {
+        "field": "logFileStats.recordCount",
+        "operator": ">=",
+        "value": 1000
+      },
+      {
+        "field": "logFileStats.toolCount.flutter-tool",
+        "operator": "<",
+        "value": 3
+      }
+    ],
+    "buttons": [
+        {
+            "buttonText": "Take Survey",
+            "action": "accept",
+            "url": "https://google.qualtrics.com/jfe/form/SV_5gsB2EuG324y2",
+            "promptRemainsVisible": false
+        }
+    ]
+  }
+]
+''';
+
+    test('valid json', () {
+      withClock(Clock.fixed(DateTime(2023, 6, 15)), () {
+        final parsedSurveys = SurveyHandler.parseSurveysFromJson(
+            jsonDecode(validContents) as List);
+
+        expect(parsedSurveys.length, 1);
+        expect(parsedSurveys.first.conditionList.length, 2);
+
+        final firstCondition = parsedSurveys.first.conditionList.first;
+        final secondCondition = parsedSurveys.first.conditionList[1];
+
+        expect(firstCondition.field, 'logFileStats.recordCount');
+        expect(firstCondition.operatorString, '>=');
+        expect(firstCondition.value, 1000);
+
+        expect(secondCondition.field, 'logFileStats.toolCount.flutter-tool');
+        expect(secondCondition.operatorString, '<');
+        expect(secondCondition.value, 3);
+
+        expect(parsedSurveys.first.buttonList.length, 1);
+        expect(
+            parsedSurveys.first.buttonList.first.promptRemainsVisible, false);
+      });
+    });
+
+    test('invalid condition json', () {
+      withClock(Clock.fixed(DateTime(2023, 6, 15)), () {
+        final parsedSurveys = SurveyHandler.parseSurveysFromJson(
+            jsonDecode(invalidConditionValueContents) as List);
+
+        expect(parsedSurveys.length, 0,
+            reason: 'The condition value is not a '
+                'proper integer so it should error returning no surveys');
+      });
+    });
+
+    test('invalid dash tool json', () {
+      withClock(Clock.fixed(DateTime(2023, 6, 15)), () {
+        final parsedSurveys = SurveyHandler.parseSurveysFromJson(
+            jsonDecode(invalidDashToolContents) as List);
+
+        expect(parsedSurveys.length, 0,
+            reason: 'The dash tool in the exclude array is not valid '
+                'so it should error returning no surveys');
+      });
+    });
+  });
+
+  group('Testing with FakeSurveyHandler', () {
+    late Analytics analytics;
+    late Directory homeDirectory;
+    late MemoryFileSystem fs;
+    late File clientIdFile;
+    late File dismissedSurveyFile;
+
+    setUp(() {
+      fs = MemoryFileSystem.test(style: FileSystemStyle.posix);
+      homeDirectory = fs.directory('home');
+
+      // Write the client ID file out so that we don't get
+      // a randomly assigned id for this test generated within
+      // the analytics constructor
+      clientIdFile = homeDirectory
+          .childDirectory(kDartToolDirectoryName)
+          .childFile(kClientIdFileName);
+      clientIdFile.createSync(recursive: true);
+      clientIdFile.writeAsStringSync('string1');
+
+      // Assign the json file that will hold the persisted surveys
+      dismissedSurveyFile = homeDirectory
+          .childDirectory(kDartToolDirectoryName)
+          .childFile(kDismissedSurveyFileName);
+
+      // Setup two tools to be onboarded with this package so
+      // that we can simulate two different tools interacting with
+      // surveys
+      //
+      // This is especially useful when testing the "excludeDashTools" array
+      // to prevent certain tools from getting a survey from this package
+      final initialAnalyticsFlutter = Analytics.fake(
+        tool: DashTool.flutterTool,
+        homeDirectory: homeDirectory,
+        dartVersion: 'dartVersion',
+        fs: fs,
+        platform: DevicePlatform.macos,
+      );
+      final initialAnalyticsDart = Analytics.fake(
+        tool: DashTool.dartTool,
+        homeDirectory: homeDirectory,
+        dartVersion: 'dartVersion',
+        fs: fs,
+        platform: DevicePlatform.macos,
+      );
+      initialAnalyticsFlutter.clientShowedMessage();
+      initialAnalyticsDart.clientShowedMessage();
+    });
+
+    test('returns valid survey', () async {
+      await withClock(Clock.fixed(DateTime(2023, 3, 3)), () async {
+        analytics = Analytics.fake(
+          tool: DashTool.flutterTool,
+          homeDirectory: homeDirectory,
+          dartVersion: 'dartVersion',
+          fs: fs,
+          platform: DevicePlatform.macos,
+          surveyHandler: FakeSurveyHandler.fromList(
+            dismissedSurveyFile: dismissedSurveyFile,
+            initializedSurveys: <Survey>[
+              Survey(
+                uniqueId: 'uniqueId',
+                startDate: DateTime(2023, 1, 1),
+                endDate: DateTime(2023, 12, 31),
+                description: 'description',
+                snoozeForMinutes: 10,
+                samplingRate: 1.0,
+                excludeDashToolList: [],
+                conditionList: <Condition>[
+                  Condition('logFileStats.recordCount', '>=', 50),
+                  Condition('logFileStats.toolCount.flutter-tool', '>', 0),
+                ],
+                buttonList: [
+                  SurveyButton(
+                    buttonText: 'buttonText',
+                    action: 'accept',
+                    url: 'http://example.com',
+                    promptRemainsVisible: false,
+                  ),
+                ],
+              ),
+            ],
+          ),
+        );
+
+        // Simulate 60 events to send so that the first condition is satisified
+        for (var i = 0; i < 60; i++) {
+          analytics.send(testEvent);
+        }
+
+        final fetchedSurveys = await analytics.fetchAvailableSurveys();
+
+        expect(fetchedSurveys.length, 1);
+
+        final survey = fetchedSurveys.first;
+        expect(survey.conditionList.length, 2);
+        expect(survey.buttonList.length, 1);
+      });
+    });
+
+    test('does not return expired survey', () async {
+      await withClock(Clock.fixed(DateTime(2023, 3, 3)), () async {
+        analytics = Analytics.fake(
+          tool: DashTool.flutterTool,
+          homeDirectory: homeDirectory,
+          dartVersion: 'dartVersion',
+          fs: fs,
+          platform: DevicePlatform.macos,
+          surveyHandler: FakeSurveyHandler.fromList(
+            dismissedSurveyFile: dismissedSurveyFile,
+            initializedSurveys: <Survey>[
+              Survey(
+                uniqueId: 'uniqueId',
+                startDate: DateTime(2022, 1, 1),
+                endDate: DateTime(2022, 12, 31),
+                description: 'description',
+                snoozeForMinutes: 10,
+                samplingRate: 1.0,
+                excludeDashToolList: [],
+                conditionList: <Condition>[
+                  Condition('logFileStats.recordCount', '>=', 50),
+                  Condition('logFileStats.toolCount.flutter-tool', '>', 0),
+                ],
+                buttonList: [],
+              ),
+            ],
+          ),
+        );
+
+        // Simulate 60 events to send so that the first condition is satisified
+        for (var i = 0; i < 60; i++) {
+          analytics.send(testEvent);
+        }
+
+        final fetchedSurveys = await analytics.fetchAvailableSurveys();
+
+        expect(fetchedSurveys.length, 0);
+      });
+    });
+
+    test('does not return survey if opted out of telemetry', () async {
+      await withClock(Clock.fixed(DateTime(2023, 3, 3)), () async {
+        analytics = Analytics.fake(
+          tool: DashTool.flutterTool,
+          homeDirectory: homeDirectory,
+          dartVersion: 'dartVersion',
+          fs: fs,
+          platform: DevicePlatform.macos,
+          surveyHandler: FakeSurveyHandler.fromList(
+            dismissedSurveyFile: dismissedSurveyFile,
+            initializedSurveys: <Survey>[
+              Survey(
+                uniqueId: 'uniqueId',
+                startDate: DateTime(2023, 1, 1),
+                endDate: DateTime(2023, 12, 31),
+                description: 'description',
+                snoozeForMinutes: 10,
+                samplingRate: 1.0,
+                excludeDashToolList: [],
+                conditionList: <Condition>[
+                  Condition('logFileStats.recordCount', '>=', 50),
+                  Condition('logFileStats.toolCount.flutter-tool', '>', 0),
+                ],
+                buttonList: [],
+              ),
+            ],
+          ),
+        );
+
+        // Simulate 60 events to send so that the first condition is satisified
+        for (var i = 0; i < 60; i++) {
+          analytics.send(testEvent);
+        }
+
+        await analytics.setTelemetry(false);
+        expect(analytics.okToSend, false);
+
+        final fetchedSurveys = await analytics.fetchAvailableSurveys();
+
+        expect(fetchedSurveys.length, 0);
+      });
+    });
+
+    test('returns valid survey from json', () async {
+      await withClock(Clock.fixed(DateTime(2023, 3, 3)), () async {
+        analytics = Analytics.fake(
+          tool: DashTool.flutterTool,
+          homeDirectory: homeDirectory,
+          dartVersion: 'dartVersion',
+          fs: fs,
+          platform: DevicePlatform.macos,
+          surveyHandler: FakeSurveyHandler.fromString(
+              dismissedSurveyFile: dismissedSurveyFile, content: '''
+[
+    {
+        "uniqueId": "uniqueId123",
+        "startDate": "2023-01-01T09:00:00-07:00",
+        "endDate": "2023-12-31T09:00:00-07:00",
+        "description": "description123",
+        "snoozeForMinutes": "10",
+        "samplingRate": "1.0",
+        "excludeDashTools": [],
+        "conditions": [
+            {
+                "field": "logFileStats.recordCount",
+                "operator": ">=",
+                "value": 50
+            }
+        ],
+        "buttons": [
+            {
+                "buttonText": "Take Survey",
+                "action": "accept",
+                "url": "https://google.qualtrics.com/jfe/form/SV_5gsB2EuG324y2",
+                "promptRemainsVisible": false
+            },
+            {
+                "buttonText": "Dismiss",
+                "action": "dismiss",
+                "url": null,
+                "promptRemainsVisible": false
+            },
+            {
+                "buttonText": "More Info",
+                "action": "snooze",
+                "url": "https://docs.flutter.dev/reference/crash-reporting",
+                "promptRemainsVisible": true
+            }
+        ]
+    }
+]
+'''),
+        );
+
+        // Simulate 60 events to send so that the first condition is satisified
+        for (var i = 0; i < 60; i++) {
+          analytics.send(testEvent);
+        }
+
+        final fetchedSurveys = await analytics.fetchAvailableSurveys();
+
+        expect(fetchedSurveys.length, 1);
+
+        final survey = fetchedSurveys.first;
+        expect(survey.uniqueId, 'uniqueId123');
+        expect(survey.startDate.year, 2023);
+        expect(survey.startDate.month, 1);
+        expect(survey.startDate.day, 1);
+        expect(survey.endDate.year, 2023);
+        expect(survey.endDate.month, 12);
+        expect(survey.endDate.day, 31);
+        expect(survey.description, 'description123');
+        expect(survey.snoozeForMinutes, 10);
+        expect(survey.samplingRate, 1.0);
+        expect(survey.conditionList.length, 1);
+
+        final condition = survey.conditionList.first;
+        expect(condition.field, 'logFileStats.recordCount');
+        expect(condition.operatorString, '>=');
+        expect(condition.value, 50);
+
+        final buttonList = survey.buttonList;
+        expect(buttonList.length, 3);
+        expect(buttonList.first.buttonText, 'Take Survey');
+        expect(buttonList.first.action, 'accept');
+        expect(buttonList.first.url,
+            'https://google.qualtrics.com/jfe/form/SV_5gsB2EuG324y2');
+        expect(buttonList.first.promptRemainsVisible, false);
+
+        expect(buttonList.elementAt(1).buttonText, 'Dismiss');
+        expect(buttonList.elementAt(1).action, 'dismiss');
+        expect(buttonList.elementAt(1).url, isNull);
+        expect(buttonList.elementAt(1).promptRemainsVisible, false);
+
+        expect(buttonList.last.buttonText, 'More Info');
+        expect(buttonList.last.action, 'snooze');
+        expect(buttonList.last.url,
+            'https://docs.flutter.dev/reference/crash-reporting');
+        expect(buttonList.last.promptRemainsVisible, true);
+      });
+    });
+
+    test('no survey returned from malformed json', () async {
+      // The date is not valid for the start date
+      await withClock(Clock.fixed(DateTime(2023, 3, 3)), () async {
+        analytics = Analytics.fake(
+          tool: DashTool.flutterTool,
+          homeDirectory: homeDirectory,
+          dartVersion: 'dartVersion',
+          fs: fs,
+          platform: DevicePlatform.macos,
+          surveyHandler: FakeSurveyHandler.fromString(
+              dismissedSurveyFile: dismissedSurveyFile, content: '''
+[
+    {
+        "uniqueId": "uniqueId123",
+        "startDate": "NOT A REAL DATE",
+        "endDate": "2023-07-30T09:00:00-07:00",
+        "description": "Help improve Flutter's release builds with this 3-question survey!",
+        "snoozeForMinutes": "7200",
+        "samplingRate": "0.1",
+        "excludeDashTools": [],
+        "conditions": [
+            {
+                "field": "logFileStats.recordCount",
+                "operator": ">=",
+                "value": 50
+            }
+        ],
+        "buttons": [
+            {
+                "buttonText": "Take Survey",
+                "action": "accept",
+                "url": "https://google.qualtrics.com/jfe/form/SV_5gsB2EuG5Et5Yy2",
+                "promptRemainsVisible": false
+            },
+            {
+                "buttonText": "Dismiss",
+                "action": "dismiss",
+                "url": null,
+                "promptRemainsVisible": false
+            },
+            {
+                "buttonText": "More Info",
+                "action": "snooze",
+                "url": "https://docs.flutter.dev/reference/crash-reporting",
+                "promptRemainsVisible": false
+            }
+        ]
+    }
+]
+'''),
+        );
+
+        // Simulate 60 events to send so that the first condition is satisified
+        for (var i = 0; i < 60; i++) {
+          analytics.send(testEvent);
+        }
+
+        final fetchedSurveys = await analytics.fetchAvailableSurveys();
+
+        expect(fetchedSurveys.length, 0);
+      });
+    });
+
+    test('returns two valid survey from json', () async {
+      await withClock(Clock.fixed(DateTime(2023, 3, 3)), () async {
+        analytics = Analytics.fake(
+          tool: DashTool.flutterTool,
+          homeDirectory: homeDirectory,
+          dartVersion: 'dartVersion',
+          fs: fs,
+          platform: DevicePlatform.macos,
+          surveyHandler: FakeSurveyHandler.fromString(
+              dismissedSurveyFile: dismissedSurveyFile, content: '''
+[
+    {
+        "uniqueId": "12345",
+        "startDate": "2023-01-01T09:00:00-07:00",
+        "endDate": "2023-12-31T09:00:00-07:00",
+        "description": "xxxxxxx",
+        "snoozeForMinutes": "10",
+        "samplingRate": "1.0",
+        "excludeDashTools": [],
+        "conditions": [
+            {
+                "field": "logFileStats.recordCount",
+                "operator": ">=",
+                "value": 50
+            }
+        ], 
+        "buttons": []
+    },
+    {
+        "uniqueId": "67890",
+        "startDate": "2023-01-01T09:00:00-07:00",
+        "endDate": "2023-12-31T09:00:00-07:00",
+        "description": "xxxxxxx",
+        "snoozeForMinutes": "10",
+        "samplingRate": "1.0",
+        "excludeDashTools": [],
+        "conditions": [
+            {
+                "field": "logFileStats.recordCount",
+                "operator": ">=",
+                "value": 50
+            }
+        ],
+        "buttons": [
+            {
+                "buttonText": "More Info",
+                "action": "snooze",
+                "url": "https://docs.flutter.dev/reference/crash-reporting",
+                "promptRemainsVisible": true
+            }
+        ]
+    }
+]
+'''),
+        );
+
+        // Simulate 60 events to send so that the first condition is satisified
+        for (var i = 0; i < 60; i++) {
+          analytics.send(testEvent);
+        }
+
+        final fetchedSurveys = await analytics.fetchAvailableSurveys();
+
+        expect(fetchedSurveys.length, 2);
+
+        final firstSurvey = fetchedSurveys.first;
+        final secondSurvey = fetchedSurveys.last;
+
+        expect(firstSurvey.uniqueId, '12345');
+        expect(secondSurvey.uniqueId, '67890');
+
+        final secondSurveyButtons = secondSurvey.buttonList;
+        expect(secondSurveyButtons.length, 1);
+        expect(secondSurveyButtons.first.buttonText, 'More Info');
+        expect(secondSurveyButtons.first.action, 'snooze');
+        expect(secondSurveyButtons.first.url,
+            'https://docs.flutter.dev/reference/crash-reporting');
+        expect(secondSurveyButtons.first.promptRemainsVisible, true);
+      });
+    });
+
+    test('valid survey not returned if opted out', () async {
+      await withClock(Clock.fixed(DateTime(2023, 3, 3)), () async {
+        analytics = Analytics.fake(
+          tool: DashTool.flutterTool,
+          homeDirectory: homeDirectory,
+          dartVersion: 'dartVersion',
+          fs: fs,
+          platform: DevicePlatform.macos,
+          surveyHandler: FakeSurveyHandler.fromList(
+            dismissedSurveyFile: dismissedSurveyFile,
+            initializedSurveys: <Survey>[
+              Survey(
+                uniqueId: 'uniqueId',
+                startDate: DateTime(2023, 1, 1),
+                endDate: DateTime(2023, 12, 31),
+                description: 'description',
+                snoozeForMinutes: 10,
+                samplingRate: 1.0,
+                excludeDashToolList: [],
+                conditionList: <Condition>[
+                  Condition('logFileStats.recordCount', '>=', 50),
+                  Condition('logFileStats.toolCount.flutter-tool', '>', 0),
+                ],
+                buttonList: [],
+              ),
+            ],
+          ),
+        );
+
+        // Simulate 60 events to send so that the first condition is satisified
+        for (var i = 0; i < 60; i++) {
+          analytics.send(testEvent);
+        }
+
+        // Setting to false will prevent anything from getting returned
+        await analytics.setTelemetry(false);
+        var fetchedSurveys = await analytics.fetchAvailableSurveys();
+        expect(fetchedSurveys.length, 0);
+
+        // Setting telemetry back to true should enable the surveys to get
+        // returned again; we will also need to send the fake events again
+        // because on opt out, the log file will get cleared and one of
+        // the conditions for the fake survey loaded is that we need
+        // at least 50 records for one of the conditions
+        await analytics.setTelemetry(true);
+        for (var i = 0; i < 60; i++) {
+          analytics.send(testEvent);
+        }
+        fetchedSurveys = await analytics.fetchAvailableSurveys();
+        expect(fetchedSurveys.length, 1);
+      });
+    });
+
+    test('Sampling rate correctly returns a valid survey', () async {
+      // This test will use a predefined client ID string of `string1`
+      // which has been set in the setup along with a predefined
+      // string for the survey ID of `string2` to get a sample rate value
+      //
+      // The combination of `string1` and `string2` will return 0.40
+      // from the sampleRate utility function so we have set the threshold
+      // to be 0.6 which should return surveys
+      await withClock(Clock.fixed(DateTime(2023, 3, 3)), () async {
+        final survey = Survey(
+          uniqueId: 'string2',
+          startDate: DateTime(2023, 1, 1),
+          endDate: DateTime(2023, 12, 31),
+          description: 'description',
+          snoozeForMinutes: 10,
+          samplingRate: 0.6,
+          excludeDashToolList: [],
+          conditionList: <Condition>[
+            Condition('logFileStats.recordCount', '>=', 50),
+            Condition('logFileStats.toolCount.flutter-tool', '>', 0),
+          ],
+          buttonList: [],
+        );
+        analytics = Analytics.fake(
+          tool: DashTool.flutterTool,
+          homeDirectory: homeDirectory,
+          dartVersion: 'dartVersion',
+          fs: fs,
+          platform: DevicePlatform.macos,
+          surveyHandler: FakeSurveyHandler.fromList(
+            dismissedSurveyFile: dismissedSurveyFile,
+            initializedSurveys: <Survey>[survey],
+          ),
+        );
+
+        // Simulate 60 events to send so that the first condition is satisified
+        for (var i = 0; i < 60; i++) {
+          analytics.send(testEvent);
+        }
+
+        final fetchedSurveys = await analytics.fetchAvailableSurveys();
+
+        expect(survey.samplingRate, 0.6);
+        expect(fetchedSurveys.length, 1);
+      });
+    });
+
+    test('Sampling rate filters out a survey', () async {
+      // We will reduce the survey's sampling rate to be 0.3 which is
+      // less than value returned from the predefined client ID and
+      // survey sample
+      await withClock(Clock.fixed(DateTime(2023, 3, 3)), () async {
+        final survey = Survey(
+          uniqueId: 'string2',
+          startDate: DateTime(2023, 1, 1),
+          endDate: DateTime(2023, 12, 31),
+          description: 'description',
+          snoozeForMinutes: 10,
+          samplingRate: 0.15,
+          excludeDashToolList: [],
+          conditionList: <Condition>[
+            Condition('logFileStats.recordCount', '>=', 50),
+            Condition('logFileStats.toolCount.flutter-tool', '>', 0),
+          ],
+          buttonList: [],
+        );
+        analytics = Analytics.fake(
+          tool: DashTool.flutterTool,
+          homeDirectory: homeDirectory,
+          dartVersion: 'dartVersion',
+          fs: fs,
+          platform: DevicePlatform.macos,
+          surveyHandler: FakeSurveyHandler.fromList(
+            dismissedSurveyFile: dismissedSurveyFile,
+            initializedSurveys: <Survey>[survey],
+          ),
+        );
+
+        // Simulate 60 events to send so that the first condition is satisified
+        for (var i = 0; i < 60; i++) {
+          analytics.send(testEvent);
+        }
+
+        final fetchedSurveys = await analytics.fetchAvailableSurveys();
+
+        expect(survey.samplingRate, 0.15);
+        expect(fetchedSurveys.length, 0);
+      });
+    });
+
+    test('Snoozing survey is successful with snooze timeout from survey',
+        () async {
+      expect(dismissedSurveyFile.readAsStringSync(), '{}',
+          reason: 'Should be an empty object');
+
+      // Initialize the survey class that we will use for this test
+      final minutesToSnooze = 30;
+      final surveyToLoad = Survey(
+        uniqueId: 'uniqueId',
+        startDate: DateTime(2023, 1, 1),
+        endDate: DateTime(2023, 12, 31),
+        description: 'description',
+        snoozeForMinutes:
+            minutesToSnooze, // Initialized survey with `minutesToSnooze`
+        samplingRate: 1.0,
+        excludeDashToolList: [],
+        conditionList: <Condition>[],
+        buttonList: [],
+      );
+
+      await withClock(Clock.fixed(DateTime(2023, 3, 3, 12, 0)), () async {
+        analytics = Analytics.fake(
+          tool: DashTool.flutterTool,
+          homeDirectory: homeDirectory,
+          dartVersion: 'dartVersion',
+          fs: fs,
+          platform: DevicePlatform.macos,
+          surveyHandler: FakeSurveyHandler.fromList(
+            dismissedSurveyFile: dismissedSurveyFile,
+            initializedSurveys: <Survey>[surveyToLoad],
+          ),
+        );
+
+        final fetchedSurveys = await analytics.fetchAvailableSurveys();
+        expect(fetchedSurveys.length, 1);
+
+        final survey = fetchedSurveys.first;
+        expect(survey.snoozeForMinutes, minutesToSnooze);
+
+        // We will snooze the survey now and it should not show up
+        // if we fetch surveys again before the minutes to snooze time
+        // has finished
+        analytics.surveyShown(survey);
+      });
+
+      // This analytics instance will be simulated to be shortly after the first
+      // snooze, but before the snooze period has elapsed
+      await withClock(Clock.fixed(DateTime(2023, 3, 3, 12, 15)), () async {
+        analytics = Analytics.fake(
+          tool: DashTool.flutterTool,
+          homeDirectory: homeDirectory,
+          dartVersion: 'dartVersion',
+          fs: fs,
+          platform: DevicePlatform.macos,
+          surveyHandler: FakeSurveyHandler.fromList(
+            dismissedSurveyFile: dismissedSurveyFile,
+            initializedSurveys: <Survey>[surveyToLoad],
+          ),
+        );
+
+        final fetchedSurveys = await analytics.fetchAvailableSurveys();
+        expect(fetchedSurveys.length, 0,
+            reason: 'The snooze period has not elapsed yet');
+      });
+
+      // This analytics instance will be simulated to be after the snooze period
+      await withClock(Clock.fixed(DateTime(2023, 3, 3, 12, 35)), () async {
+        analytics = Analytics.fake(
+          tool: DashTool.flutterTool,
+          homeDirectory: homeDirectory,
+          dartVersion: 'dartVersion',
+          fs: fs,
+          platform: DevicePlatform.macos,
+          surveyHandler: FakeSurveyHandler.fromList(
+            dismissedSurveyFile: dismissedSurveyFile,
+            initializedSurveys: <Survey>[surveyToLoad],
+          ),
+        );
+
+        final fetchedSurveys = await analytics.fetchAvailableSurveys();
+        expect(fetchedSurveys.length, 1,
+            reason: 'The snooze period has elapsed');
+      });
+    });
+
+    test('Dimissing permanently is successful', () async {
+      final minutesToSnooze = 10;
+      final surveyToLoad = Survey(
+        uniqueId: 'uniqueId',
+        startDate: DateTime(2023, 1, 1),
+        endDate: DateTime(2023, 12, 31),
+        description: 'description',
+        snoozeForMinutes: minutesToSnooze,
+        samplingRate: 1.0,
+        excludeDashToolList: [],
+        conditionList: <Condition>[],
+        buttonList: [
+          SurveyButton(
+            buttonText: 'buttonText',
+            action: 'accept',
+            promptRemainsVisible: false,
+          ),
+          SurveyButton(
+            buttonText: 'buttonText',
+            action: 'dismiss',
+            promptRemainsVisible: false,
+          ),
+        ],
+      );
+
+      await withClock(Clock.fixed(DateTime(2023, 3, 3, 12, 0)), () async {
+        analytics = Analytics.fake(
+          tool: DashTool.flutterTool,
+          homeDirectory: homeDirectory,
+          dartVersion: 'dartVersion',
+          fs: fs,
+          platform: DevicePlatform.macos,
+          surveyHandler: FakeSurveyHandler.fromList(
+            dismissedSurveyFile: dismissedSurveyFile,
+            initializedSurveys: <Survey>[surveyToLoad],
+          ),
+        );
+
+        final fetchedSurveys = await analytics.fetchAvailableSurveys();
+        expect(fetchedSurveys.length, 1);
+
+        // Dismissing permanently will ensure that this survey is not
+        // shown again
+        final survey = fetchedSurveys.first;
+        analytics.surveyInteracted(
+          survey: survey,
+          surveyButton: survey.buttonList.first,
+        );
+      });
+
+      // Moving out a week
+      await withClock(Clock.fixed(DateTime(2023, 3, 10, 12, 0)), () async {
+        analytics = Analytics.fake(
+          tool: DashTool.flutterTool,
+          homeDirectory: homeDirectory,
+          dartVersion: 'dartVersion',
+          fs: fs,
+          platform: DevicePlatform.macos,
+          surveyHandler: FakeSurveyHandler.fromList(
+            dismissedSurveyFile: dismissedSurveyFile,
+            initializedSurveys: <Survey>[surveyToLoad],
+          ),
+        );
+
+        final fetchedSurveys = await analytics.fetchAvailableSurveys();
+        expect(fetchedSurveys.length, 0);
+      });
+    });
+
+    test('malformed persisted json file for surveys', () async {
+      // When the survey handler encounters an error when parsing the
+      // persisted json file, it will reset it using the static method
+      // under the [Initializer] class and reset it to be an empty json object
+      final minutesToSnooze = 10;
+      final surveyToLoad = Survey(
+        uniqueId: 'uniqueId',
+        startDate: DateTime(2023, 1, 1),
+        endDate: DateTime(2023, 12, 31),
+        description: 'description',
+        snoozeForMinutes: minutesToSnooze,
+        samplingRate: 1.0,
+        excludeDashToolList: [],
+        conditionList: <Condition>[],
+        buttonList: [
+          SurveyButton(
+            buttonText: 'buttonText',
+            action: 'accept',
+            promptRemainsVisible: false,
+          ),
+          SurveyButton(
+            buttonText: 'buttonText',
+            action: 'dismiss',
+            promptRemainsVisible: false,
+          ),
+        ],
+      );
+
+      await withClock(Clock.fixed(DateTime(2023, 3, 3, 12, 0)), () async {
+        analytics = Analytics.fake(
+          tool: DashTool.flutterTool,
+          homeDirectory: homeDirectory,
+          dartVersion: 'dartVersion',
+          fs: fs,
+          platform: DevicePlatform.macos,
+          surveyHandler: FakeSurveyHandler.fromList(
+            dismissedSurveyFile: dismissedSurveyFile,
+            initializedSurveys: <Survey>[surveyToLoad],
+          ),
+        );
+
+        final fetchedSurveys = await analytics.fetchAvailableSurveys();
+        expect(fetchedSurveys.length, 1);
+
+        // Dismissing permanently will ensure that this survey is not
+        // shown again
+        final survey = fetchedSurveys.first;
+        expect(survey.buttonList.length, 2);
+        analytics.surveyInteracted(
+          survey: survey,
+          surveyButton: survey.buttonList.first,
+        );
+      });
+
+      // Purposefully write invalid json into the persisted file
+      dismissedSurveyFile.writeAsStringSync('{');
+
+      // Moving out a week
+      await withClock(Clock.fixed(DateTime(2023, 3, 10, 12, 0)), () async {
+        analytics = Analytics.fake(
+          tool: DashTool.flutterTool,
+          homeDirectory: homeDirectory,
+          dartVersion: 'dartVersion',
+          fs: fs,
+          platform: DevicePlatform.macos,
+          surveyHandler: FakeSurveyHandler.fromList(
+            dismissedSurveyFile: dismissedSurveyFile,
+            initializedSurveys: <Survey>[surveyToLoad],
+          ),
+        );
+
+        final fetchedSurveys = await analytics.fetchAvailableSurveys();
+        expect(fetchedSurveys.length, 1);
+      });
+    });
+
+    test('persisted json file goes missing handled', () async {
+      // If the persisted json file with the dismissed surveys is missing
+      // there should be error handling to recreate the file again with
+      // an empty json object
+      final minutesToSnooze = 10;
+      final surveyToLoad = Survey(
+        uniqueId: 'uniqueId',
+        startDate: DateTime(2023, 1, 1),
+        endDate: DateTime(2023, 12, 31),
+        description: 'description',
+        snoozeForMinutes: minutesToSnooze,
+        samplingRate: 1.0,
+        excludeDashToolList: [],
+        conditionList: <Condition>[],
+        buttonList: [
+          SurveyButton(
+            buttonText: 'buttonText',
+            action: 'accept',
+            promptRemainsVisible: false,
+          ),
+          SurveyButton(
+            buttonText: 'buttonText',
+            action: 'dismiss',
+            promptRemainsVisible: false,
+          ),
+        ],
+      );
+
+      await withClock(Clock.fixed(DateTime(2023, 3, 3, 12, 0)), () async {
+        analytics = Analytics.fake(
+          tool: DashTool.flutterTool,
+          homeDirectory: homeDirectory,
+          dartVersion: 'dartVersion',
+          fs: fs,
+          platform: DevicePlatform.macos,
+          surveyHandler: FakeSurveyHandler.fromList(
+            dismissedSurveyFile: dismissedSurveyFile,
+            initializedSurveys: <Survey>[surveyToLoad],
+          ),
+        );
+
+        final fetchedSurveys = await analytics.fetchAvailableSurveys();
+        expect(fetchedSurveys.length, 1);
+
+        // Dismissing permanently will ensure that this survey is not
+        // shown again
+        final survey = fetchedSurveys.first;
+        expect(survey.buttonList.length, 2);
+        analytics.surveyInteracted(
+          survey: survey,
+          surveyButton: survey.buttonList.first,
+        );
+      });
+
+      // Moving out a week
+      await withClock(Clock.fixed(DateTime(2023, 3, 10, 12, 0)), () async {
+        analytics = Analytics.fake(
+          tool: DashTool.flutterTool,
+          homeDirectory: homeDirectory,
+          dartVersion: 'dartVersion',
+          fs: fs,
+          platform: DevicePlatform.macos,
+          surveyHandler: FakeSurveyHandler.fromList(
+            dismissedSurveyFile: dismissedSurveyFile,
+            initializedSurveys: <Survey>[surveyToLoad],
+          ),
+        );
+
+        // Purposefully delete the file
+        dismissedSurveyFile.deleteSync();
+
+        final fetchedSurveys = await analytics.fetchAvailableSurveys();
+        expect(fetchedSurveys.length, 1);
+      });
+    });
+
+    test('Filtering out with excludeDashTool array', () async {
+      await withClock(Clock.fixed(DateTime(2023, 3, 3)), () async {
+        analytics = Analytics.fake(
+          tool: DashTool.flutterTool,
+          homeDirectory: homeDirectory,
+          dartVersion: 'dartVersion',
+          fs: fs,
+          platform: DevicePlatform.macos,
+          surveyHandler: FakeSurveyHandler.fromList(
+            dismissedSurveyFile: dismissedSurveyFile,
+            initializedSurveys: <Survey>[
+              Survey(
+                uniqueId: 'uniqueId',
+                startDate: DateTime(2023, 1, 1),
+                endDate: DateTime(2023, 12, 31),
+                description: 'description',
+                snoozeForMinutes: 10,
+                samplingRate: 1.0,
+                // This should be the same as the tool in the
+                // Analytics constructor above
+                excludeDashToolList: [
+                  DashTool.flutterTool,
+                ],
+                conditionList: [],
+                buttonList: [
+                  SurveyButton(
+                    buttonText: 'buttonText',
+                    action: 'accept',
+                    url: 'http://example.com',
+                    promptRemainsVisible: false,
+                  ),
+                ],
+              ),
+            ],
+          ),
+        );
+
+        final fetchedSurveys = await analytics.fetchAvailableSurveys();
+
+        expect(fetchedSurveys.length, 0);
+      });
+    });
+
+    test(
+        'Filter from excludeDashTool array does not '
+        'apply for different tool', () async {
+      await withClock(Clock.fixed(DateTime(2023, 3, 3)), () async {
+        analytics = Analytics.fake(
+          tool: DashTool.flutterTool,
+          homeDirectory: homeDirectory,
+          dartVersion: 'dartVersion',
+          fs: fs,
+          platform: DevicePlatform.macos,
+          surveyHandler: FakeSurveyHandler.fromList(
+            dismissedSurveyFile: dismissedSurveyFile,
+            initializedSurveys: <Survey>[
+              Survey(
+                uniqueId: 'uniqueId',
+                startDate: DateTime(2023, 1, 1),
+                endDate: DateTime(2023, 12, 31),
+                description: 'description',
+                snoozeForMinutes: 10,
+                samplingRate: 1.0,
+                // This should be different from the tool in the
+                // Analytics constructor above
+                excludeDashToolList: [
+                  DashTool.devtools,
+                ],
+                conditionList: [],
+                buttonList: [
+                  SurveyButton(
+                    buttonText: 'buttonText',
+                    action: 'accept',
+                    url: 'http://example.com',
+                    promptRemainsVisible: false,
+                  ),
+                ],
+              ),
+            ],
+          ),
+        );
+
+        final fetchedSurveys = await analytics.fetchAvailableSurveys();
+
+        expect(fetchedSurveys.length, 1);
+
+        final survey = fetchedSurveys.first;
+        expect(survey.excludeDashToolList.length, 1);
+        expect(survey.excludeDashToolList.contains(DashTool.devtools), true);
+      });
+    });
+  });
+}
diff --git a/pkgs/unified_analytics/test/unified_analytics_test.dart b/pkgs/unified_analytics/test/unified_analytics_test.dart
new file mode 100644
index 0000000..2e78df4
--- /dev/null
+++ b/pkgs/unified_analytics/test/unified_analytics_test.dart
@@ -0,0 +1,1275 @@
+// Copyright (c) 2023, 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.
+
+// ignore_for_file: lines_longer_than_80_chars, avoid_dynamic_calls
+
+import 'dart:convert';
+import 'dart:io' as io;
+import 'dart:math';
+
+import 'package:clock/clock.dart';
+import 'package:file/file.dart';
+import 'package:file/memory.dart';
+import 'package:test/test.dart';
+import 'package:unified_analytics/src/constants.dart';
+import 'package:unified_analytics/src/enums.dart';
+import 'package:unified_analytics/src/utils.dart';
+import 'package:unified_analytics/unified_analytics.dart';
+import 'package:yaml/yaml.dart';
+
+void main() {
+  late MemoryFileSystem fs;
+  late Directory home;
+  late Directory dartToolDirectory;
+  late Analytics initializationAnalytics;
+  late FakeAnalytics analytics;
+  late File clientIdFile;
+  late File sessionFile;
+  late File configFile;
+  late File logFile;
+  late File dismissedSurveyFile;
+
+  const homeDirName = 'home';
+  const initialTool = DashTool.flutterTool;
+  const secondTool = DashTool.dartTool;
+  const toolsMessageVersion = 1;
+  const toolsMessage = 'toolsMessage';
+  const flutterChannel = 'flutterChannel';
+  const flutterVersion = 'flutterVersion';
+  const dartVersion = 'dartVersion';
+  const platform = DevicePlatform.macos;
+  const clientIde = 'VSCode';
+
+  final testEvent = Event.hotReloadTime(timeMs: 50);
+
+  setUp(() {
+    // Setup the filesystem with the home directory
+    final fsStyle =
+        io.Platform.isWindows ? FileSystemStyle.windows : FileSystemStyle.posix;
+    fs = MemoryFileSystem.test(style: fsStyle);
+    home = fs.directory(homeDirName);
+    dartToolDirectory = home.childDirectory(kDartToolDirectoryName);
+
+    // This is the first analytics instance that will be used to demonstrate
+    // that events will not be sent with the first run of analytics
+    initializationAnalytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+    expect(initializationAnalytics.shouldShowMessage, true);
+    initializationAnalytics.clientShowedMessage();
+    expect(initializationAnalytics.shouldShowMessage, false);
+
+    // The main analytics instance, other instances can be spawned within tests
+    // to test how to instances running together work
+    //
+    // This instance should have the same parameters as the one above for
+    // [initializationAnalytics]
+    analytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+      clientIde: clientIde,
+    );
+    analytics.clientShowedMessage();
+
+    // The 5 files that should have been generated
+    clientIdFile = home
+        .childDirectory(kDartToolDirectoryName)
+        .childFile(kClientIdFileName);
+    sessionFile =
+        home.childDirectory(kDartToolDirectoryName).childFile(kSessionFileName);
+    configFile =
+        home.childDirectory(kDartToolDirectoryName).childFile(kConfigFileName);
+    logFile =
+        home.childDirectory(kDartToolDirectoryName).childFile(kLogFileName);
+    dismissedSurveyFile = home
+        .childDirectory(kDartToolDirectoryName)
+        .childFile(kDismissedSurveyFileName);
+  });
+
+  test('Initializer properly sets up on first run', () {
+    expect(dartToolDirectory.existsSync(), true,
+        reason: 'The directory should have been created');
+    expect(clientIdFile.existsSync(), true,
+        reason: 'The $kClientIdFileName file was not found');
+    expect(sessionFile.existsSync(), true,
+        reason: 'The $kSessionFileName file was not found');
+    expect(configFile.existsSync(), true,
+        reason: 'The $kConfigFileName was not found');
+    expect(logFile.existsSync(), true,
+        reason: 'The $kLogFileName file was not found');
+    expect(dismissedSurveyFile.existsSync(), true,
+        reason: 'The $dismissedSurveyFile file was not found');
+    expect(dartToolDirectory.listSync().length, equals(5),
+        reason:
+            'There should only be 5 files in the $kDartToolDirectoryName directory');
+    expect(configFile.readAsLinesSync().length,
+        kConfigString.split('\n').length + 1,
+        reason: 'The number of lines should equal lines in constant value + 1 '
+            'for the initialized tool');
+  });
+
+  test('Resetting session file when data is malformed', () {
+    // Purposefully write content to the session file that
+    // can't be decoded as an integer
+    sessionFile.writeAsStringSync('contents');
+
+    // Define the initial time to start
+    final start = DateTime(1995, 3, 3, 12, 0);
+
+    // Set the clock to the start value defined above
+    withClock(Clock.fixed(start), () {
+      final timestamp = clock.now().millisecondsSinceEpoch.toString();
+      expect(sessionFile.readAsStringSync(), 'contents');
+      analytics.userProperty.preparePayload();
+      expect(sessionFile.readAsStringSync(),
+          '{"session_id": $timestamp, "last_ping": $timestamp}');
+
+      analytics.sendPendingErrorEvents();
+
+      // Attempting to fetch the session id when malformed should also
+      // send an error event while parsing
+      final lastEvent = analytics.sentEvents.last;
+      expect(lastEvent, isNotNull);
+      expect(lastEvent.eventName, DashEvent.analyticsException);
+      expect(
+          lastEvent.eventData['workflow']!, 'UserProperty._refreshSessionData');
+      expect(lastEvent.eventData['error']!, 'FormatException');
+    });
+  });
+
+  test('Handles malformed session file on startup', () {
+    // Ensure that we are able to send an error message on startup if
+    // we encounter an error while parsing the contents of the session file
+    // for session data
+    sessionFile.writeAsStringSync('not a valid session id');
+
+    analytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+      clientIde: clientIde,
+    );
+    analytics.clientShowedMessage();
+
+    // Invoking a send command should reset the session file to a good state
+    //
+    // Having it reformat the session file before any send event happens will just
+    // add additional work on startup
+    analytics.send(testEvent);
+
+    analytics.sendPendingErrorEvents();
+    final errorEvent = analytics.sentEvents
+        .where((element) => element.eventName == DashEvent.analyticsException)
+        .firstOrNull;
+    expect(errorEvent, isNotNull);
+    expect(
+        errorEvent!.eventData['workflow'], 'UserProperty._refreshSessionData');
+    expect(errorEvent.eventData['error'], 'FormatException');
+    expect(errorEvent.eventData['description'],
+        'message: Unexpected character\nsource: not a valid session id');
+  });
+
+  test('Resetting session file when file is removed', () {
+    // Purposefully write delete the file
+    sessionFile.deleteSync();
+
+    // Define the initial time to start
+    final start = DateTime(1995, 3, 3, 12, 0);
+
+    // Set the clock to the start value defined above
+    withClock(Clock.fixed(start), () {
+      final timestamp = clock.now().millisecondsSinceEpoch.toString();
+      expect(sessionFile.existsSync(), false);
+      analytics.userProperty.preparePayload();
+      expect(sessionFile.readAsStringSync(),
+          '{"session_id": $timestamp, "last_ping": $timestamp}');
+
+      analytics.sendPendingErrorEvents();
+
+      // Attempting to fetch the session id when malformed should also
+      // send an error event while parsing
+      final lastEvent = analytics.sentEvents.last;
+      expect(lastEvent, isNotNull);
+      expect(lastEvent.eventName, DashEvent.analyticsException);
+      expect(
+          lastEvent.eventData['workflow']!, 'UserProperty._refreshSessionData');
+      expect(lastEvent.eventData['error']!, 'FileSystemException');
+    });
+  });
+
+  test('New tool is successfully added to config file', () {
+    // Create a new instance of the analytics class with the new tool
+    final secondAnalytics = Analytics.fake(
+      tool: secondTool,
+      homeDirectory: home,
+      flutterChannel: 'ey-test-channel',
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: 'Flutter 3.6.0-7.0.pre.47',
+      dartVersion: 'Dart 2.19.0',
+      fs: fs,
+      platform: platform,
+    );
+    secondAnalytics.clientShowedMessage();
+
+    expect(secondAnalytics.parsedTools.length, equals(2),
+        reason: 'There should be only 2 tools that have '
+            'been parsed into the config file');
+    expect(secondAnalytics.parsedTools.containsKey(initialTool.label), true,
+        reason: 'The first tool: ${initialTool.label} should be in the map');
+    expect(secondAnalytics.parsedTools.containsKey(secondTool.label), true,
+        reason: 'The second tool: $secondAnalytics should be in the map');
+    expect(configFile.readAsStringSync().startsWith(kConfigString), true,
+        reason:
+            'The config file should have the same message from the constants file');
+  });
+
+  test('First time analytics run will not send events, second time will', () {
+    // Send an event with the first analytics class; this should result
+    // in no logs in the log file which keeps track of all the events
+    // that have been sent
+    initializationAnalytics.send(testEvent);
+    initializationAnalytics.send(testEvent);
+
+    // Use the second instance of analytics defined in setUp() to send the actual
+    // events to simulate the second time the tool ran
+    analytics.send(testEvent);
+
+    expect(logFile.readAsLinesSync().length, 1,
+        reason: 'The second analytics instance should have logged an event');
+  });
+
+  test('Toggling telemetry boolean through Analytics class api', () async {
+    final originalClientId = clientIdFile.readAsStringSync();
+
+    expect(analytics.telemetryEnabled, true,
+        reason: 'Telemetry should be enabled by default '
+            'when initialized for the first time');
+    // Use the API to disable analytics
+    expect(logFile.readAsLinesSync().length, 0);
+    await analytics.setTelemetry(false);
+    expect(analytics.telemetryEnabled, false,
+        reason: 'Analytics telemetry should be disabled');
+    expect(logFile.readAsLinesSync().length, 0,
+        reason: 'Log file should have been cleared after opting out');
+    expect(clientIdFile.readAsStringSync().length, 0,
+        reason: 'CLIENT ID file gets cleared on opt out');
+    expect(sessionFile.readAsStringSync().length, 0,
+        reason: 'Session file gets cleared on opt out');
+
+    // Toggle it back to being enabled
+    await analytics.setTelemetry(true);
+    expect(analytics.telemetryEnabled, true,
+        reason: 'Analytics telemetry should be enabled');
+    expect(logFile.readAsLinesSync().length, 1,
+        reason: 'There should only one event since it was cleared on opt out');
+    expect(clientIdFile.readAsStringSync().length, greaterThan(0),
+        reason: 'CLIENT ID file gets regenerated on opt in');
+    expect(sessionFile.readAsStringSync().length, greaterThan(0),
+        reason: 'Session file gets regenerated on opt in');
+
+    // Extract the last log item to check for the keys
+    final lastLogItem =
+        jsonDecode(logFile.readAsLinesSync().last) as Map<String, Object?>;
+    expect((lastLogItem['events'] as List).last['name'],
+        'analytics_collection_enabled',
+        reason: 'Check on event name');
+    expect((lastLogItem['events'] as List).last['params']['status'], true,
+        reason: 'Status should be false');
+    expect((lastLogItem['client_id'] as String).isNotEmpty, true);
+    expect(originalClientId != lastLogItem['client_id'], true,
+        reason: 'When opting in again, the client id should be regenerated');
+  });
+
+  test('Confirm client id is not empty string after opting in', () async {
+    await analytics.setTelemetry(false);
+    expect(logFile.readAsLinesSync().length, 0,
+        reason: 'Log file should have been cleared after opting out');
+    expect(clientIdFile.readAsStringSync().length, 0,
+        reason: 'CLIENT ID file gets cleared on opt out');
+
+    // Start up a second instance to simulate starting another
+    // command being run
+    final secondAnalytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    // Setting telemetry back on will emit a new event
+    // where the client id string should not be empty
+    await secondAnalytics.setTelemetry(true);
+    expect(analytics.telemetryEnabled, true,
+        reason: 'Analytics telemetry should be enabled');
+    expect(logFile.readAsLinesSync().length, 1,
+        reason: 'There should only one event since it was cleared on opt out');
+    expect(clientIdFile.readAsStringSync().length, greaterThan(0),
+        reason: 'CLIENT ID file gets regenerated on opt in');
+
+    // Extract the last log item to check for the keys
+    final lastLogItem =
+        jsonDecode(logFile.readAsLinesSync().last) as Map<String, Object?>;
+    expect((lastLogItem['client_id'] as String).isNotEmpty, true,
+        reason: 'The client id should have been regenerated and '
+            'emitted in the opt in event');
+  });
+
+  test(
+      'Telemetry has been disabled by one '
+      'tool and second tool correctly shows telemetry is disabled', () async {
+    expect(analytics.telemetryEnabled, true,
+        reason: 'Analytics telemetry should be enabled on initialization');
+    // Use the API to disable analytics
+    await analytics.setTelemetry(false);
+    expect(analytics.telemetryEnabled, false,
+        reason: 'Analytics telemetry should be disabled');
+
+    // Initialize a second analytics class, which simulates a second tool
+    // Create a new instance of the analytics class with the new tool
+    final secondAnalytics = Analytics.fake(
+      tool: secondTool,
+      homeDirectory: home,
+      flutterChannel: 'ey-test-channel',
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: 'Flutter 3.6.0-7.0.pre.47',
+      dartVersion: 'Dart 2.19.0',
+      fs: fs,
+      platform: platform,
+    );
+    secondAnalytics.clientShowedMessage();
+
+    expect(secondAnalytics.telemetryEnabled, false,
+        reason: 'Analytics telemetry should be disabled by the first class '
+            'and the second class should show telemetry is disabled');
+  });
+
+  test(
+      'Two concurrent instances are running '
+      'and reflect an accurate up to date telemetry status', () async {
+    // Initialize a second analytics class, which simulates a second tool
+    final secondAnalytics = Analytics.fake(
+      tool: secondTool,
+      homeDirectory: home,
+      flutterChannel: 'ey-test-channel',
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: 'Flutter 3.6.0-7.0.pre.47',
+      dartVersion: 'Dart 2.19.0',
+      fs: fs,
+      platform: platform,
+    );
+    secondAnalytics.clientShowedMessage();
+
+    expect(analytics.telemetryEnabled, true,
+        reason: 'Telemetry should be enabled on initialization for '
+            'first analytics instance');
+    expect(secondAnalytics.telemetryEnabled, true,
+        reason: 'Telemetry should be enabled on initialization for '
+            'second analytics instance');
+
+    // Use the API to disable analytics on the first instance
+    await analytics.setTelemetry(false);
+    expect(analytics.telemetryEnabled, false,
+        reason: 'Analytics telemetry should be disabled on first instance');
+
+    expect(secondAnalytics.telemetryEnabled, false,
+        reason: 'Analytics telemetry should be disabled by the first class '
+            'and the second class should show telemetry is disabled'
+            ' by checking the timestamp on the config file');
+  });
+
+  test('New line character is added if missing', () {
+    String currentConfigFileString;
+
+    expect(configFile.readAsStringSync().endsWith('\n'), true,
+        reason: 'When initialized, the tool should correctly '
+            'add a trailing new line character');
+
+    // Remove the trailing new line character before initializing a second
+    // analytics class; the new class should correctly format the config file
+    currentConfigFileString = configFile.readAsStringSync();
+    currentConfigFileString = currentConfigFileString.substring(
+        0, currentConfigFileString.length - 1);
+
+    // Write back out to the config file to be processed again
+    configFile.writeAsStringSync(currentConfigFileString);
+
+    expect(configFile.readAsStringSync().endsWith('\n'), false,
+        reason: 'The trailing new line should be missing');
+
+    // Initialize a second analytics class, which simulates a second tool
+    // which should correct the missing trailing new line character
+    final secondAnalytics = Analytics.fake(
+      tool: secondTool,
+      homeDirectory: home,
+      flutterChannel: 'ey-test-channel',
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: 'Flutter 3.6.0-7.0.pre.47',
+      dartVersion: 'Dart 2.19.0',
+      fs: fs,
+      platform: platform,
+    );
+    secondAnalytics.clientShowedMessage();
+
+    expect(secondAnalytics.telemetryEnabled, true);
+
+    expect(configFile.readAsStringSync().endsWith('\n'), true,
+        reason: 'The second analytics class will correct '
+            'the missing new line character');
+  });
+
+  test('Incrementing the version for a tool is successful', () {
+    expect(analytics.parsedTools[initialTool.label]?.versionNumber,
+        toolsMessageVersion,
+        reason: 'On initialization, the first version number should '
+            'be what is set in the setup method');
+
+    // Initialize a second analytics class for the same tool as
+    // the first analytics instance except with a newer version for
+    // the tools message and version
+    final secondAnalytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion + 1,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+    expect(secondAnalytics.shouldShowMessage, true);
+    expect(secondAnalytics.okToSend, false);
+    secondAnalytics.clientShowedMessage();
+    expect(secondAnalytics.shouldShowMessage, false);
+    expect(secondAnalytics.okToSend, false,
+        reason: 'New version for the message will be treated as a first run');
+
+    expect(secondAnalytics.parsedTools[initialTool.label]?.versionNumber,
+        toolsMessageVersion + 1,
+        reason:
+            'The second analytics instance should have incremented the version');
+  });
+
+  test(
+      'Config file resets when there is not exactly one match for the reporting flag',
+      () async {
+    // Write to the config file a string that is not formatted correctly
+    // (ie. there is more than one match for the reporting flag)
+    configFile.writeAsStringSync('''
+# INTRODUCTION
+#
+# This is the Flutter and Dart telemetry reporting
+# configuration file.
+#
+# Lines starting with a #" are documentation that
+# the tools maintain automatically.
+#
+# All other lines are configuration lines. They have
+# the form "name=value". If multiple lines contain
+# the same configuration name with different values,
+# the parser will default to a conservative value. 
+
+# DISABLING TELEMETRY REPORTING
+#
+# To disable telemetry reporting, set "reporting" to
+# the value "0" and to enable, set to "1":
+reporting=1
+reporting=1
+
+# NOTIFICATIONS
+#
+# Each tool records when it last informed the user about
+# analytics reporting and the privacy policy.
+#
+# The following tools have so far read this file:
+#
+#   dart-tools (Dart CLI developer tool)
+#   devtools (DevTools debugging and performance tools)
+#   flutter-tools (Flutter CLI developer tool)
+#
+# For each one, the file may contain a configuration line
+# where the name is the code in the list above, e.g. "dart-tool",
+# and the value is a date in the form YYYY-MM-DD, a comma, and
+# a number representing the version of the message that was
+# displayed.''');
+
+    // Disable telemetry which should result in a reset of the config file
+    await analytics.setTelemetry(false);
+
+    expect(configFile.readAsStringSync().startsWith(kConfigString), true,
+        reason: 'The tool should have reset the config file '
+            'because it was not formatted correctly');
+  });
+
+  test('Config file resets when there is not exactly one match for the tool',
+      () {
+    // Write to the config file a string that is not formatted correctly
+    // (ie. there is more than one match for the reporting flag)
+    configFile.writeAsStringSync('''
+# INTRODUCTION
+#
+# This is the Flutter and Dart telemetry reporting
+# configuration file.
+#
+# Lines starting with a #" are documentation that
+# the tools maintain automatically.
+#
+# All other lines are configuration lines. They have
+# the form "name=value". If multiple lines contain
+# the same configuration name with different values,
+# the parser will default to a conservative value. 
+
+# DISABLING TELEMETRY REPORTING
+#
+# To disable telemetry reporting, set "reporting" to
+# the value "0" and to enable, set to "1":
+reporting=1
+
+# NOTIFICATIONS
+#
+# Each tool records when it last informed the user about
+# analytics reporting and the privacy policy.
+#
+# The following tools have so far read this file:
+#
+#   dart-tools (Dart CLI developer tool)
+#   devtools (DevTools debugging and performance tools)
+#   flutter-tools (Flutter CLI developer tool)
+#
+# For each one, the file may contain a configuration line
+# where the name is the code in the list above, e.g. "dart-tool",
+# and the value is a date in the form YYYY-MM-DD, a comma, and
+# a number representing the version of the message that was
+# displayed.
+${initialTool.label}=$dateStamp,$toolsMessageVersion
+${initialTool.label}=$dateStamp,$toolsMessageVersion
+''');
+
+    // Initialize a second analytics class for the same tool as
+    // the first analytics instance except with a newer version for
+    // the tools message and version
+    //
+    // This second instance should reset the config file when it goes
+    // to increment the version in the file
+    final secondAnalytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion + 1,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+    secondAnalytics.clientShowedMessage();
+
+    expect(
+      configFile.readAsStringSync(),
+      kConfigString,
+      reason: 'The config file should have been reset completely '
+          'due to a malformed file that contained two lines for the same tool',
+    );
+
+    // Creating a third instance after the second instance
+    // has reset the config file should include the newly added
+    // tool again with its incremented version number
+    final thirdAnalytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion + 1,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+    thirdAnalytics.clientShowedMessage();
+
+    expect(
+      configFile.readAsStringSync().endsWith(
+          '# displayed.\n${initialTool.label}=$dateStamp,${toolsMessageVersion + 1}\n'),
+      true,
+      reason: 'The config file ends with the correctly formatted ending '
+          'after removing the duplicate lines for a given tool',
+    );
+    expect(
+      thirdAnalytics.parsedTools[initialTool.label]?.versionNumber,
+      toolsMessageVersion + 1,
+      reason: 'The new version should have been incremented',
+    );
+  });
+
+  test('Check that UserProperty class has all the necessary keys', () {
+    const userPropertyKeys = <String>[
+      'session_id',
+      'flutter_channel',
+      'host',
+      'flutter_version',
+      'dart_version',
+      'analytics_pkg_version',
+      'tool',
+      'local_time',
+      'host_os_version',
+      'locale',
+      'client_ide',
+      'enabled_features',
+    ];
+    expect(analytics.userPropertyMap.keys.length, userPropertyKeys.length,
+        reason: 'There should only be ${userPropertyKeys.length} keys');
+    for (final key in userPropertyKeys) {
+      expect(analytics.userPropertyMap.keys.contains(key), true,
+          reason: 'The $key variable is required');
+    }
+  });
+
+  test('The minimum session duration should be at least 30 minutes', () {
+    expect(kSessionDurationMinutes < 30, false,
+        reason: 'Session is less than 30 minutes');
+  });
+
+  test(
+      'The session id stays the same when duration'
+      ' is less than the constraint', () {
+    // For this test, we will need control clock time so we will delete
+    // the [dartToolDirectory] and all of its contents and reconstruct a
+    // new [Analytics] instance at a specific time
+    dartToolDirectory.deleteSync(recursive: true);
+    expect(dartToolDirectory.existsSync(), false,
+        reason: 'The directory should have been cleared');
+
+    // Define the initial time to start
+    final start = DateTime(1995, 3, 3, 12, 0);
+
+    // Set the clock to the start value defined above
+    withClock(Clock.fixed(start), () {
+      // This class will be constructed at a fixed time
+      final secondAnalytics = Analytics.fake(
+        tool: secondTool,
+        homeDirectory: home,
+        flutterChannel: flutterChannel,
+        toolsMessageVersion: toolsMessageVersion,
+        toolsMessage: toolsMessage,
+        flutterVersion: 'Flutter 3.6.0-7.0.pre.47',
+        dartVersion: 'Dart 2.19.0',
+        fs: fs,
+        platform: platform,
+      );
+      secondAnalytics.clientShowedMessage();
+
+      expect(secondAnalytics.userPropertyMap['session_id']?['value'],
+          start.millisecondsSinceEpoch);
+      expect(sessionFile.lastModifiedSync().millisecondsSinceEpoch,
+          start.millisecondsSinceEpoch);
+    });
+
+    // Add time to the start time that is less than the duration
+    final end = start.add(const Duration(minutes: kSessionDurationMinutes - 1));
+
+    // Use a new clock to ensure that the session id didn't change
+    withClock(Clock.fixed(end), () {
+      // A new instance will need to be created since the second
+      // instance in the previous block is scoped - this new instance
+      // should not reset the files generated by the second instance
+      final thirdAnalytics = Analytics.fake(
+        tool: secondTool,
+        homeDirectory: home,
+        flutterChannel: flutterChannel,
+        toolsMessageVersion: toolsMessageVersion,
+        toolsMessage: toolsMessage,
+        flutterVersion: 'Flutter 3.6.0-7.0.pre.47',
+        dartVersion: 'Dart 2.19.0',
+        fs: fs,
+        platform: platform,
+      );
+      thirdAnalytics.clientShowedMessage();
+
+      // Calling the send event method will result in the session file
+      // getting updated but because we use the `Analytics.fake()` constructor
+      // no events will be sent
+      thirdAnalytics.send(testEvent);
+
+      expect(thirdAnalytics.userPropertyMap['session_id']?['value'],
+          start.millisecondsSinceEpoch,
+          reason: 'The session id should not have changed since it was made '
+              'within the duration');
+      expect(sessionFile.lastModifiedSync().millisecondsSinceEpoch,
+          end.millisecondsSinceEpoch,
+          reason: 'The last modified value should have been updated');
+    });
+  });
+
+  test('The session id is refreshed once event is sent after duration', () {
+    // For this test, we will need control clock time so we will delete
+    // the [dartToolDirectory] and all of its contents and reconstruct a
+    // new [Analytics] instance at a specific time
+    dartToolDirectory.deleteSync(recursive: true);
+    expect(dartToolDirectory.existsSync(), false,
+        reason: 'The directory should have been cleared');
+
+    // Define the initial time to start
+    final start = DateTime(1995, 3, 3, 12, 0);
+
+    // Set the clock to the start value defined above
+    withClock(Clock.fixed(start), () {
+      // This class will be constructed at a fixed time
+      final secondAnalytics = Analytics.fake(
+        tool: secondTool,
+        homeDirectory: home,
+        flutterChannel: flutterChannel,
+        toolsMessageVersion: toolsMessageVersion,
+        toolsMessage: toolsMessage,
+        flutterVersion: 'Flutter 3.6.0-7.0.pre.47',
+        dartVersion: 'Dart 2.19.0',
+        fs: fs,
+        platform: platform,
+      );
+      secondAnalytics.clientShowedMessage();
+
+      expect(secondAnalytics.userPropertyMap['session_id']?['value'],
+          start.millisecondsSinceEpoch);
+      expect(sessionFile.lastModifiedSync().millisecondsSinceEpoch,
+          start.millisecondsSinceEpoch);
+
+      secondAnalytics.send(testEvent);
+      expect(sessionFile.readAsStringSync(),
+          '{"session_id": ${start.millisecondsSinceEpoch}, "last_ping": ${start.millisecondsSinceEpoch}}');
+    });
+
+    // Add time to the start time that is less than the duration
+    final end = start.add(const Duration(minutes: kSessionDurationMinutes + 1));
+
+    // Use a new clock to ensure that the session id didn't change
+    withClock(Clock.fixed(end), () {
+      // A new instance will need to be created since the second
+      // instance in the previous block is scoped - this new instance
+      // should not reset the files generated by the second instance
+      final thirdAnalytics = Analytics.fake(
+        tool: secondTool,
+        homeDirectory: home,
+        flutterChannel: flutterChannel,
+        toolsMessageVersion: toolsMessageVersion,
+        toolsMessage: toolsMessage,
+        flutterVersion: 'Flutter 3.6.0-7.0.pre.47',
+        dartVersion: 'Dart 2.19.0',
+        fs: fs,
+        platform: platform,
+      );
+      thirdAnalytics.clientShowedMessage();
+
+      // Calling the send event method will result in the session file
+      // getting updated but because we use the `Analytics.fake()` constructor
+      // no events will be sent
+      thirdAnalytics.send(testEvent);
+
+      expect(thirdAnalytics.userPropertyMap['session_id']?['value'],
+          end.millisecondsSinceEpoch,
+          reason: 'The session id should have changed since it was made '
+              'outside the duration');
+      expect(sessionFile.lastModifiedSync().millisecondsSinceEpoch,
+          end.millisecondsSinceEpoch,
+          reason: 'The last modified value should have been updated');
+      expect(sessionFile.readAsStringSync(),
+          '{"session_id": ${end.millisecondsSinceEpoch}, "last_ping": ${end.millisecondsSinceEpoch}}');
+    });
+  });
+
+  test('Validate the available enum types for DevicePlatform', () {
+    expect(DevicePlatform.values.length, 3,
+        reason: 'There should only be 3 supported device platforms');
+    expect(DevicePlatform.values.contains(DevicePlatform.windows), true);
+    expect(DevicePlatform.values.contains(DevicePlatform.macos), true);
+    expect(DevicePlatform.values.contains(DevicePlatform.linux), true);
+  });
+
+  test('Validate the request body', () {
+    // Sample map for event data
+    final eventData = <String, dynamic>{
+      'time': 5,
+      'command': 'run',
+    };
+
+    final Map<String, dynamic> body = generateRequestBody(
+      clientId: Uuid().generateV4(),
+      eventName: DashEvent.hotReloadTime,
+      eventData: eventData,
+      userProperty: analytics.userProperty,
+    );
+
+    // Checks for the top level keys
+    expect(body.containsKey('client_id'), true,
+        reason: '"client_id" is required at the top level');
+    expect(body.containsKey('events'), true,
+        reason: '"events" is required at the top level');
+    expect(body.containsKey('user_properties'), true,
+        reason: '"user_properties" is required at the top level');
+
+    // Regex for the client id
+    final clientIdPattern = RegExp(
+        r'^[0-9a-z]{8}\-[0-9a-z]{4}\-[0-9a-z]{4}\-[0-9a-z]{4}\-[0-9a-z]{12}$');
+
+    // Checks for the top level values
+    expect(body['client_id'].runtimeType, String,
+        reason: 'The client id must be a string');
+    expect(clientIdPattern.hasMatch(body['client_id'] as String), true,
+        reason: 'The client id is not properly formatted, ie '
+            '46cc0ba6-f604-4fd9-aa2f-8a20beb24cd4');
+    expect(
+        (body['events'][0] as Map<String, dynamic>).containsKey('name'), true,
+        reason: 'Each event in the events array needs a name');
+    expect(
+        (body['events'][0] as Map<String, dynamic>).containsKey('params'), true,
+        reason: 'Each event in the events array needs a params key');
+  });
+
+  test('Check that log file is correctly persisting events sent', () {
+    final int numberOfEvents = max((kLogFileLength * 0.1).floor(), 5);
+
+    for (var i = 0; i < numberOfEvents; i++) {
+      analytics.send(testEvent);
+    }
+
+    expect(logFile.readAsLinesSync().length, numberOfEvents,
+        reason: 'The number of events should be $numberOfEvents');
+
+    // Add the max number of events to confirm it does not exceed the max
+    for (var i = 0; i < kLogFileLength; i++) {
+      analytics.send(testEvent);
+    }
+
+    expect(logFile.readAsLinesSync().length, kLogFileLength,
+        reason: 'The number of events should be capped at $kLogFileLength');
+  });
+
+  test('Check the query on the log file works as expected', () {
+    // Define a new clock so that we can check the output of the
+    // log file stats method explicitly
+    final start = DateTime(1995, 3, 3, 12, 0);
+    final firstClock = Clock.fixed(start);
+
+    // Run with the simulated clock for the initial events
+    withClock(firstClock, () {
+      expect(analytics.logFileStats(), isNull,
+          reason: 'The result for the log file stats should be null when '
+              'there are no logs');
+      analytics.send(testEvent);
+
+      final firstQuery = analytics.logFileStats()!;
+      expect(firstQuery.sessionCount, 1,
+          reason:
+              'There should only be one session after the initial send event');
+      expect(firstQuery.flutterChannelCount, {'flutterChannel': 1},
+          reason: 'There should only be one flutter channel logged');
+      expect(firstQuery.toolCount, {'flutter-tool': 1},
+          reason: 'There should only be one tool logged');
+    });
+
+    // Define a new clock that is outside of the session duration
+    final secondClock =
+        start.add(const Duration(minutes: kSessionDurationMinutes + 1));
+
+    // Use the new clock to send an event that will change the session identifier
+    withClock(Clock.fixed(secondClock), () {
+      analytics.send(testEvent);
+
+      final secondQuery = analytics.logFileStats()!;
+
+      // Construct the expected response for the second query
+      expect(secondQuery.startDateTime, DateTime(1995, 3, 3, 12, 0));
+      expect(secondQuery.minsFromStartDateTime, 31);
+      expect(secondQuery.endDateTime, DateTime(1995, 3, 3, 12, 31));
+      expect(secondQuery.minsFromEndDateTime, 0);
+      expect(secondQuery.sessionCount, 2);
+      expect(secondQuery.flutterChannelCount, {'flutterChannel': 2});
+      expect(secondQuery.toolCount, {'flutter-tool': 2});
+      expect(secondQuery.recordCount, 2);
+      expect(secondQuery.eventCount, {'hot_reload_time': 2});
+    });
+  });
+
+  test('Check that the log file shows two different tools being used', () {
+    // Use a for loop two initialize the second analytics instance
+    // twice to account for no events being sent on the first instance
+    // run for a given tool
+    Analytics? secondAnalytics;
+    for (var i = 0; i < 2; i++) {
+      secondAnalytics = Analytics.fake(
+        tool: secondTool,
+        homeDirectory: home,
+        flutterChannel: flutterChannel,
+        toolsMessageVersion: toolsMessageVersion,
+        toolsMessage: toolsMessage,
+        flutterVersion: 'Flutter 3.6.0-7.0.pre.47',
+        dartVersion: 'Dart 2.19.0',
+        fs: fs,
+        platform: platform,
+      );
+      secondAnalytics.clientShowedMessage();
+    }
+
+    // Send events with both instances of the classes
+    analytics.send(testEvent);
+    secondAnalytics!.send(testEvent);
+
+    // Query the log file stats to verify that there are two tools
+    final query = analytics.logFileStats()!;
+
+    expect(query.toolCount, {'flutter-tool': 1, 'dart-tool': 1},
+        reason: 'There should have been two tools in the persisted logs');
+  });
+
+  test('Check that log data missing some keys results in null for stats', () {
+    // The following string represents a log item that is malformed (missing the `tool` key)
+    const malformedLog = '{"client_id":"d40133a0-7ea6-4347-b668-ffae94bb8774",'
+        '"events":[{"name":"hot_reload_time","params":{"time_ns":345}}],'
+        '"user_properties":{'
+        '"session_id":{"value":1675193534342},'
+        '"flutter_channel":{"value":"ey-test-channel"},'
+        '"host":{"value":"macOS"},'
+        '"flutter_version":{"value":"Flutter 3.6.0-7.0.pre.47"},'
+        '"dart_version":{"value":"Dart 2.19.0"},'
+        // '"tool":{"value":"flutter-tools"},'  NEEDS REMAIN REMOVED
+        '"local_time":{"value":"2023-01-31 14:32:14.592898 -0500"}}}';
+
+    logFile.writeAsStringSync(malformedLog);
+    final query = analytics.logFileStats();
+
+    expect(query, isNull,
+        reason:
+            'The query should be null because `tool` is missing under `user_properties`');
+  });
+
+  test('Malformed local_time string should result in null for stats', () {
+    // The following string represents a log item that is malformed (missing the `tool` key)
+    const malformedLog = '{"client_id":"d40133a0-7ea6-4347-b668-ffae94bb8774",'
+        '"events":[{"name":"hot_reload_time","params":{"time_ns":345}}],'
+        '"user_properties":{'
+        '"session_id":{"value":1675193534342},'
+        '"flutter_channel":{"value":"ey-test-channel"},'
+        '"host":{"value":"macOS"},'
+        '"flutter_version":{"value":"Flutter 3.6.0-7.0.pre.47"},'
+        '"dart_version":{"value":"Dart 2.19.0"},'
+        '"tool":{"value":"flutter-tools"},'
+        '"local_time":{"value":"2023-xx-31 14:32:14.592898 -0500"}}}'; // PURPOSEFULLY MALFORMED
+
+    logFile.writeAsStringSync(malformedLog);
+    final query = analytics.logFileStats();
+
+    expect(query, isNull,
+        reason:
+            'The query should be null because the `local_time` value is malformed');
+  });
+
+  test('Version is the same in the change log, pubspec, and constants.dart',
+      () {
+    // Parse the contents of the pubspec.yaml
+    final pubspecYamlString = io.File('pubspec.yaml').readAsStringSync();
+
+    // Parse into a yaml document to extract the version number
+    final doc = loadYaml(pubspecYamlString) as YamlMap;
+    final version = doc['version'] as String;
+
+    expect(version, kPackageVersion,
+        reason: 'The package version in the pubspec and '
+            'constants.dart need to match\n'
+            'Pubspec: $version && constants.dart: $kPackageVersion\n\n'
+            'Make sure both are the same');
+
+    // Parse the contents of the change log file
+    final changeLogFirstLineString =
+        io.File('CHANGELOG.md').readAsLinesSync().first;
+    expect(changeLogFirstLineString.substring(3), kPackageVersion,
+        reason: 'The CHANGELOG.md file needs the first line to '
+            'be the same version as the pubspec and constants.dart');
+  });
+
+  test('Null values for flutter parameters is reflected properly in log file',
+      () {
+    // Because we are using the `MemoryFileSystem.test` constructor,
+    // we don't have a real clock in the filesystem, and because we
+    // are checking the last modified timestamp for the session file
+    // to determine if we need to update the session id, manually setting
+    // that timestamp will ensure we are not updating session id when it
+    // first gets created
+    sessionFile.setLastModifiedSync(DateTime.now());
+
+    // Use a for loop two initialize the second analytics instance
+    // twice to account for no events being sent on the first instance
+    // run for a given tool
+    Analytics? secondAnalytics;
+    for (var i = 0; i < 2; i++) {
+      secondAnalytics = Analytics.fake(
+        tool: secondTool,
+        homeDirectory: home,
+        // flutterChannel: flutterChannel,  THIS NEEDS TO REMAIN REMOVED
+        toolsMessageVersion: toolsMessageVersion,
+        toolsMessage: toolsMessage,
+        flutterVersion: 'Flutter 3.6.0-7.0.pre.47',
+        dartVersion: 'Dart 2.19.0',
+        fs: fs,
+        platform: platform,
+      );
+      secondAnalytics.clientShowedMessage();
+    }
+
+    // Send an event and check that the query stats reflects what is expected
+    secondAnalytics!.send(testEvent);
+
+    // Query the log file stats to verify that there are two tools
+    final query = analytics.logFileStats()!;
+
+    expect(query.toolCount, {'dart-tool': 1},
+        reason: 'There should have only been on tool that sent events');
+    expect(query.flutterChannelCount.isEmpty, true,
+        reason:
+            'The instance does not have flutter information so it should be 0');
+
+    // Sending a query with the first analytics instance which has flutter information
+    // available should reflect in the query that there is 1 flutter channel present
+    analytics.send(testEvent);
+    final query2 = analytics.logFileStats()!;
+
+    expect(query2.toolCount, {'dart-tool': 1, 'flutter-tool': 1},
+        reason: 'Two different analytics instances have '
+            'been initialized and sent events');
+    expect(query2.sessionCount, query.sessionCount,
+        reason: 'The session should have remained the same');
+    expect(query2.flutterChannelCount, {'flutterChannel': 1},
+        reason: 'The first instance has flutter information initialized');
+  });
+
+  group('Testing against Google Analytics limitations:', () {
+    // Link to limitations documentation
+    // https://developers.google.com/analytics/devguides/collection/protocol/ga4/sending-events?client_type=gtag#limitations
+    //
+    // Only the limitations specified below have been added, the other
+    // are not able to be validated because it will vary by each tool
+    //
+    // 1. Events can have a maximum of 25 user properties
+    // 2. User property names must be 24 characters or fewer
+    // 3. (Only for `tool` name) User property values must be 36 characters or fewer
+    // 4. Event names must be 40 characters or fewer, may only contain alpha-numeric
+    //    characters and underscores, and must start with an alphabetic character
+    test('max 25 user properties per event', () {
+      final Map<String, Object> userPropPayload =
+          analytics.userProperty.preparePayload();
+      const maxUserPropKeys = 25;
+
+      expect(userPropPayload.keys.length < maxUserPropKeys, true,
+          reason: 'There are too many keys in the UserProperty payload');
+    });
+
+    test('max 24 characters for user prop keys', () {
+      final Map<String, Object> userPropPayload =
+          analytics.userProperty.preparePayload();
+      const maxUserPropLength = 24;
+
+      var userPropLengthValid = true;
+      final invalidUserProps = <String>[];
+      for (final key in userPropPayload.keys) {
+        if (key.length > maxUserPropLength) {
+          userPropLengthValid = false;
+          invalidUserProps.add(key);
+        }
+      }
+      expect(userPropLengthValid, true,
+          reason:
+              'The max length for each user prop is $maxUserPropLength chars\n'
+              'The below keys are too long:\n$invalidUserProps');
+    });
+
+    test('max 36 characters for user prop values (only `tool` key)', () {
+      // Checks item 3
+      // All tools must be under 36 characters (and enforce each tool
+      // begins with a letter)
+      final toolLabelPattern = RegExp(r'^[a-zA-Z][a-zA-Z\_-]{0,35}$');
+      var toolLengthValid = true;
+      final invalidTools = <DashTool>[];
+      for (final tool in DashTool.values) {
+        if (!toolLabelPattern.hasMatch(tool.label)) {
+          toolLengthValid = false;
+          invalidTools.add(tool);
+        }
+      }
+
+      expect(toolLengthValid, true,
+          reason:
+              'All tool labels must be under 36 characters and begin with a letter\n'
+              'The following are invalid\n$invalidTools');
+    });
+
+    test('max 40 characters for event names', () {
+      // Check that each event name is less than 40 chars and starts with
+      // an alphabetic character; the entire string has to be alphanumeric
+      // and underscores
+      final eventLabelPattern = RegExp(r'^[a-zA-Z]{1}[a-zA-Z0-9\_]{0,39}$');
+      var eventValid = true;
+      final invalidEvents = <DashEvent>[];
+      for (final event in DashEvent.values) {
+        if (!eventLabelPattern.hasMatch(event.label)) {
+          eventValid = false;
+          invalidEvents.add(event);
+        }
+      }
+
+      expect(eventValid, true,
+          reason: 'All event labels should have letters and underscores '
+              'as a delimiter if needed; invalid events below\n$invalidEvents');
+    });
+  });
+
+  test('Confirm credentials for GA', () {
+    expect(kGoogleAnalyticsApiSecret, 'Ka1jc8tZSzWc_GXMWHfPHA');
+    expect(kGoogleAnalyticsMeasurementId, 'G-04BXPVBCWJ');
+  });
+
+  test('Consent message is formatted correctly for the flutter tool', () {
+    // Retrieve the consent message for flutter tools
+    final consentMessage = analytics.getConsentMessage;
+
+    expect(consentMessage, equalsIgnoringWhitespace(r'''
+The Flutter CLI developer tool uses Google Analytics to report usage and diagnostic
+data along with package dependencies, and crash reporting to send basic crash
+reports. This data is used to help improve the Dart platform, Flutter framework,
+and related tools.
+
+Telemetry is not sent on the very first run. To disable reporting of telemetry,
+run this terminal command:
+
+    flutter --disable-analytics
+
+If you opt out of telemetry, an opt-out event will be sent, and then no further
+information will be sent. This data is collected in accordance with the Google
+Privacy Policy (https://policies.google.com/privacy).
+'''));
+  });
+
+  test('Consent message is formatted correctly for any tool other than flutter',
+      () {
+    // Create a new instance of the analytics class with the new tool
+    final secondAnalytics = Analytics.fake(
+      tool: secondTool,
+      homeDirectory: home,
+      flutterChannel: 'ey-test-channel',
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: 'Flutter 3.6.0-7.0.pre.47',
+      dartVersion: 'Dart 2.19.0',
+      fs: fs,
+      platform: platform,
+    );
+
+    // Retrieve the consent message for flutter tools
+    final consentMessage = secondAnalytics.getConsentMessage;
+
+    expect(consentMessage, equalsIgnoringWhitespace(r'''
+The Dart CLI developer tool uses Google Analytics to report usage and diagnostic
+data along with package dependencies, and crash reporting to send basic crash
+reports. This data is used to help improve the Dart platform, Flutter framework,
+and related tools.
+
+Telemetry is not sent on the very first run. To disable reporting of telemetry,
+run this terminal command:
+
+    dart --disable-analytics
+
+If you opt out of telemetry, an opt-out event will be sent, and then no further
+information will be sent. This data is collected in accordance with the Google
+Privacy Policy (https://policies.google.com/privacy).
+'''));
+  });
+
+  test('Equality operator works for identical events', () {
+    final eventOne = Event.clientRequest(
+      duration: 'duration',
+      latency: 'latency',
+      method: 'method',
+    );
+    final eventTwo = Event.clientRequest(
+      duration: 'duration',
+      latency: 'latency',
+      method: 'method',
+    );
+
+    expect(eventOne == eventTwo, true);
+  });
+
+  test('Equality operator works for non-identical events', () {
+    final eventOne = Event.clientRequest(
+      duration: 'duration',
+      latency: 'latency',
+      method: 'method',
+      added: 'DIFFERENT FROM EVENT TWO',
+    );
+    final eventTwo = Event.clientRequest(
+      duration: 'duration',
+      latency: 'latency',
+      method: 'method',
+    );
+
+    expect(eventOne == eventTwo, false);
+  });
+
+  test('Find a match for an event in a list of events', () {
+    final eventList = [
+      Event.analyticsCollectionEnabled(status: true),
+      Event.memoryInfo(rss: 500),
+      Event.clientRequest(
+          duration: 'duration', latency: 'latency', method: 'method'),
+    ];
+
+    final eventToMatch = Event.memoryInfo(rss: 500);
+
+    expect(eventList.contains(eventToMatch), true);
+    expect(eventList.where((element) => element == eventToMatch).length, 1);
+  });
+
+  group('Unit tests for util dartSDKVersion', () {
+    test('parses correctly for non-stable version', () {
+      final originalVersion =
+          '3.4.0-148.0.dev (dev) (Thu Feb 15 12:05:45 2024 -0800) on "macos_arm64"';
+
+      expect(parseDartSDKVersion(originalVersion),
+          '3.4.0 (build 3.4.0-148.0.dev)');
+    });
+
+    test('parses correctly for stable version', () {
+      final originalVersion =
+          '3.3.0 (stable) (Tue Feb 13 10:25:19 2024 +0000) on "macos_arm64"';
+
+      expect(parseDartSDKVersion(originalVersion), '3.3.0');
+    });
+  });
+}
diff --git a/pkgs/unified_analytics/test/workflow_test.dart b/pkgs/unified_analytics/test/workflow_test.dart
new file mode 100644
index 0000000..3a623a0
--- /dev/null
+++ b/pkgs/unified_analytics/test/workflow_test.dart
@@ -0,0 +1,382 @@
+// Copyright (c) 2023, 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.
+
+import 'dart:io' as io;
+
+import 'package:file/file.dart';
+import 'package:file/memory.dart';
+import 'package:test/test.dart';
+import 'package:unified_analytics/src/constants.dart';
+import 'package:unified_analytics/src/enums.dart';
+import 'package:unified_analytics/src/utils.dart';
+import 'package:unified_analytics/unified_analytics.dart';
+
+void main() {
+  late MemoryFileSystem fs;
+  late Directory home;
+  late Directory dartToolDirectory;
+  late File clientIdFile;
+  late File sessionFile;
+  late File configFile;
+  late File logFile;
+  late File dismissedSurveyFile;
+
+  const homeDirName = 'home';
+  const initialTool = DashTool.flutterTool;
+  const secondTool = DashTool.dartTool;
+  const toolsMessageVersion = 1;
+  const toolsMessage = 'toolsMessage';
+  const flutterChannel = 'flutterChannel';
+  const flutterVersion = 'flutterVersion';
+  const dartVersion = 'dartVersion';
+  const platform = DevicePlatform.macos;
+
+  final testEvent = Event.hotReloadTime(timeMs: 50);
+
+  setUp(() {
+    // Setup the filesystem with the home directory
+    final fsStyle =
+        io.Platform.isWindows ? FileSystemStyle.windows : FileSystemStyle.posix;
+    fs = MemoryFileSystem.test(style: fsStyle);
+    home = fs.directory(homeDirName);
+    dartToolDirectory = home.childDirectory(kDartToolDirectoryName);
+
+    // The 3 files that should have been generated
+    clientIdFile = home
+        .childDirectory(kDartToolDirectoryName)
+        .childFile(kClientIdFileName);
+    sessionFile =
+        home.childDirectory(kDartToolDirectoryName).childFile(kSessionFileName);
+    configFile =
+        home.childDirectory(kDartToolDirectoryName).childFile(kConfigFileName);
+    logFile =
+        home.childDirectory(kDartToolDirectoryName).childFile(kLogFileName);
+    dismissedSurveyFile = home
+        .childDirectory(kDartToolDirectoryName)
+        .childFile(kDismissedSurveyFileName);
+  });
+
+  test('Confirm workflow for first run', () {
+    final firstAnalytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    expect(firstAnalytics.shouldShowMessage, true);
+    expect(firstAnalytics.okToSend, false);
+
+    firstAnalytics.clientShowedMessage();
+    expect(firstAnalytics.shouldShowMessage, false);
+    expect(firstAnalytics.okToSend, false,
+        reason: 'On the first run, we should not be ok '
+            'to send any events, even if the user accepts');
+  });
+
+  test('Confirm workflow for updated tools message version + new tool', () {
+    // Helper function to check the state of the instance
+    void checkAnalyticsInstance(Analytics instance) {
+      expect(instance.shouldShowMessage, true);
+      expect(instance.okToSend, false);
+
+      instance.clientShowedMessage();
+      expect(instance.shouldShowMessage, false);
+      expect(instance.okToSend, false,
+          reason: 'On the first run, we should not be ok '
+              'to send any events, even if the user accepts');
+    }
+
+    final firstAnalytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    checkAnalyticsInstance(firstAnalytics);
+
+    // Instance where we increment the version of the message
+    final secondAnalytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion + 1, // Incrementing version
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    // Running the same checks for the second instance, it should
+    // behave the same as if it was a first run
+    checkAnalyticsInstance(secondAnalytics);
+
+    // Instance for a different tool with the incremented version
+    final thirdAnalytics = Analytics.fake(
+      tool: secondTool, // Different tool
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion + 1, // Incrementing version
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    // The instance with a new tool getting onboarded should be
+    // treated the same as the 2 previous instances
+    checkAnalyticsInstance(thirdAnalytics);
+  });
+
+  test('Confirm workflow for checking tools into the config file', () {
+    final firstAnalytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    // Host of assertions to ensure all required artifacts
+    // are created
+    expect(dartToolDirectory.existsSync(), true,
+        reason: 'The directory should have been created');
+    expect(clientIdFile.existsSync(), true,
+        reason: 'The $kClientIdFileName file was not found');
+    expect(sessionFile.existsSync(), true,
+        reason: 'The $kSessionFileName file was not found');
+    expect(configFile.existsSync(), true,
+        reason: 'The $kConfigFileName was not found');
+    expect(logFile.existsSync(), true,
+        reason: 'The $kLogFileName file was not found');
+    expect(dismissedSurveyFile.existsSync(), true,
+        reason: 'The $dismissedSurveyFile file was not found');
+    expect(
+      dartToolDirectory.listSync().length,
+      equals(5),
+      reason: 'There should only be 5 files in the $kDartToolDirectoryName '
+          'directory',
+    );
+    expect(configFile.readAsStringSync(), kConfigString);
+
+    expect(firstAnalytics.shouldShowMessage, true);
+
+    // Attempting to send a message with this instance should be
+    // blocked because it has not invoked `clientShowedMessage()`
+    // and it is the first run
+    //
+    // Even after invoking the method, it should be prevented from
+    // sending a message because it is the first time the tool was
+    // run in this instance
+    firstAnalytics.send(testEvent);
+    expect(logFile.readAsLinesSync().length, 0);
+    firstAnalytics.clientShowedMessage();
+
+    // Attempt to send two events, both should be blocked because it is
+    // part of the first instance
+    firstAnalytics.send(testEvent);
+    firstAnalytics.send(testEvent);
+    expect(logFile.readAsLinesSync().length, 0);
+
+    // Creating a second analytics instance from the same tool now should
+    // allow for events to be sent
+    final secondAnalytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    expect(secondAnalytics.shouldShowMessage, false);
+    secondAnalytics.send(testEvent);
+    expect(logFile.readAsLinesSync().length, 1,
+        reason: 'Events will be blocked until invoking method '
+            'ensuring client has seen message');
+
+    secondAnalytics.send(testEvent);
+    secondAnalytics.send(testEvent);
+    expect(logFile.readAsLinesSync().length, 3);
+
+    // Next, we will want to confirm that the message should be showing when
+    // a new analytics instance has been created with a newer version for
+    // message that should be shown
+    //
+    // In this case, it should be treated as a new tool being added for the
+    // first time and all events should be blocked
+
+    // Delete the log file to reset the counter of events sent
+    logFile.deleteSync();
+    final thirdAnalytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion + 1, // Incrementing version
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    expect(logFile.existsSync(), true,
+        reason: 'The $kLogFileName file was not found');
+    expect(thirdAnalytics.shouldShowMessage, true,
+        reason: 'New version number should require showing message');
+    thirdAnalytics.send(testEvent);
+    expect(logFile.readAsLinesSync().length, 0);
+    thirdAnalytics.clientShowedMessage();
+
+    // Attempt to send two events, both should be blocked because it is
+    // part of the third instance which has a new version for the consent
+    // message which will be treated as a new tool being onboarded
+    thirdAnalytics.send(testEvent);
+    thirdAnalytics.send(testEvent);
+    expect(logFile.readAsLinesSync().length, 0);
+
+    // The fourth instance of the analytics class with the consent message
+    // version incremented should now be able to send messages
+    final fourthAnalytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion + 1, // Incrementing version
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    expect(fourthAnalytics.shouldShowMessage, false);
+    fourthAnalytics.send(testEvent);
+    expect(logFile.readAsLinesSync().length, 1,
+        reason: 'Events will be blocked until invoking method '
+            'ensuring client has seen message');
+
+    fourthAnalytics.send(testEvent);
+    fourthAnalytics.send(testEvent);
+    expect(logFile.readAsLinesSync().length, 3);
+  });
+
+  test('Disable second instance if first one did not show message', () {
+    final firstAnalytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    expect(firstAnalytics.shouldShowMessage, true);
+
+    final secondAnalytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    expect(secondAnalytics.shouldShowMessage, true);
+
+    secondAnalytics.clientShowedMessage();
+
+    final thirdAnalytics = Analytics.fake(
+      tool: initialTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: toolsMessageVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: flutterVersion,
+      dartVersion: dartVersion,
+      fs: fs,
+      platform: platform,
+    );
+
+    expect(thirdAnalytics.shouldShowMessage, false);
+  });
+
+  test('Passing large version number gets logged in config', () {
+    final firstVersion = toolsMessageVersion + 3;
+    final secondAnalytics = Analytics.fake(
+      tool: secondTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: firstVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: 'Flutter 3.6.0-7.0.pre.47',
+      dartVersion: 'Dart 2.19.0',
+      fs: fs,
+      platform: platform,
+    );
+    secondAnalytics.clientShowedMessage();
+
+    expect(
+        configFile
+            .readAsStringSync()
+            .endsWith('${secondTool.label}=$dateStamp,$firstVersion\n'),
+        true);
+
+    // Create a new instane of the secondTool with an even
+    // bigger version
+    final secondVersion = firstVersion + 3;
+    final thirdAnalytics = Analytics.fake(
+      tool: secondTool,
+      homeDirectory: home,
+      flutterChannel: flutterChannel,
+      toolsMessageVersion: secondVersion,
+      toolsMessage: toolsMessage,
+      flutterVersion: 'Flutter 3.6.0-7.0.pre.47',
+      dartVersion: 'Dart 2.19.0',
+      fs: fs,
+      platform: platform,
+    );
+
+    expect(
+        configFile
+            .readAsStringSync()
+            .endsWith('${secondTool.label}=$dateStamp,$firstVersion\n'),
+        true);
+
+    // After invoking this method, it will get updated
+    // in the config with the next version
+    thirdAnalytics.clientShowedMessage();
+
+    expect(
+        configFile
+            .readAsStringSync()
+            .endsWith('${secondTool.label}=$dateStamp,$secondVersion\n'),
+        true);
+  });
+}