From 5256afd0fffe6d23c4c0b364381a62ddaf7f1aaf Mon Sep 17 00:00:00 2001 From: Parker Lougheed <parlough@gmail.com> Date: Thu, 30 Jan 2025 15:34:55 -0600 Subject: [PATCH] Clean up and fixes for dart:html usages in code excerpts --- .../create_libraries/lib/src/hw_html.dart | 7 ------ examples/create_libraries/lib/src/hw_web.dart | 7 ++++++ examples/create_libraries/pubspec.yaml | 3 +++ examples/html/README.md | 7 ++++-- examples/html/lib/html.dart | 2 +- examples/html/pubspec.yaml | 4 +-- examples/html/test/html_test.dart | 2 ++ examples/misc/bin/cheatsheet/cascades.dart | 18 ++++++------- .../lib/effective_dart/style_lib_good.dart | 2 +- examples/misc/pubspec.yaml | 1 + .../misc/test/language_tour/browser_test.dart | 24 ++++++++---------- .../lib/common_fixes_analysis.dart | 5 ++-- src/content/effective-dart/style.md | 2 +- src/content/interop/js-interop/package-web.md | 25 ++++++++++--------- src/content/language/operators.md | 16 +++++------- src/content/libraries/async/zones.md | 2 +- src/content/libraries/index.md | 2 +- src/content/resources/dart-cheatsheet.md | 16 ++++++------ src/content/tutorials/server/cmdline.md | 3 ++- src/content/tutorials/server/fetch-data.md | 6 ++--- 20 files changed, 78 insertions(+), 76 deletions(-) delete mode 100644 examples/create_libraries/lib/src/hw_html.dart create mode 100644 examples/create_libraries/lib/src/hw_web.dart diff --git a/examples/create_libraries/lib/src/hw_html.dart b/examples/create_libraries/lib/src/hw_html.dart deleted file mode 100644 index e3eca24351..0000000000 --- a/examples/create_libraries/lib/src/hw_html.dart +++ /dev/null @@ -1,7 +0,0 @@ -import 'dart:html'; - -void alarm([String? text]) { - window.alert(text ?? message); -} - -String get message => 'Hello World from JavaScript!'; diff --git a/examples/create_libraries/lib/src/hw_web.dart b/examples/create_libraries/lib/src/hw_web.dart new file mode 100644 index 0000000000..49708c6430 --- /dev/null +++ b/examples/create_libraries/lib/src/hw_web.dart @@ -0,0 +1,7 @@ +import 'package:web/web.dart' as web; + +void alarm([String? text]) { + web.window.alert(text ?? message); +} + +String get message => 'Hello world from the web!'; diff --git a/examples/create_libraries/pubspec.yaml b/examples/create_libraries/pubspec.yaml index be4f5d01ca..37451e8b11 100644 --- a/examples/create_libraries/pubspec.yaml +++ b/examples/create_libraries/pubspec.yaml @@ -6,5 +6,8 @@ resolution: workspace environment: sdk: ^3.6.0 +dependencies: + web: ^1.1.0 + dev_dependencies: test: ^1.25.8 diff --git a/examples/html/README.md b/examples/html/README.md index 9a6c8f55d7..e75f9438d5 100644 --- a/examples/html/README.md +++ b/examples/html/README.md @@ -1,2 +1,5 @@ -This package is not an app, it is a collection of code excerpts and associated -tests used in the `dart:html` library tour. +**Deprecated** collection of code excerpts used +in the now-historical `dart:html` library tour. + +All usages of `dart:html` should migrate to `dart:js_interop` and `package:web`. +To learn more, check out [Dart JS interop](https://dart.dev/interop/js-interop). diff --git a/examples/html/lib/html.dart b/examples/html/lib/html.dart index 3cd1cb1e98..a956bc9154 100644 --- a/examples/html/lib/html.dart +++ b/examples/html/lib/html.dart @@ -1,4 +1,4 @@ -// ignore_for_file: unused_element, unused_local_variable +// ignore_for_file: unused_element, unused_local_variable, deprecated_member_use // #docregion import import 'dart:html'; // #enddocregion import diff --git a/examples/html/pubspec.yaml b/examples/html/pubspec.yaml index 1f665528c8..b05879fe71 100644 --- a/examples/html/pubspec.yaml +++ b/examples/html/pubspec.yaml @@ -1,5 +1,5 @@ -name: html_library_examples -description: dart.dev example code. +name: deprecated_html_library_examples +description: Deprecated dart.dev example code. version: 0.0.1 resolution: workspace diff --git a/examples/html/test/html_test.dart b/examples/html/test/html_test.dart index bbc1ccbe00..f9f6f110f3 100644 --- a/examples/html/test/html_test.dart +++ b/examples/html/test/html_test.dart @@ -1,3 +1,5 @@ +// ignore_for_file: deprecated_member_use + @Tags(['browser']) @TestOn('browser') library; diff --git a/examples/misc/bin/cheatsheet/cascades.dart b/examples/misc/bin/cheatsheet/cascades.dart index 409c04df29..250388f6e7 100644 --- a/examples/misc/bin/cheatsheet/cascades.dart +++ b/examples/misc/bin/cheatsheet/cascades.dart @@ -1,6 +1,6 @@ // ignore_for_file: avoid_single_cascade_in_expression_statements -import 'dart:html'; +import 'package:web/web.dart' as web; void main() { final myObject = SomeObject(); @@ -14,18 +14,18 @@ void main() { // #enddocregion uses-cascade // #docregion query-without-cascades - var button = querySelector('#confirm'); - button?.text = 'Confirm'; - button?.classes.add('important'); - button?.onClick.listen((e) => window.alert('Confirmed!')); + final button = web.document.querySelector('#confirm'); + button?.textContent = 'Confirm'; + button?.classList.add('important'); + button?.onClick.listen((e) => web.window.alert('Confirmed!')); button?.scrollIntoView(); // #enddocregion query-without-cascades // #docregion query-with-cascades - querySelector('#confirm') - ?..text = 'Confirm' - ..classes.add('important') - ..onClick.listen((e) => window.alert('Confirmed!')) + web.document.querySelector('#confirm') + ?..textContent = 'Confirm' + ..classList.add('important') + ..onClick.listen((e) => web.window.alert('Confirmed!')) ..scrollIntoView(); // #enddocregion query-with-cascades } diff --git a/examples/misc/lib/effective_dart/style_lib_good.dart b/examples/misc/lib/effective_dart/style_lib_good.dart index 60d7b23004..4e159df5cc 100644 --- a/examples/misc/lib/effective_dart/style_lib_good.dart +++ b/examples/misc/lib/effective_dart/style_lib_good.dart @@ -14,7 +14,7 @@ import 'package:examples/effective_dart/bar.dart' as js; // #docregion dart-import-first import 'dart:async'; -import 'dart:html'; +import 'dart:collection'; // #docregion pkg-import-before-local, sorted import 'package:examples/effective_dart/bar/bar.dart'; diff --git a/examples/misc/pubspec.yaml b/examples/misc/pubspec.yaml index c27ffea177..29c2597eca 100644 --- a/examples/misc/pubspec.yaml +++ b/examples/misc/pubspec.yaml @@ -10,6 +10,7 @@ dependencies: characters: ^1.3.0 examples_util: { path: ../util } http: ^1.2.2 + web: ^1.1.0 dev_dependencies: test: ^1.25.8 diff --git a/examples/misc/test/language_tour/browser_test.dart b/examples/misc/test/language_tour/browser_test.dart index e2f07cb54e..9216b56377 100644 --- a/examples/misc/test/language_tour/browser_test.dart +++ b/examples/misc/test/language_tour/browser_test.dart @@ -1,5 +1,3 @@ -// ignore_for_file: unused_import - @Tags(['browser']) @TestOn('browser') library; @@ -7,39 +5,39 @@ library; // #docregion dart-js-interop-import import 'dart:js_interop'; // #enddocregion dart-js-interop-import -import 'dart:html'; // #docregion package-import import 'package:test/test.dart'; // #enddocregion package-import +import 'package:web/web.dart'; void main() { test('cascade-operator', () { final div = '<button id="confirm"></button>'; - document.body?.appendHtml(div); + document.body?.insertAdjacentHTML('beforeend', div.toJS); // #docregion cascade-operator - querySelector('#confirm') // Get an object. - ?..text = 'Confirm' // Use its members. - ..classes.add('important') + document.querySelector('#confirm') // Get an object. + ?..textContent = 'Confirm' // Use its members. + ..classList.add('important') ..onClick.listen((e) => window.alert('Confirmed!')) ..scrollIntoView(); // #enddocregion cascade-operator - expect(document.querySelector('#confirm')?.text, 'Confirm'); + expect(document.querySelector('#confirm')?.textContent, 'Confirm'); }); test('cascade-operator-example-expanded', () { final div = '<button id="confirm"></button>'; - document.body?.appendHtml(div); + document.body?.insertAdjacentHTML('beforeend', div.toJS); // #docregion cascade-operator-example-expanded - var button = querySelector('#confirm'); - button?.text = 'Confirm'; - button?.classes.add('important'); + final button = document.querySelector('#confirm'); + button?.textContent = 'Confirm'; + button?.classList.add('important'); button?.onClick.listen((e) => window.alert('Confirmed!')); button?.scrollIntoView(); // #enddocregion cascade-operator-example-expanded - expect(document.querySelector('#confirm')?.text, 'Confirm'); + expect(document.querySelector('#confirm')?.textContent, 'Confirm'); }); } diff --git a/examples/type_system/lib/common_fixes_analysis.dart b/examples/type_system/lib/common_fixes_analysis.dart index 68d168a0d3..0c7d2cb035 100644 --- a/examples/type_system/lib/common_fixes_analysis.dart +++ b/examples/type_system/lib/common_fixes_analysis.dart @@ -1,6 +1,6 @@ // NOTE: Declarations in this file are analyzed but not tested. // ignore_for_file: unused_element, unused_local_variable, one_member_abstracts, use_super_parameters -// ignore_for_file: prefer_function_declarations_over_variables, unused_field, strict_raw_type +// ignore_for_file: prefer_function_declarations_over_variables, unused_field, strict_raw_type, deprecated_member_use import 'dart:html'; @@ -157,7 +157,6 @@ abstract class C implements List<int> {} // #enddocregion compatible-generics // #docregion conflicting-generics -// ignore: inconsistent_inheritance, conflicting_generic_interfaces, -// ignore: duplicate_definition +// ignore: duplicate_definition, inconsistent_inheritance, conflicting_generic_interfaces abstract class C implements List<int>, Iterable<num> {} // #enddocregion conflicting-generics diff --git a/src/content/effective-dart/style.md b/src/content/effective-dart/style.md index ef4154d94d..4414f8acd5 100644 --- a/src/content/effective-dart/style.md +++ b/src/content/effective-dart/style.md @@ -355,7 +355,7 @@ A single linter rule handles all the ordering guidelines: <?code-excerpt "style_lib_good.dart (dart-import-first)" replace="/\w+\/effective_dart\///g"?> ```dart tag=good import 'dart:async'; -import 'dart:html'; +import 'dart:collection'; import 'package:bar/bar.dart'; import 'package:foo/foo.dart'; diff --git a/src/content/interop/js-interop/package-web.md b/src/content/interop/js-interop/package-web.md index 23c9d6238c..40ddf16935 100644 --- a/src/content/interop/js-interop/package-web.md +++ b/src/content/interop/js-interop/package-web.md @@ -205,7 +205,7 @@ A value of type '...' can't be assigned to a variable of type 'JSFunction?' ### Conditional imports -It is common for code to use a conditional import based on whether `dart:html` +It's common for code to use a conditional import based on whether `dart:html` is supported to differentiate between native and web: ```dart @@ -214,14 +214,15 @@ export 'src/hw_none.dart' if (dart.library.html) 'src/hw_html.dart'; ``` -However, since `dart:html` is not supported when compiling to Wasm, the correct -alternative now is to use `dart.library.js_interop` to differentiate between -native and web: +However, since `dart:html` is deprecated and not supported when +compiling to Wasm, the correct alternative now is to +use `dart.library.js_interop` to differentiate between native and web: +<?code-excerpt "create_libraries/lib/hw_mp.dart (export)"?> ```dart -export 'src/hw_none.dart' - if (dart.library.io) 'src/hw_io.dart' - if (dart.library.js_interop) 'src/hw_web.dart'; +export 'src/hw_none.dart' // Stub implementation + if (dart.library.io) 'src/hw_io.dart' // dart:io implementation + if (dart.library.js_interop) 'src/hw_web.dart'; // package:web implementation ``` ### Virtual dispatch and mocking @@ -263,7 +264,7 @@ automatically do this. ## Helpers The core of `package:web` contains `external` interop members, -but does not provide other functionality that `dart:html` provided by default. +but doesn't provide other functionality that `dart:html` provided by default. To mitigate these differences, `package:web` contains [`helpers`][helpers] for additional support in handling a number of use cases that aren't directly available through the core interop. @@ -275,12 +276,12 @@ event listeners. Instead, you can use [stream helpers][] that makes it easy to subscribe to events with Dart `Stream`s without writing that code yourself. ```dart -// dart:html version -InputElement htmlInput = InputElement(); +// Original dart:html version: +final htmlInput = InputElement(); await htmlInput.onBlur.first; -// package:web version -HTMLInputElement webInput = document.createElement('input') as HTMLInputElement; +// Migrated package:web version: +final webInput = HTMLInputElement(); await webInput.onBlur.first; ``` diff --git a/src/content/language/operators.md b/src/content/language/operators.md index c21dda735a..b9b6bd87cd 100644 --- a/src/content/language/operators.md +++ b/src/content/language/operators.md @@ -448,24 +448,20 @@ are attempted on that null object. <?code-excerpt "misc/test/language_tour/browser_test.dart (cascade-operator)"?> ```dart -querySelector('#confirm') // Get an object. - ?..text = 'Confirm' // Use its members. - ..classes.add('important') +document.querySelector('#confirm') // Get an object. + ?..textContent = 'Confirm' // Use its members. + ..classList.add('important') ..onClick.listen((e) => window.alert('Confirmed!')) ..scrollIntoView(); ``` -:::version-note -The `?..` syntax requires a [language version][] of at least 2.12. -::: - The previous code is equivalent to the following: <?code-excerpt "misc/test/language_tour/browser_test.dart (cascade-operator-example-expanded)"?> ```dart -var button = querySelector('#confirm'); -button?.text = 'Confirm'; -button?.classes.add('important'); +final button = document.querySelector('#confirm'); +button?.textContent = 'Confirm'; +button?.classList.add('important'); button?.onClick.listen((e) => window.alert('Confirmed!')); button?.scrollIntoView(); ``` diff --git a/src/content/libraries/async/zones.md b/src/content/libraries/async/zones.md index 75507ddccb..173e67327f 100644 --- a/src/content/libraries/async/zones.md +++ b/src/content/libraries/async/zones.md @@ -792,7 +792,7 @@ The source code for the stack_trace package You can find the stack_trace source code in the [stack_trace GitHub project]({{site.repo.dart.org}}/stack_trace). -The source code for dart:html and dart:async +The source code for dart:async : These two SDK libraries implement APIs featuring asynchronous callbacks, and thus they deal with zones. You can browse or download their source code under the diff --git a/src/content/libraries/index.md b/src/content/libraries/index.md index a268bf7aa7..39534e2a97 100644 --- a/src/content/libraries/index.md +++ b/src/content/libraries/index.md @@ -48,7 +48,7 @@ consult the [Dart API reference.][Dart API] [dart:js_interop](/interop/js-interop) : APIs for interop with the web platform. - Along with `package:web`,`dart:js_interop` replaces `dart:html`. + Along with `package:web`, `dart:js_interop` replaces `dart:html`. As mentioned, these pages are just an overview; diff --git a/src/content/resources/dart-cheatsheet.md b/src/content/resources/dart-cheatsheet.md index 498d19ee8d..5ab989b54d 100644 --- a/src/content/resources/dart-cheatsheet.md +++ b/src/content/resources/dart-cheatsheet.md @@ -619,10 +619,10 @@ to read properties of `button` if it isn't `null`: <?code-excerpt "misc/bin/cheatsheet/cascades.dart (query-without-cascades)"?> ```dart -var button = querySelector('#confirm'); -button?.text = 'Confirm'; -button?.classes.add('important'); -button?.onClick.listen((e) => window.alert('Confirmed!')); +final button = web.document.querySelector('#confirm'); +button?.textContent = 'Confirm'; +button?.classList.add('important'); +button?.onClick.listen((e) => web.window.alert('Confirmed!')); button?.scrollIntoView(); ``` @@ -635,10 +635,10 @@ and makes the `button` variable unnecessary: <?code-excerpt "misc/bin/cheatsheet/cascades.dart (query-with-cascades)"?> ```dart -querySelector('#confirm') - ?..text = 'Confirm' - ..classes.add('important') - ..onClick.listen((e) => window.alert('Confirmed!')) +web.document.querySelector('#confirm') + ?..textContent = 'Confirm' + ..classList.add('important') + ..onClick.listen((e) => web.window.alert('Confirmed!')) ..scrollIntoView(); ``` diff --git a/src/content/tutorials/server/cmdline.md b/src/content/tutorials/server/cmdline.md index 6ce6cca8cd..74c4ac8c5a 100644 --- a/src/content/tutorials/server/cmdline.md +++ b/src/content/tutorials/server/cmdline.md @@ -285,7 +285,8 @@ import 'dart:io'; ``` :::note -Web apps (apps that depend on `dart:html`) can't use the `dart:io` library. +Apps that run on the [web platform](/overview#platform) +can't use the `dart:io` library. ::: ### stdout diff --git a/src/content/tutorials/server/fetch-data.md b/src/content/tutorials/server/fetch-data.md index c1300316bb..a2f5ac2ac0 100644 --- a/src/content/tutorials/server/fetch-data.md +++ b/src/content/tutorials/server/fetch-data.md @@ -148,10 +148,8 @@ for making composable HTTP requests, with optional fine-grained control. :::note -You should avoid directly using `dart:io` or `dart:html` -to make HTTP requests. -Those libraries are platform-dependent -and tied to a single implementation. +Avoid directly using `dart:io` or `dart:html` to make HTTP requests. +Those libraries are platform-dependent and tied to a single implementation. ::: To add a dependency on `package:http`,