From a6a442fbc80c18bd90b79ba8f814cfdbebdfa62c Mon Sep 17 00:00:00 2001 From: __ <8144986+fschr@users.noreply.github.com> Date: Tue, 20 Dec 2022 07:38:25 -0600 Subject: [PATCH 01/76] website/docs/tutorial: fix two typos (#2971) --- website/docs/tutorial/index.mdx | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/website/docs/tutorial/index.mdx b/website/docs/tutorial/index.mdx index dedd3b450bb..7d00a466c9a 100644 --- a/website/docs/tutorial/index.mdx +++ b/website/docs/tutorial/index.mdx @@ -372,7 +372,7 @@ struct VideosListProps { } ``` -Then we modify the `VideosList` component to pass the "emit" the selected video to the callback. +Then we modify the `VideosList` component to "emit" the selected video to the callback. ```rust ,ignore {2-4,6-12,15-16} #[function_component(VideosList)] @@ -397,7 +397,7 @@ Then we modify the `VideosList` component to pass the "emit" the selected video ``` Next, we need to modify the usage of `VideosList` to pass that callback. But before doing that, we should create -a new component, `VideoDetails`, component that is displayed when a video is clicked. +a new component, `VideoDetails`, that is displayed when a video is clicked. ```rust use website_test::tutorial::Video; From 16df0150a99501a251971d57d0c83f542f577e5e Mon Sep 17 00:00:00 2001 From: Michael Jones Date: Tue, 20 Dec 2022 13:41:58 +0000 Subject: [PATCH 02/76] Fix typo in wasm-bindgen doc page (#2963) --- website/docs/concepts/basic-web-technologies/wasm-bindgen.mdx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/website/docs/concepts/basic-web-technologies/wasm-bindgen.mdx b/website/docs/concepts/basic-web-technologies/wasm-bindgen.mdx index 2363f118df7..0c718c4cd9b 100644 --- a/website/docs/concepts/basic-web-technologies/wasm-bindgen.mdx +++ b/website/docs/concepts/basic-web-technologies/wasm-bindgen.mdx @@ -169,7 +169,7 @@ _[`JsCast` documentation](https://rustwasm.github.io/wasm-bindgen/api/wasm_bindg ### [`Closure`](https://rustwasm.github.io/wasm-bindgen/api/wasm_bindgen/closure/struct.Closure.html) -The `Closure` type provides a way to transfer Rust closures to JavaScript, the closures past to +The `Closure` type provides a way to transfer Rust closures to JavaScript, the closures passed to JavaScript must have a `'static` lifetime for soundness reasons. This type is a "handle" in the sense that whenever it is dropped it will invalidate the JS From aebd22596360d5035e64e69a1c45c522588d1ce5 Mon Sep 17 00:00:00 2001 From: WorldSEnder Date: Wed, 21 Dec 2022 01:57:55 +0000 Subject: [PATCH 03/76] Reentrant event listeners (#3037) * add test case for reentrent event listeners * use Fn to allow reentrent event listeners --- packages/yew/src/dom_bundle/btag/listeners.rs | 39 +++++++++ packages/yew/src/dom_bundle/subtree_root.rs | 85 ++++++++++++++++--- 2 files changed, 111 insertions(+), 13 deletions(-) diff --git a/packages/yew/src/dom_bundle/btag/listeners.rs b/packages/yew/src/dom_bundle/btag/listeners.rs index 746e23eb7f9..8866896f38c 100644 --- a/packages/yew/src/dom_bundle/btag/listeners.rs +++ b/packages/yew/src/dom_bundle/btag/listeners.rs @@ -749,4 +749,43 @@ mod tests { .unwrap() }) } + + #[test] + fn reentrant_listener() { + #[derive(PartialEq, Properties, Default)] + struct Reetrant { + secondary_target_ref: NodeRef, + } + impl Mixin for Reetrant { + fn view(ctx: &Context, state: &State) -> Html + where + C: Component>, + { + let targetref = &ctx.props().wrapped.secondary_target_ref; + let onclick = { + let targetref = targetref.clone(); + ctx.link().callback(move |_| { + // Note: `click` (and dispatchEvent for that matter) swallows errors thrown + // from listeners and reports them as uncaught to the console. Hence, we + // assert that we got to the second event listener instead, by dispatching a + // second Message::Action + click(&targetref); + Message::Action + }) + }; + let onclick2 = ctx.link().callback(move |_| Message::Action); + html! { +
+ + +
+ } + } + } + let (_, el) = init::(); + + assert_count(&el, 0); + click(&el); + assert_count(&el, 2); + } } diff --git a/packages/yew/src/dom_bundle/subtree_root.rs b/packages/yew/src/dom_bundle/subtree_root.rs index fdf3851963a..f9c719d3aef 100644 --- a/packages/yew/src/dom_bundle/subtree_root.rs +++ b/packages/yew/src/dom_bundle/subtree_root.rs @@ -1,15 +1,17 @@ //! Per-subtree state of apps +use std::borrow::Cow; use std::cell::RefCell; use std::collections::HashSet; use std::hash::{Hash, Hasher}; use std::rc::{Rc, Weak}; use std::sync::atomic::{AtomicBool, AtomicU32, Ordering}; -use gloo::events::{EventListener, EventListenerOptions, EventListenerPhase}; -use wasm_bindgen::prelude::wasm_bindgen; -use wasm_bindgen::JsCast; -use web_sys::{Element, Event, EventTarget as HtmlEventTarget, ShadowRoot}; +use wasm_bindgen::prelude::{wasm_bindgen, Closure}; +use wasm_bindgen::{JsCast, UnwrapThrowExt}; +use web_sys::{ + AddEventListenerOptions, Element, Event, EventTarget as HtmlEventTarget, ShadowRoot, +}; use super::{test_log, Registry}; use crate::virtual_dom::{Listener, ListenerKind}; @@ -113,6 +115,70 @@ impl From<&dyn Listener> for EventDescriptor { } } +// FIXME: this is a reproduction of gloo's EventListener to work around #2989 +// change back to gloo's implementation once it has been decided how to fix this upstream +// The important part is that we use `Fn` instead of `FnMut` below! +type EventClosure = Closure; +#[derive(Debug)] +#[must_use = "event listener will never be called after being dropped"] +struct EventListener { + target: HtmlEventTarget, + event_type: Cow<'static, str>, + callback: Option, +} + +impl Drop for EventListener { + #[inline] + fn drop(&mut self) { + if let Some(ref callback) = self.callback { + self.target + .remove_event_listener_with_callback_and_bool( + &self.event_type, + callback.as_ref().unchecked_ref(), + true, // Always capture + ) + .unwrap_throw(); + } + } +} + +impl EventListener { + fn new( + target: &HtmlEventTarget, + desc: &EventDescriptor, + callback: impl 'static + Fn(&Event), + ) -> Self { + let event_type = desc.kind.type_name(); + + let callback = Closure::wrap(Box::new(callback) as Box); + // defaults: { once: false } + let mut options = AddEventListenerOptions::new(); + options.capture(true).passive(desc.passive); + + target + .add_event_listener_with_callback_and_add_event_listener_options( + &event_type, + callback.as_ref().unchecked_ref(), + &options, + ) + .unwrap_throw(); + + EventListener { + target: target.clone(), + event_type, + callback: Some(callback), + } + } + + #[cfg(not(test))] + fn forget(mut self) { + if let Some(callback) = self.callback.take() { + // Should always match, but no need to introduce a panic path here + callback.forget(); + } + } +} + /// Ensures event handler registration. // Separate struct to DRY, while avoiding partial struct mutability. #[derive(Debug)] @@ -135,15 +201,8 @@ impl HostHandlers { } } - fn add_listener(&mut self, desc: &EventDescriptor, callback: impl 'static + FnMut(&Event)) { - let cl = { - let desc = desc.clone(); - let options = EventListenerOptions { - phase: EventListenerPhase::Capture, - passive: desc.passive, - }; - EventListener::new_with_options(&self.host, desc.kind.type_name(), options, callback) - }; + fn add_listener(&mut self, desc: &EventDescriptor, callback: impl 'static + Fn(&Event)) { + let cl = EventListener::new(&self.host, desc, callback); // Never drop the closure as this event handler is static #[cfg(not(test))] From 1542e2b1818ff566acfcd942d380a6497a35ecd0 Mon Sep 17 00:00:00 2001 From: Kai Salmon Date: Thu, 22 Dec 2022 20:38:26 +0000 Subject: [PATCH 04/76] Only handle "normal" clicks on s (#3056) * Fixing https://github.com/yewstack/yew/issues/2911 Prevents Link onclick behaviour from executing if the Ctrl key (for Windows and Linux) or Meta Key (For Mac) is pressed. This technically introduces a bug that means that links will reload the page on windows machines when the windows key is held down. However, this error is also in React Router, so I think we can get away with it. See: https://github.com/remix-run/react-router/blob/11156ac7f3d7c1c557c67cc449ecbf9bd5c6a4ca/packages/react-router-dom/dom.ts#L29 * Router Links now use default browser behaviour for alt and shift keys. This change is inspired by https://github.com/remix-run/react-router/blob/11156ac7f3d7c1c557c67cc449ecbf9bd5c6a4ca/packages/react-router-dom/dom.ts#L2://github.com/remix-run/react-router/blob/11156ac7f3d7c1c557c67cc449ecbf9bd5c6a4ca/packages/react-router-dom/dom.ts#L29 This allows uses to shift click links to save whatever the link points at, and alt click on links to open them in new windows --- packages/yew-router/src/components/link.rs | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/packages/yew-router/src/components/link.rs b/packages/yew-router/src/components/link.rs index 34c08cd63a9..3ea72ca390c 100644 --- a/packages/yew-router/src/components/link.rs +++ b/packages/yew-router/src/components/link.rs @@ -55,8 +55,10 @@ where let query = query.clone(); Callback::from(move |e: MouseEvent| { + if e.meta_key() || e.ctrl_key() || e.shift_key() || e.alt_key() { + return; + } e.prevent_default(); - match query { None => { navigator.push(&to); From d2f35e45b2f56faf7b55c0b45a0740cacee17a24 Mon Sep 17 00:00:00 2001 From: Jesper Olsen <43079279+jesper-olsen@users.noreply.github.com> Date: Thu, 22 Dec 2022 14:49:50 -0600 Subject: [PATCH 05/76] remove "Next loop" - introduction repeating in yew.rs/docs (#3040) --- website/sidebars/docs.js | 1 - website/versioned_sidebars/version-0.20-sidebars.json | 1 - 2 files changed, 2 deletions(-) diff --git a/website/sidebars/docs.js b/website/sidebars/docs.js index 6a6ca8d3548..4af523f56ec 100644 --- a/website/sidebars/docs.js +++ b/website/sidebars/docs.js @@ -117,7 +117,6 @@ module.exports = { }, items: [ 'advanced-topics/struct-components/hoc', - 'advanced-topics/struct-components/introduction', 'advanced-topics/struct-components/lifecycle', 'advanced-topics/struct-components/scope', 'advanced-topics/struct-components/callbacks', diff --git a/website/versioned_sidebars/version-0.20-sidebars.json b/website/versioned_sidebars/version-0.20-sidebars.json index fe11bbbb64e..8e1ac5ef81a 100644 --- a/website/versioned_sidebars/version-0.20-sidebars.json +++ b/website/versioned_sidebars/version-0.20-sidebars.json @@ -110,7 +110,6 @@ }, "items": [ "advanced-topics/struct-components/hoc", - "advanced-topics/struct-components/introduction", "advanced-topics/struct-components/lifecycle", "advanced-topics/struct-components/scope", "advanced-topics/struct-components/callbacks", From a5468b940d25f73201d3f7bceb1423f3e753a5f5 Mon Sep 17 00:00:00 2001 From: lucasmerlin Date: Sat, 24 Dec 2022 10:46:10 +0100 Subject: [PATCH 06/76] Add hurlurl to awesome.md (#3051) --- website/community/awesome.md | 1 + 1 file changed, 1 insertion(+) diff --git a/website/community/awesome.md b/website/community/awesome.md index 8e41674c909..c79aa5055de 100644 --- a/website/community/awesome.md +++ b/website/community/awesome.md @@ -50,6 +50,7 @@ description: 'Community projects built using yew' - [Marc Portfolio](https://gitlab.com/marcempunkt/maeurerdev) - A software developer portfolio, [Live Demo](https://maeurer.dev/). - [zzhack](https://github.com/zzhack-stack/zzhack) - A personal blog, based on Rust & Yew, [Live Demo](https://www.zzhack.fun/technology). - [viz.rs](https://github.com/viz-rs/viz-rs.github.io) - A website for viz web framework, [Live Demo](https://viz.rs/). +- [hurlurl](https://github.com/lucasmerlin/hurlurl) - A randomizing link shortener, [Live Demo](https://hurlurl.com/). ## Templates From 7bfba6b31c843471cec4b92dbf54b795731dab95 Mon Sep 17 00:00:00 2001 From: Simon Date: Wed, 28 Dec 2022 16:09:01 +0000 Subject: [PATCH 07/76] Update SVG colors (#3064) --- .static/yew.svg | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.static/yew.svg b/.static/yew.svg index 3082a4c3da2..e838a2c6076 100644 --- a/.static/yew.svg +++ b/.static/yew.svg @@ -1,7 +1,7 @@ - + - + From 38e2478d9a2b7a251f6fd068675618326d18fd5a Mon Sep 17 00:00:00 2001 From: Muhammad Hamza Date: Fri, 30 Dec 2022 17:37:10 +0500 Subject: [PATCH 08/76] Use SVG for logo on website (#3065) --- website/docusaurus.config.js | 4 ++-- .static/yew.svg => website/static/img/logo.svg | 0 2 files changed, 2 insertions(+), 2 deletions(-) rename .static/yew.svg => website/static/img/logo.svg (100%) diff --git a/website/docusaurus.config.js b/website/docusaurus.config.js index 5f75da5aeb3..0f64678e51b 100644 --- a/website/docusaurus.config.js +++ b/website/docusaurus.config.js @@ -11,7 +11,7 @@ module.exports = { baseUrl: '/', onBrokenLinks: 'throw', onBrokenMarkdownLinks: 'warn', - favicon: 'img/logo.png', + favicon: 'img/logo.svg', organizationName: 'yewstack', // Usually your GitHub org/user name. projectName: 'yew', // Usually your repo name. themeConfig: { @@ -24,7 +24,7 @@ module.exports = { title: 'Yew', logo: { alt: 'Yew Logo', - src: 'img/logo.png', + src: 'img/logo.svg', }, items: [ { diff --git a/.static/yew.svg b/website/static/img/logo.svg similarity index 100% rename from .static/yew.svg rename to website/static/img/logo.svg From 919695f5ef8df7a54d828295e58a85dbc5cdda52 Mon Sep 17 00:00:00 2001 From: Kai Salmon Date: Sun, 1 Jan 2023 18:27:07 +0000 Subject: [PATCH 09/76] The webworker in the web_worker_fib exampel is now marked as a relative path (#3057) --- examples/web_worker_fib/src/agent.rs | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/examples/web_worker_fib/src/agent.rs b/examples/web_worker_fib/src/agent.rs index 0294aeefad1..e002caeada4 100644 --- a/examples/web_worker_fib/src/agent.rs +++ b/examples/web_worker_fib/src/agent.rs @@ -52,4 +52,8 @@ impl yew_agent::Worker for Worker { fn name_of_resource() -> &'static str { "worker.js" } + + fn resource_path_is_relative() -> bool { + true + } } From 0a3ec950711de9e3848862c8c30b82a2f6984809 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 4 Jan 2023 23:23:11 +0900 Subject: [PATCH 10/76] Bump @typescript-eslint/eslint-plugin from 5.45.0 to 5.47.1 in /website (#3069) Bumps [@typescript-eslint/eslint-plugin](https://github.com/typescript-eslint/typescript-eslint/tree/HEAD/packages/eslint-plugin) from 5.45.0 to 5.47.1. - [Release notes](https://github.com/typescript-eslint/typescript-eslint/releases) - [Changelog](https://github.com/typescript-eslint/typescript-eslint/blob/main/packages/eslint-plugin/CHANGELOG.md) - [Commits](https://github.com/typescript-eslint/typescript-eslint/commits/v5.47.1/packages/eslint-plugin) --- updated-dependencies: - dependency-name: "@typescript-eslint/eslint-plugin" dependency-type: direct:development update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- website/package-lock.json | 352 ++++++++++++++++++++++++++++++++++---- website/package.json | 2 +- 2 files changed, 318 insertions(+), 36 deletions(-) diff --git a/website/package-lock.json b/website/package-lock.json index e3fdc731d3c..5253bc6d51a 100644 --- a/website/package-lock.json +++ b/website/package-lock.json @@ -31,7 +31,7 @@ "@types/react": "^17.0.43", "@types/react-helmet": "^6.1.6", "@types/react-router-dom": "^5.3.3", - "@typescript-eslint/eslint-plugin": "^5.45.0", + "@typescript-eslint/eslint-plugin": "^5.47.1", "@typescript-eslint/parser": "^5.45.0", "dir-compare": "^4.0.0", "prettier": "2.8.0", @@ -4434,14 +4434,14 @@ } }, "node_modules/@typescript-eslint/eslint-plugin": { - "version": "5.45.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.45.0.tgz", - "integrity": "sha512-CXXHNlf0oL+Yg021cxgOdMHNTXD17rHkq7iW6RFHoybdFgQBjU3yIXhhcPpGwr1CjZlo6ET8C6tzX5juQoXeGA==", + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.47.1.tgz", + "integrity": "sha512-r4RZ2Jl9kcQN7K/dcOT+J7NAimbiis4sSM9spvWimsBvDegMhKLA5vri2jG19PmIPbDjPeWzfUPQ2hjEzA4Nmg==", "dev": true, "dependencies": { - "@typescript-eslint/scope-manager": "5.45.0", - "@typescript-eslint/type-utils": "5.45.0", - "@typescript-eslint/utils": "5.45.0", + "@typescript-eslint/scope-manager": "5.47.1", + "@typescript-eslint/type-utils": "5.47.1", + "@typescript-eslint/utils": "5.47.1", "debug": "^4.3.4", "ignore": "^5.2.0", "natural-compare-lite": "^1.4.0", @@ -4466,6 +4466,53 @@ } } }, + "node_modules/@typescript-eslint/eslint-plugin/node_modules/@typescript-eslint/scope-manager": { + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.47.1.tgz", + "integrity": "sha512-9hsFDsgUwrdOoW1D97Ewog7DYSHaq4WKuNs0LHF9RiCmqB0Z+XRR4Pf7u7u9z/8CciHuJ6yxNws1XznI3ddjEw==", + "dev": true, + "dependencies": { + "@typescript-eslint/types": "5.47.1", + "@typescript-eslint/visitor-keys": "5.47.1" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + } + }, + "node_modules/@typescript-eslint/eslint-plugin/node_modules/@typescript-eslint/types": { + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.47.1.tgz", + "integrity": "sha512-CmALY9YWXEpwuu6377ybJBZdtSAnzXLSQcxLSqSQSbC7VfpMu/HLVdrnVJj7ycI138EHqocW02LPJErE35cE9A==", + "dev": true, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + } + }, + "node_modules/@typescript-eslint/eslint-plugin/node_modules/@typescript-eslint/visitor-keys": { + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.47.1.tgz", + "integrity": "sha512-rF3pmut2JCCjh6BLRhNKdYjULMb1brvoaiWDlHfLNVgmnZ0sBVJrs3SyaKE1XoDDnJuAx/hDQryHYmPUuNq0ig==", + "dev": true, + "dependencies": { + "@typescript-eslint/types": "5.47.1", + "eslint-visitor-keys": "^3.3.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + } + }, "node_modules/@typescript-eslint/parser": { "version": "5.45.0", "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-5.45.0.tgz", @@ -4511,13 +4558,13 @@ } }, "node_modules/@typescript-eslint/type-utils": { - "version": "5.45.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-5.45.0.tgz", - "integrity": "sha512-DY7BXVFSIGRGFZ574hTEyLPRiQIvI/9oGcN8t1A7f6zIs6ftbrU0nhyV26ZW//6f85avkwrLag424n+fkuoJ1Q==", + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-5.47.1.tgz", + "integrity": "sha512-/UKOeo8ee80A7/GJA427oIrBi/Gd4osk/3auBUg4Rn9EahFpevVV1mUK8hjyQD5lHPqX397x6CwOk5WGh1E/1w==", "dev": true, "dependencies": { - "@typescript-eslint/typescript-estree": "5.45.0", - "@typescript-eslint/utils": "5.45.0", + "@typescript-eslint/typescript-estree": "5.47.1", + "@typescript-eslint/utils": "5.47.1", "debug": "^4.3.4", "tsutils": "^3.21.0" }, @@ -4537,6 +4584,63 @@ } } }, + "node_modules/@typescript-eslint/type-utils/node_modules/@typescript-eslint/types": { + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.47.1.tgz", + "integrity": "sha512-CmALY9YWXEpwuu6377ybJBZdtSAnzXLSQcxLSqSQSbC7VfpMu/HLVdrnVJj7ycI138EHqocW02LPJErE35cE9A==", + "dev": true, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + } + }, + "node_modules/@typescript-eslint/type-utils/node_modules/@typescript-eslint/typescript-estree": { + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.47.1.tgz", + "integrity": "sha512-4+ZhFSuISAvRi2xUszEj0xXbNTHceV9GbH9S8oAD2a/F9SW57aJNQVOCxG8GPfSWH/X4eOPdMEU2jYVuWKEpWA==", + "dev": true, + "dependencies": { + "@typescript-eslint/types": "5.47.1", + "@typescript-eslint/visitor-keys": "5.47.1", + "debug": "^4.3.4", + "globby": "^11.1.0", + "is-glob": "^4.0.3", + "semver": "^7.3.7", + "tsutils": "^3.21.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } + } + }, + "node_modules/@typescript-eslint/type-utils/node_modules/@typescript-eslint/visitor-keys": { + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.47.1.tgz", + "integrity": "sha512-rF3pmut2JCCjh6BLRhNKdYjULMb1brvoaiWDlHfLNVgmnZ0sBVJrs3SyaKE1XoDDnJuAx/hDQryHYmPUuNq0ig==", + "dev": true, + "dependencies": { + "@typescript-eslint/types": "5.47.1", + "eslint-visitor-keys": "^3.3.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + } + }, "node_modules/@typescript-eslint/types": { "version": "5.45.0", "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.45.0.tgz", @@ -4578,16 +4682,16 @@ } }, "node_modules/@typescript-eslint/utils": { - "version": "5.45.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-5.45.0.tgz", - "integrity": "sha512-OUg2JvsVI1oIee/SwiejTot2OxwU8a7UfTFMOdlhD2y+Hl6memUSL4s98bpUTo8EpVEr0lmwlU7JSu/p2QpSvA==", + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-5.47.1.tgz", + "integrity": "sha512-l90SdwqfmkuIVaREZ2ykEfCezepCLxzWMo5gVfcJsJCaT4jHT+QjgSkYhs5BMQmWqE9k3AtIfk4g211z/sTMVw==", "dev": true, "dependencies": { "@types/json-schema": "^7.0.9", "@types/semver": "^7.3.12", - "@typescript-eslint/scope-manager": "5.45.0", - "@typescript-eslint/types": "5.45.0", - "@typescript-eslint/typescript-estree": "5.45.0", + "@typescript-eslint/scope-manager": "5.47.1", + "@typescript-eslint/types": "5.47.1", + "@typescript-eslint/typescript-estree": "5.47.1", "eslint-scope": "^5.1.1", "eslint-utils": "^3.0.0", "semver": "^7.3.7" @@ -4603,6 +4707,80 @@ "eslint": "^6.0.0 || ^7.0.0 || ^8.0.0" } }, + "node_modules/@typescript-eslint/utils/node_modules/@typescript-eslint/scope-manager": { + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.47.1.tgz", + "integrity": "sha512-9hsFDsgUwrdOoW1D97Ewog7DYSHaq4WKuNs0LHF9RiCmqB0Z+XRR4Pf7u7u9z/8CciHuJ6yxNws1XznI3ddjEw==", + "dev": true, + "dependencies": { + "@typescript-eslint/types": "5.47.1", + "@typescript-eslint/visitor-keys": "5.47.1" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + } + }, + "node_modules/@typescript-eslint/utils/node_modules/@typescript-eslint/types": { + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.47.1.tgz", + "integrity": "sha512-CmALY9YWXEpwuu6377ybJBZdtSAnzXLSQcxLSqSQSbC7VfpMu/HLVdrnVJj7ycI138EHqocW02LPJErE35cE9A==", + "dev": true, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + } + }, + "node_modules/@typescript-eslint/utils/node_modules/@typescript-eslint/typescript-estree": { + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.47.1.tgz", + "integrity": "sha512-4+ZhFSuISAvRi2xUszEj0xXbNTHceV9GbH9S8oAD2a/F9SW57aJNQVOCxG8GPfSWH/X4eOPdMEU2jYVuWKEpWA==", + "dev": true, + "dependencies": { + "@typescript-eslint/types": "5.47.1", + "@typescript-eslint/visitor-keys": "5.47.1", + "debug": "^4.3.4", + "globby": "^11.1.0", + "is-glob": "^4.0.3", + "semver": "^7.3.7", + "tsutils": "^3.21.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } + } + }, + "node_modules/@typescript-eslint/utils/node_modules/@typescript-eslint/visitor-keys": { + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.47.1.tgz", + "integrity": "sha512-rF3pmut2JCCjh6BLRhNKdYjULMb1brvoaiWDlHfLNVgmnZ0sBVJrs3SyaKE1XoDDnJuAx/hDQryHYmPUuNq0ig==", + "dev": true, + "dependencies": { + "@typescript-eslint/types": "5.47.1", + "eslint-visitor-keys": "^3.3.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + } + }, "node_modules/@typescript-eslint/visitor-keys": { "version": "5.45.0", "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.45.0.tgz", @@ -17008,20 +17186,48 @@ } }, "@typescript-eslint/eslint-plugin": { - "version": "5.45.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.45.0.tgz", - "integrity": "sha512-CXXHNlf0oL+Yg021cxgOdMHNTXD17rHkq7iW6RFHoybdFgQBjU3yIXhhcPpGwr1CjZlo6ET8C6tzX5juQoXeGA==", + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.47.1.tgz", + "integrity": "sha512-r4RZ2Jl9kcQN7K/dcOT+J7NAimbiis4sSM9spvWimsBvDegMhKLA5vri2jG19PmIPbDjPeWzfUPQ2hjEzA4Nmg==", "dev": true, "requires": { - "@typescript-eslint/scope-manager": "5.45.0", - "@typescript-eslint/type-utils": "5.45.0", - "@typescript-eslint/utils": "5.45.0", + "@typescript-eslint/scope-manager": "5.47.1", + "@typescript-eslint/type-utils": "5.47.1", + "@typescript-eslint/utils": "5.47.1", "debug": "^4.3.4", "ignore": "^5.2.0", "natural-compare-lite": "^1.4.0", "regexpp": "^3.2.0", "semver": "^7.3.7", "tsutils": "^3.21.0" + }, + "dependencies": { + "@typescript-eslint/scope-manager": { + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.47.1.tgz", + "integrity": "sha512-9hsFDsgUwrdOoW1D97Ewog7DYSHaq4WKuNs0LHF9RiCmqB0Z+XRR4Pf7u7u9z/8CciHuJ6yxNws1XznI3ddjEw==", + "dev": true, + "requires": { + "@typescript-eslint/types": "5.47.1", + "@typescript-eslint/visitor-keys": "5.47.1" + } + }, + "@typescript-eslint/types": { + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.47.1.tgz", + "integrity": "sha512-CmALY9YWXEpwuu6377ybJBZdtSAnzXLSQcxLSqSQSbC7VfpMu/HLVdrnVJj7ycI138EHqocW02LPJErE35cE9A==", + "dev": true + }, + "@typescript-eslint/visitor-keys": { + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.47.1.tgz", + "integrity": "sha512-rF3pmut2JCCjh6BLRhNKdYjULMb1brvoaiWDlHfLNVgmnZ0sBVJrs3SyaKE1XoDDnJuAx/hDQryHYmPUuNq0ig==", + "dev": true, + "requires": { + "@typescript-eslint/types": "5.47.1", + "eslint-visitor-keys": "^3.3.0" + } + } } }, "@typescript-eslint/parser": { @@ -17047,15 +17253,48 @@ } }, "@typescript-eslint/type-utils": { - "version": "5.45.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-5.45.0.tgz", - "integrity": "sha512-DY7BXVFSIGRGFZ574hTEyLPRiQIvI/9oGcN8t1A7f6zIs6ftbrU0nhyV26ZW//6f85avkwrLag424n+fkuoJ1Q==", + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-5.47.1.tgz", + "integrity": "sha512-/UKOeo8ee80A7/GJA427oIrBi/Gd4osk/3auBUg4Rn9EahFpevVV1mUK8hjyQD5lHPqX397x6CwOk5WGh1E/1w==", "dev": true, "requires": { - "@typescript-eslint/typescript-estree": "5.45.0", - "@typescript-eslint/utils": "5.45.0", + "@typescript-eslint/typescript-estree": "5.47.1", + "@typescript-eslint/utils": "5.47.1", "debug": "^4.3.4", "tsutils": "^3.21.0" + }, + "dependencies": { + "@typescript-eslint/types": { + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.47.1.tgz", + "integrity": "sha512-CmALY9YWXEpwuu6377ybJBZdtSAnzXLSQcxLSqSQSbC7VfpMu/HLVdrnVJj7ycI138EHqocW02LPJErE35cE9A==", + "dev": true + }, + "@typescript-eslint/typescript-estree": { + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.47.1.tgz", + "integrity": "sha512-4+ZhFSuISAvRi2xUszEj0xXbNTHceV9GbH9S8oAD2a/F9SW57aJNQVOCxG8GPfSWH/X4eOPdMEU2jYVuWKEpWA==", + "dev": true, + "requires": { + "@typescript-eslint/types": "5.47.1", + "@typescript-eslint/visitor-keys": "5.47.1", + "debug": "^4.3.4", + "globby": "^11.1.0", + "is-glob": "^4.0.3", + "semver": "^7.3.7", + "tsutils": "^3.21.0" + } + }, + "@typescript-eslint/visitor-keys": { + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.47.1.tgz", + "integrity": "sha512-rF3pmut2JCCjh6BLRhNKdYjULMb1brvoaiWDlHfLNVgmnZ0sBVJrs3SyaKE1XoDDnJuAx/hDQryHYmPUuNq0ig==", + "dev": true, + "requires": { + "@typescript-eslint/types": "5.47.1", + "eslint-visitor-keys": "^3.3.0" + } + } } }, "@typescript-eslint/types": { @@ -17080,19 +17319,62 @@ } }, "@typescript-eslint/utils": { - "version": "5.45.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-5.45.0.tgz", - "integrity": "sha512-OUg2JvsVI1oIee/SwiejTot2OxwU8a7UfTFMOdlhD2y+Hl6memUSL4s98bpUTo8EpVEr0lmwlU7JSu/p2QpSvA==", + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-5.47.1.tgz", + "integrity": "sha512-l90SdwqfmkuIVaREZ2ykEfCezepCLxzWMo5gVfcJsJCaT4jHT+QjgSkYhs5BMQmWqE9k3AtIfk4g211z/sTMVw==", "dev": true, "requires": { "@types/json-schema": "^7.0.9", "@types/semver": "^7.3.12", - "@typescript-eslint/scope-manager": "5.45.0", - "@typescript-eslint/types": "5.45.0", - "@typescript-eslint/typescript-estree": "5.45.0", + "@typescript-eslint/scope-manager": "5.47.1", + "@typescript-eslint/types": "5.47.1", + "@typescript-eslint/typescript-estree": "5.47.1", "eslint-scope": "^5.1.1", "eslint-utils": "^3.0.0", "semver": "^7.3.7" + }, + "dependencies": { + "@typescript-eslint/scope-manager": { + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.47.1.tgz", + "integrity": "sha512-9hsFDsgUwrdOoW1D97Ewog7DYSHaq4WKuNs0LHF9RiCmqB0Z+XRR4Pf7u7u9z/8CciHuJ6yxNws1XznI3ddjEw==", + "dev": true, + "requires": { + "@typescript-eslint/types": "5.47.1", + "@typescript-eslint/visitor-keys": "5.47.1" + } + }, + "@typescript-eslint/types": { + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.47.1.tgz", + "integrity": "sha512-CmALY9YWXEpwuu6377ybJBZdtSAnzXLSQcxLSqSQSbC7VfpMu/HLVdrnVJj7ycI138EHqocW02LPJErE35cE9A==", + "dev": true + }, + "@typescript-eslint/typescript-estree": { + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.47.1.tgz", + "integrity": "sha512-4+ZhFSuISAvRi2xUszEj0xXbNTHceV9GbH9S8oAD2a/F9SW57aJNQVOCxG8GPfSWH/X4eOPdMEU2jYVuWKEpWA==", + "dev": true, + "requires": { + "@typescript-eslint/types": "5.47.1", + "@typescript-eslint/visitor-keys": "5.47.1", + "debug": "^4.3.4", + "globby": "^11.1.0", + "is-glob": "^4.0.3", + "semver": "^7.3.7", + "tsutils": "^3.21.0" + } + }, + "@typescript-eslint/visitor-keys": { + "version": "5.47.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.47.1.tgz", + "integrity": "sha512-rF3pmut2JCCjh6BLRhNKdYjULMb1brvoaiWDlHfLNVgmnZ0sBVJrs3SyaKE1XoDDnJuAx/hDQryHYmPUuNq0ig==", + "dev": true, + "requires": { + "@typescript-eslint/types": "5.47.1", + "eslint-visitor-keys": "^3.3.0" + } + } } }, "@typescript-eslint/visitor-keys": { diff --git a/website/package.json b/website/package.json index 933580a0714..7467d5193a7 100644 --- a/website/package.json +++ b/website/package.json @@ -52,7 +52,7 @@ "@types/react": "^17.0.43", "@types/react-helmet": "^6.1.6", "@types/react-router-dom": "^5.3.3", - "@typescript-eslint/eslint-plugin": "^5.45.0", + "@typescript-eslint/eslint-plugin": "^5.47.1", "@typescript-eslint/parser": "^5.45.0", "dir-compare": "^4.0.0", "prettier": "2.8.0", From cf9077ddb59939f09a4d51bcbca7fe3ab7761d0f Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 4 Jan 2023 23:24:12 +0900 Subject: [PATCH 11/76] Bump actions/upload-artifact from 2 to 3 (#3074) Bumps [actions/upload-artifact](https://github.com/actions/upload-artifact) from 2 to 3. - [Release notes](https://github.com/actions/upload-artifact/releases) - [Commits](https://github.com/actions/upload-artifact/compare/v2...v3) --- updated-dependencies: - dependency-name: actions/upload-artifact dependency-type: direct:production update-type: version-update:semver-major ... Signed-off-by: dependabot[bot] Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- .github/workflows/benchmark-ssr.yml | 2 +- .github/workflows/build-api-docs.yml | 4 ++-- .github/workflows/build-website.yml | 4 ++-- .github/workflows/size-cmp.yml | 2 +- 4 files changed, 6 insertions(+), 6 deletions(-) diff --git a/.github/workflows/benchmark-ssr.yml b/.github/workflows/benchmark-ssr.yml index b9fa89739bb..e42a0e8b08e 100644 --- a/.github/workflows/benchmark-ssr.yml +++ b/.github/workflows/benchmark-ssr.yml @@ -62,7 +62,7 @@ jobs: echo "${{ github.event.number }}" > .PR_NUMBER - name: Upload Artifact - uses: actions/upload-artifact@v2 + uses: actions/upload-artifact@v3 with: name: benchmark-ssr path: | diff --git a/.github/workflows/build-api-docs.yml b/.github/workflows/build-api-docs.yml index a6e0b4f66b8..001cf542161 100644 --- a/.github/workflows/build-api-docs.yml +++ b/.github/workflows/build-api-docs.yml @@ -46,7 +46,7 @@ jobs: cp -r target/doc/* api-docs/dist/next - name: Upload build artifact - uses: actions/upload-artifact@v2 + uses: actions/upload-artifact@v3 with: name: api-docs path: api-docs/ @@ -59,7 +59,7 @@ jobs: - if: github.event_name == 'pull_request' name: Upload pr info - uses: actions/upload-artifact@v2 + uses: actions/upload-artifact@v3 with: name: pr-info path: "${{ env.PR_INFO_FILE }}" diff --git a/.github/workflows/build-website.yml b/.github/workflows/build-website.yml index 8f7fc91d6b6..821791b0644 100644 --- a/.github/workflows/build-website.yml +++ b/.github/workflows/build-website.yml @@ -48,7 +48,7 @@ jobs: npm run build - name: Upload build artifact - uses: actions/upload-artifact@v2 + uses: actions/upload-artifact@v3 with: name: website path: website/build/ @@ -61,7 +61,7 @@ jobs: - if: github.event_name == 'pull_request' name: Upload pr info - uses: actions/upload-artifact@v2 + uses: actions/upload-artifact@v3 with: name: pr-info path: "${{ env.PR_INFO_FILE }}" diff --git a/.github/workflows/size-cmp.yml b/.github/workflows/size-cmp.yml index 4e421bcb0d2..b223c816864 100644 --- a/.github/workflows/size-cmp.yml +++ b/.github/workflows/size-cmp.yml @@ -72,7 +72,7 @@ jobs: ISSUE_NUMBER: ${{ github.event.number }} - name: Upload Artifact - uses: actions/upload-artifact@v2 + uses: actions/upload-artifact@v3 with: name: size-cmp-info path: ".SIZE_CMP_INFO" From 685e1737bf7ff02f24b136a0ca97585177ac86af Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 4 Jan 2023 23:24:35 +0900 Subject: [PATCH 12/76] Bump jetli/trunk-action from 0.1.0 to 0.2.0 (#3073) Bumps [jetli/trunk-action](https://github.com/jetli/trunk-action) from 0.1.0 to 0.2.0. - [Release notes](https://github.com/jetli/trunk-action/releases) - [Commits](https://github.com/jetli/trunk-action/compare/v0.1.0...v0.2.0) --- updated-dependencies: - dependency-name: jetli/trunk-action dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- .github/workflows/publish-examples.yml | 2 +- .github/workflows/size-cmp.yml | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/publish-examples.yml b/.github/workflows/publish-examples.yml index e8089d5ed1f..c8c2a74fef2 100644 --- a/.github/workflows/publish-examples.yml +++ b/.github/workflows/publish-examples.yml @@ -26,7 +26,7 @@ jobs: - uses: Swatinem/rust-cache@v2 - - uses: jetli/trunk-action@v0.1.0 + - uses: jetli/trunk-action@v0.2.0 with: version: 'latest' diff --git a/.github/workflows/size-cmp.yml b/.github/workflows/size-cmp.yml index b223c816864..42eeadef941 100644 --- a/.github/workflows/size-cmp.yml +++ b/.github/workflows/size-cmp.yml @@ -49,7 +49,7 @@ jobs: key: pr - name: Setup Trunk - uses: jetli/trunk-action@v0.1.0 + uses: jetli/trunk-action@v0.2.0 with: version: 'latest' From 52730df5df7fdcbc4cbd1c242a219bb0c43e41b3 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 4 Jan 2023 23:25:15 +0900 Subject: [PATCH 13/76] Bump @docusaurus/plugin-client-redirects from 2.1.0 to 2.2.0 in /website (#3072) Bumps [@docusaurus/plugin-client-redirects](https://github.com/facebook/docusaurus/tree/HEAD/packages/docusaurus-plugin-client-redirects) from 2.1.0 to 2.2.0. - [Release notes](https://github.com/facebook/docusaurus/releases) - [Changelog](https://github.com/facebook/docusaurus/blob/main/CHANGELOG.md) - [Commits](https://github.com/facebook/docusaurus/commits/v2.2.0/packages/docusaurus-plugin-client-redirects) --- updated-dependencies: - dependency-name: "@docusaurus/plugin-client-redirects" dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- website/package-lock.json | 281 +++++++++++++++----------------------- website/package.json | 2 +- 2 files changed, 111 insertions(+), 172 deletions(-) diff --git a/website/package-lock.json b/website/package-lock.json index 5253bc6d51a..173d556c35f 100644 --- a/website/package-lock.json +++ b/website/package-lock.json @@ -9,7 +9,7 @@ "version": "0.0.0", "dependencies": { "@docusaurus/core": "~2.2.0", - "@docusaurus/plugin-client-redirects": "~2.1.0", + "@docusaurus/plugin-client-redirects": "~2.2.0", "@docusaurus/plugin-content-docs": "~2.2.0", "@docusaurus/plugin-content-pages": "~2.2.0", "@docusaurus/plugin-google-analytics": "~2.2.0", @@ -2135,15 +2135,15 @@ } }, "node_modules/@docusaurus/plugin-client-redirects": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/@docusaurus/plugin-client-redirects/-/plugin-client-redirects-2.1.0.tgz", - "integrity": "sha512-3PhzwHSyZWqBAFPJuLJE3dZVuKWQEj9ReQP85Z3/2hpnQoVNBgAqc+64FIko0FvvK1iluLeasO7NWGyuATngvw==", + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/plugin-client-redirects/-/plugin-client-redirects-2.2.0.tgz", + "integrity": "sha512-psBoWi+cbc2I+VPkKJlcZ12tRN3xiv22tnZfNKyMo18iSY8gr4B6Q0G2KZXGPgNGJ/6gq7ATfgDK6p9h9XRxMQ==", "dependencies": { - "@docusaurus/core": "2.1.0", - "@docusaurus/logger": "2.1.0", - "@docusaurus/utils": "2.1.0", - "@docusaurus/utils-common": "2.1.0", - "@docusaurus/utils-validation": "2.1.0", + "@docusaurus/core": "2.2.0", + "@docusaurus/logger": "2.2.0", + "@docusaurus/utils": "2.2.0", + "@docusaurus/utils-common": "2.2.0", + "@docusaurus/utils-validation": "2.2.0", "eta": "^1.12.3", "fs-extra": "^10.1.0", "lodash": "^4.17.21", @@ -2157,102 +2157,79 @@ "react-dom": "^16.8.4 || ^17.0.0" } }, - "node_modules/@docusaurus/plugin-client-redirects/node_modules/@docusaurus/core": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/@docusaurus/core/-/core-2.1.0.tgz", - "integrity": "sha512-/ZJ6xmm+VB9Izbn0/s6h6289cbPy2k4iYFwWDhjiLsVqwa/Y0YBBcXvStfaHccudUC3OfP+26hMk7UCjc50J6Q==", + "node_modules/@docusaurus/plugin-client-redirects/node_modules/@docusaurus/logger": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/logger/-/logger-2.2.0.tgz", + "integrity": "sha512-DF3j1cA5y2nNsu/vk8AG7xwpZu6f5MKkPPMaaIbgXLnWGfm6+wkOeW7kNrxnM95YOhKUkJUophX69nGUnLsm0A==", "dependencies": { - "@babel/core": "^7.18.6", - "@babel/generator": "^7.18.7", - "@babel/plugin-syntax-dynamic-import": "^7.8.3", - "@babel/plugin-transform-runtime": "^7.18.6", - "@babel/preset-env": "^7.18.6", - "@babel/preset-react": "^7.18.6", - "@babel/preset-typescript": "^7.18.6", - "@babel/runtime": "^7.18.6", - "@babel/runtime-corejs3": "^7.18.6", - "@babel/traverse": "^7.18.8", - "@docusaurus/cssnano-preset": "2.1.0", - "@docusaurus/logger": "2.1.0", - "@docusaurus/mdx-loader": "2.1.0", - "@docusaurus/react-loadable": "5.5.2", - "@docusaurus/utils": "2.1.0", - "@docusaurus/utils-common": "2.1.0", - "@docusaurus/utils-validation": "2.1.0", - "@slorber/static-site-generator-webpack-plugin": "^4.0.7", - "@svgr/webpack": "^6.2.1", - "autoprefixer": "^10.4.7", - "babel-loader": "^8.2.5", - "babel-plugin-dynamic-import-node": "^2.3.3", - "boxen": "^6.2.1", "chalk": "^4.1.2", - "chokidar": "^3.5.3", - "clean-css": "^5.3.0", - "cli-table3": "^0.6.2", - "combine-promises": "^1.1.0", - "commander": "^5.1.0", - "copy-webpack-plugin": "^11.0.0", - "core-js": "^3.23.3", - "css-loader": "^6.7.1", - "css-minimizer-webpack-plugin": "^4.0.0", - "cssnano": "^5.1.12", - "del": "^6.1.1", - "detect-port": "^1.3.0", - "escape-html": "^1.0.3", - "eta": "^1.12.3", + "tslib": "^2.4.0" + }, + "engines": { + "node": ">=16.14" + } + }, + "node_modules/@docusaurus/plugin-client-redirects/node_modules/@docusaurus/utils": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/utils/-/utils-2.2.0.tgz", + "integrity": "sha512-oNk3cjvx7Tt1Lgh/aeZAmFpGV2pDr5nHKrBVx6hTkzGhrnMuQqLt6UPlQjdYQ3QHXwyF/ZtZMO1D5Pfi0lu7SA==", + "dependencies": { + "@docusaurus/logger": "2.2.0", + "@svgr/webpack": "^6.2.1", "file-loader": "^6.2.0", "fs-extra": "^10.1.0", - "html-minifier-terser": "^6.1.0", - "html-tags": "^3.2.0", - "html-webpack-plugin": "^5.5.0", - "import-fresh": "^3.3.0", - "leven": "^3.1.0", + "github-slugger": "^1.4.0", + "globby": "^11.1.0", + "gray-matter": "^4.0.3", + "js-yaml": "^4.1.0", "lodash": "^4.17.21", - "mini-css-extract-plugin": "^2.6.1", - "postcss": "^8.4.14", - "postcss-loader": "^7.0.0", - "prompts": "^2.4.2", - "react-dev-utils": "^12.0.1", - "react-helmet-async": "^1.3.0", - "react-loadable": "npm:@docusaurus/react-loadable@5.5.2", - "react-loadable-ssr-addon-v5-slorber": "^1.0.1", - "react-router": "^5.3.3", - "react-router-config": "^5.1.1", - "react-router-dom": "^5.3.3", - "rtl-detect": "^1.0.4", - "semver": "^7.3.7", - "serve-handler": "^6.1.3", + "micromatch": "^4.0.5", + "resolve-pathname": "^3.0.0", "shelljs": "^0.8.5", - "terser-webpack-plugin": "^5.3.3", "tslib": "^2.4.0", - "update-notifier": "^5.1.0", "url-loader": "^4.1.1", - "wait-on": "^6.0.1", - "webpack": "^5.73.0", - "webpack-bundle-analyzer": "^4.5.0", - "webpack-dev-server": "^4.9.3", - "webpack-merge": "^5.8.0", - "webpackbar": "^5.0.2" + "webpack": "^5.73.0" }, - "bin": { - "docusaurus": "bin/docusaurus.mjs" + "engines": { + "node": ">=16.14" + }, + "peerDependencies": { + "@docusaurus/types": "*" + }, + "peerDependenciesMeta": { + "@docusaurus/types": { + "optional": true + } + } + }, + "node_modules/@docusaurus/plugin-client-redirects/node_modules/@docusaurus/utils-common": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/utils-common/-/utils-common-2.2.0.tgz", + "integrity": "sha512-qebnerHp+cyovdUseDQyYFvMW1n1nv61zGe5JJfoNQUnjKuApch3IVsz+/lZ9a38pId8kqehC1Ao2bW/s0ntDA==", + "dependencies": { + "tslib": "^2.4.0" }, "engines": { "node": ">=16.14" }, "peerDependencies": { - "react": "^16.8.4 || ^17.0.0", - "react-dom": "^16.8.4 || ^17.0.0" + "@docusaurus/types": "*" + }, + "peerDependenciesMeta": { + "@docusaurus/types": { + "optional": true + } } }, - "node_modules/@docusaurus/plugin-client-redirects/node_modules/@docusaurus/cssnano-preset": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/@docusaurus/cssnano-preset/-/cssnano-preset-2.1.0.tgz", - "integrity": "sha512-pRLewcgGhOies6pzsUROfmPStDRdFw+FgV5sMtLr5+4Luv2rty5+b/eSIMMetqUsmg3A9r9bcxHk9bKAKvx3zQ==", + "node_modules/@docusaurus/plugin-client-redirects/node_modules/@docusaurus/utils-validation": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/utils-validation/-/utils-validation-2.2.0.tgz", + "integrity": "sha512-I1hcsG3yoCkasOL5qQAYAfnmVoLei7apugT6m4crQjmDGxq+UkiRrq55UqmDDyZlac/6ax/JC0p+usZ6W4nVyg==", "dependencies": { - "cssnano-preset-advanced": "^5.3.8", - "postcss": "^8.4.14", - "postcss-sort-media-queries": "^4.2.1", + "@docusaurus/logger": "2.2.0", + "@docusaurus/utils": "2.2.0", + "joi": "^17.6.0", + "js-yaml": "^4.1.0", "tslib": "^2.4.0" }, "engines": { @@ -15460,107 +15437,69 @@ } }, "@docusaurus/plugin-client-redirects": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/@docusaurus/plugin-client-redirects/-/plugin-client-redirects-2.1.0.tgz", - "integrity": "sha512-3PhzwHSyZWqBAFPJuLJE3dZVuKWQEj9ReQP85Z3/2hpnQoVNBgAqc+64FIko0FvvK1iluLeasO7NWGyuATngvw==", + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/plugin-client-redirects/-/plugin-client-redirects-2.2.0.tgz", + "integrity": "sha512-psBoWi+cbc2I+VPkKJlcZ12tRN3xiv22tnZfNKyMo18iSY8gr4B6Q0G2KZXGPgNGJ/6gq7ATfgDK6p9h9XRxMQ==", "requires": { - "@docusaurus/core": "2.1.0", - "@docusaurus/logger": "2.1.0", - "@docusaurus/utils": "2.1.0", - "@docusaurus/utils-common": "2.1.0", - "@docusaurus/utils-validation": "2.1.0", + "@docusaurus/core": "2.2.0", + "@docusaurus/logger": "2.2.0", + "@docusaurus/utils": "2.2.0", + "@docusaurus/utils-common": "2.2.0", + "@docusaurus/utils-validation": "2.2.0", "eta": "^1.12.3", "fs-extra": "^10.1.0", "lodash": "^4.17.21", "tslib": "^2.4.0" }, "dependencies": { - "@docusaurus/core": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/@docusaurus/core/-/core-2.1.0.tgz", - "integrity": "sha512-/ZJ6xmm+VB9Izbn0/s6h6289cbPy2k4iYFwWDhjiLsVqwa/Y0YBBcXvStfaHccudUC3OfP+26hMk7UCjc50J6Q==", + "@docusaurus/logger": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/logger/-/logger-2.2.0.tgz", + "integrity": "sha512-DF3j1cA5y2nNsu/vk8AG7xwpZu6f5MKkPPMaaIbgXLnWGfm6+wkOeW7kNrxnM95YOhKUkJUophX69nGUnLsm0A==", "requires": { - "@babel/core": "^7.18.6", - "@babel/generator": "^7.18.7", - "@babel/plugin-syntax-dynamic-import": "^7.8.3", - "@babel/plugin-transform-runtime": "^7.18.6", - "@babel/preset-env": "^7.18.6", - "@babel/preset-react": "^7.18.6", - "@babel/preset-typescript": "^7.18.6", - "@babel/runtime": "^7.18.6", - "@babel/runtime-corejs3": "^7.18.6", - "@babel/traverse": "^7.18.8", - "@docusaurus/cssnano-preset": "2.1.0", - "@docusaurus/logger": "2.1.0", - "@docusaurus/mdx-loader": "2.1.0", - "@docusaurus/react-loadable": "5.5.2", - "@docusaurus/utils": "2.1.0", - "@docusaurus/utils-common": "2.1.0", - "@docusaurus/utils-validation": "2.1.0", - "@slorber/static-site-generator-webpack-plugin": "^4.0.7", - "@svgr/webpack": "^6.2.1", - "autoprefixer": "^10.4.7", - "babel-loader": "^8.2.5", - "babel-plugin-dynamic-import-node": "^2.3.3", - "boxen": "^6.2.1", "chalk": "^4.1.2", - "chokidar": "^3.5.3", - "clean-css": "^5.3.0", - "cli-table3": "^0.6.2", - "combine-promises": "^1.1.0", - "commander": "^5.1.0", - "copy-webpack-plugin": "^11.0.0", - "core-js": "^3.23.3", - "css-loader": "^6.7.1", - "css-minimizer-webpack-plugin": "^4.0.0", - "cssnano": "^5.1.12", - "del": "^6.1.1", - "detect-port": "^1.3.0", - "escape-html": "^1.0.3", - "eta": "^1.12.3", + "tslib": "^2.4.0" + } + }, + "@docusaurus/utils": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/utils/-/utils-2.2.0.tgz", + "integrity": "sha512-oNk3cjvx7Tt1Lgh/aeZAmFpGV2pDr5nHKrBVx6hTkzGhrnMuQqLt6UPlQjdYQ3QHXwyF/ZtZMO1D5Pfi0lu7SA==", + "requires": { + "@docusaurus/logger": "2.2.0", + "@svgr/webpack": "^6.2.1", "file-loader": "^6.2.0", "fs-extra": "^10.1.0", - "html-minifier-terser": "^6.1.0", - "html-tags": "^3.2.0", - "html-webpack-plugin": "^5.5.0", - "import-fresh": "^3.3.0", - "leven": "^3.1.0", + "github-slugger": "^1.4.0", + "globby": "^11.1.0", + "gray-matter": "^4.0.3", + "js-yaml": "^4.1.0", "lodash": "^4.17.21", - "mini-css-extract-plugin": "^2.6.1", - "postcss": "^8.4.14", - "postcss-loader": "^7.0.0", - "prompts": "^2.4.2", - "react-dev-utils": "^12.0.1", - "react-helmet-async": "^1.3.0", - "react-loadable": "npm:@docusaurus/react-loadable@5.5.2", - "react-loadable-ssr-addon-v5-slorber": "^1.0.1", - "react-router": "^5.3.3", - "react-router-config": "^5.1.1", - "react-router-dom": "^5.3.3", - "rtl-detect": "^1.0.4", - "semver": "^7.3.7", - "serve-handler": "^6.1.3", + "micromatch": "^4.0.5", + "resolve-pathname": "^3.0.0", "shelljs": "^0.8.5", - "terser-webpack-plugin": "^5.3.3", "tslib": "^2.4.0", - "update-notifier": "^5.1.0", "url-loader": "^4.1.1", - "wait-on": "^6.0.1", - "webpack": "^5.73.0", - "webpack-bundle-analyzer": "^4.5.0", - "webpack-dev-server": "^4.9.3", - "webpack-merge": "^5.8.0", - "webpackbar": "^5.0.2" + "webpack": "^5.73.0" } }, - "@docusaurus/cssnano-preset": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/@docusaurus/cssnano-preset/-/cssnano-preset-2.1.0.tgz", - "integrity": "sha512-pRLewcgGhOies6pzsUROfmPStDRdFw+FgV5sMtLr5+4Luv2rty5+b/eSIMMetqUsmg3A9r9bcxHk9bKAKvx3zQ==", + "@docusaurus/utils-common": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/utils-common/-/utils-common-2.2.0.tgz", + "integrity": "sha512-qebnerHp+cyovdUseDQyYFvMW1n1nv61zGe5JJfoNQUnjKuApch3IVsz+/lZ9a38pId8kqehC1Ao2bW/s0ntDA==", "requires": { - "cssnano-preset-advanced": "^5.3.8", - "postcss": "^8.4.14", - "postcss-sort-media-queries": "^4.2.1", + "tslib": "^2.4.0" + } + }, + "@docusaurus/utils-validation": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/utils-validation/-/utils-validation-2.2.0.tgz", + "integrity": "sha512-I1hcsG3yoCkasOL5qQAYAfnmVoLei7apugT6m4crQjmDGxq+UkiRrq55UqmDDyZlac/6ax/JC0p+usZ6W4nVyg==", + "requires": { + "@docusaurus/logger": "2.2.0", + "@docusaurus/utils": "2.2.0", + "joi": "^17.6.0", + "js-yaml": "^4.1.0", "tslib": "^2.4.0" } } diff --git a/website/package.json b/website/package.json index 7467d5193a7..cc4ca1e8549 100644 --- a/website/package.json +++ b/website/package.json @@ -18,7 +18,7 @@ }, "dependencies": { "@docusaurus/core": "~2.2.0", - "@docusaurus/plugin-client-redirects": "~2.1.0", + "@docusaurus/plugin-client-redirects": "~2.2.0", "@docusaurus/plugin-content-docs": "~2.2.0", "@docusaurus/plugin-content-pages": "~2.2.0", "@docusaurus/plugin-google-analytics": "~2.2.0", From 1d35148d3e95f7e5b5bcdd84e41c8148d38900cf Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 4 Jan 2023 23:25:39 +0900 Subject: [PATCH 14/76] Bump prettier from 2.8.0 to 2.8.1 in /website (#3070) Bumps [prettier](https://github.com/prettier/prettier) from 2.8.0 to 2.8.1. - [Release notes](https://github.com/prettier/prettier/releases) - [Changelog](https://github.com/prettier/prettier/blob/main/CHANGELOG.md) - [Commits](https://github.com/prettier/prettier/compare/2.8.0...2.8.1) --- updated-dependencies: - dependency-name: prettier dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- website/package-lock.json | 14 +++++++------- website/package.json | 2 +- 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/website/package-lock.json b/website/package-lock.json index 173d556c35f..cc21b66efbd 100644 --- a/website/package-lock.json +++ b/website/package-lock.json @@ -34,7 +34,7 @@ "@typescript-eslint/eslint-plugin": "^5.47.1", "@typescript-eslint/parser": "^5.45.0", "dir-compare": "^4.0.0", - "prettier": "2.8.0", + "prettier": "2.8.1", "typescript": "^4.8.3" } }, @@ -10786,9 +10786,9 @@ } }, "node_modules/prettier": { - "version": "2.8.0", - "resolved": "https://registry.npmjs.org/prettier/-/prettier-2.8.0.tgz", - "integrity": "sha512-9Lmg8hTFZKG0Asr/kW9Bp8tJjRVluO8EJQVfY2T7FMw9T5jy4I/Uvx0Rca/XWf50QQ1/SS48+6IJWnrb+2yemA==", + "version": "2.8.1", + "resolved": "https://registry.npmjs.org/prettier/-/prettier-2.8.1.tgz", + "integrity": "sha512-lqGoSJBQNJidqCHE80vqZJHWHRFoNYsSpP9AjFhlhi9ODCJA541svILes/+/1GM3VaL/abZi7cpFzOpdR9UPKg==", "dev": true, "bin": { "prettier": "bin-prettier.js" @@ -21620,9 +21620,9 @@ "integrity": "sha512-ravE6m9Atw9Z/jjttRUZ+clIXogdghyZAuWJ3qEzjT+jI/dL1ifAqhZeC5VHzQp1MSt1+jxKkFNemj/iO7tVUA==" }, "prettier": { - "version": "2.8.0", - "resolved": "https://registry.npmjs.org/prettier/-/prettier-2.8.0.tgz", - "integrity": "sha512-9Lmg8hTFZKG0Asr/kW9Bp8tJjRVluO8EJQVfY2T7FMw9T5jy4I/Uvx0Rca/XWf50QQ1/SS48+6IJWnrb+2yemA==", + "version": "2.8.1", + "resolved": "https://registry.npmjs.org/prettier/-/prettier-2.8.1.tgz", + "integrity": "sha512-lqGoSJBQNJidqCHE80vqZJHWHRFoNYsSpP9AjFhlhi9ODCJA541svILes/+/1GM3VaL/abZi7cpFzOpdR9UPKg==", "dev": true }, "pretty-error": { diff --git a/website/package.json b/website/package.json index cc4ca1e8549..5d79a76c38f 100644 --- a/website/package.json +++ b/website/package.json @@ -55,7 +55,7 @@ "@typescript-eslint/eslint-plugin": "^5.47.1", "@typescript-eslint/parser": "^5.45.0", "dir-compare": "^4.0.0", - "prettier": "2.8.0", + "prettier": "2.8.1", "typescript": "^4.8.3" } } From b9a8210f2fccada96262645cebbdc34185c32a5a Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 4 Jan 2023 23:41:23 +0900 Subject: [PATCH 15/76] Bump json5 from 2.2.1 to 2.2.3 in /website (#3079) Bumps [json5](https://github.com/json5/json5) from 2.2.1 to 2.2.3. - [Release notes](https://github.com/json5/json5/releases) - [Changelog](https://github.com/json5/json5/blob/main/CHANGELOG.md) - [Commits](https://github.com/json5/json5/compare/v2.2.1...v2.2.3) --- updated-dependencies: - dependency-name: json5 dependency-type: indirect ... Signed-off-by: dependabot[bot] Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- website/package-lock.json | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/website/package-lock.json b/website/package-lock.json index cc21b66efbd..a587e5231b6 100644 --- a/website/package-lock.json +++ b/website/package-lock.json @@ -9028,9 +9028,9 @@ "peer": true }, "node_modules/json5": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/json5/-/json5-2.2.1.tgz", - "integrity": "sha512-1hqLFMSrGHRHxav9q9gNjJ5EXznIxGVO09xQRrwplcS8qs28pZ8s8hupZAmqDwZUmVZ2Qb2jnyPOWcDH8m8dlA==", + "version": "2.2.3", + "resolved": "https://registry.npmjs.org/json5/-/json5-2.2.3.tgz", + "integrity": "sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg==", "bin": { "json5": "lib/cli.js" }, @@ -20421,9 +20421,9 @@ "peer": true }, "json5": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/json5/-/json5-2.2.1.tgz", - "integrity": "sha512-1hqLFMSrGHRHxav9q9gNjJ5EXznIxGVO09xQRrwplcS8qs28pZ8s8hupZAmqDwZUmVZ2Qb2jnyPOWcDH8m8dlA==" + "version": "2.2.3", + "resolved": "https://registry.npmjs.org/json5/-/json5-2.2.3.tgz", + "integrity": "sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg==" }, "jsonfile": { "version": "6.1.0", From cc914b77a3d41768c4ff7c8c27613ae70bd081cf Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 4 Jan 2023 23:42:34 +0900 Subject: [PATCH 16/76] Bump actions/setup-node from 1 to 3 (#3076) Bumps [actions/setup-node](https://github.com/actions/setup-node) from 1 to 3. - [Release notes](https://github.com/actions/setup-node/releases) - [Commits](https://github.com/actions/setup-node/compare/v1...v3) --- updated-dependencies: - dependency-name: actions/setup-node dependency-type: direct:production update-type: version-update:semver-major ... Signed-off-by: dependabot[bot] Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- .github/workflows/benchmark.yml | 2 +- .github/workflows/build-website.yml | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/benchmark.yml b/.github/workflows/benchmark.yml index 11e1fcb52d4..d50cb0d4101 100644 --- a/.github/workflows/benchmark.yml +++ b/.github/workflows/benchmark.yml @@ -43,7 +43,7 @@ jobs: version: "latest" - name: Setup Node - uses: actions/setup-node@v1 + uses: actions/setup-node@v3 with: node-version: 16 diff --git a/.github/workflows/build-website.yml b/.github/workflows/build-website.yml index 821791b0644..1069ca21bb5 100644 --- a/.github/workflows/build-website.yml +++ b/.github/workflows/build-website.yml @@ -23,7 +23,7 @@ jobs: - uses: actions/checkout@v2 - name: Setup node - uses: actions/setup-node@v1 + uses: actions/setup-node@v3 with: node-version: "16" From e65ee6059989d065004f951728cc0702f68716bb Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 4 Jan 2023 23:43:22 +0900 Subject: [PATCH 17/76] Bump JamesSingleton/is-organization-member from 1.0.0 to 1.0.1 (#3075) Bumps [JamesSingleton/is-organization-member](https://github.com/JamesSingleton/is-organization-member) from 1.0.0 to 1.0.1. - [Release notes](https://github.com/JamesSingleton/is-organization-member/releases) - [Commits](https://github.com/JamesSingleton/is-organization-member/compare/1.0.0...1.0.1) --- updated-dependencies: - dependency-name: JamesSingleton/is-organization-member dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- .github/workflows/auto-approve-maintainer-pr.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/auto-approve-maintainer-pr.yml b/.github/workflows/auto-approve-maintainer-pr.yml index db78ebf87bc..6aeb1ad6f98 100644 --- a/.github/workflows/auto-approve-maintainer-pr.yml +++ b/.github/workflows/auto-approve-maintainer-pr.yml @@ -9,7 +9,7 @@ jobs: steps: - name: Check if organization member id: is_organization_member - uses: JamesSingleton/is-organization-member@1.0.0 + uses: JamesSingleton/is-organization-member@1.0.1 with: organization: "yewstack" username: ${{ github.actor }} From d4c2f03c3d41a6ae3b3d80e3b91b509263cb68b1 Mon Sep 17 00:00:00 2001 From: Cecile Tonglet Date: Thu, 5 Jan 2023 11:30:05 +0100 Subject: [PATCH 18/76] Add method map() on Children to wrap easily (#3039) --- packages/yew/src/html/component/children.rs | 41 ++++++++++++++++++++- packages/yew/src/utils/mod.rs | 9 +++++ 2 files changed, 48 insertions(+), 2 deletions(-) diff --git a/packages/yew/src/html/component/children.rs b/packages/yew/src/html/component/children.rs index efd2149b6d9..911cd91fa92 100644 --- a/packages/yew/src/html/component/children.rs +++ b/packages/yew/src/html/component/children.rs @@ -3,7 +3,7 @@ use std::fmt; use crate::html::Html; -use crate::virtual_dom::{VChild, VNode}; +use crate::virtual_dom::VChild; use crate::Properties; /// A type used for accepting children elements in Component::Properties. @@ -163,7 +163,7 @@ impl PartialEq for ChildrenRenderer { impl ChildrenRenderer where - T: Clone + Into, + T: Clone, { /// Create children pub fn new(children: Vec) -> Self { @@ -186,6 +186,28 @@ where // This way `self.iter().next()` only has to clone a single node. self.children.iter().cloned() } + + /// Convert the children elements to another object (if there are any). + /// + /// ``` + /// # let children = Children::new(Vec::new()); + /// # use yew::{classes, html, Children}; + /// children.map(|children| { + /// html! { + ///
+ /// {children} + ///
+ /// } + /// }) + /// # ; + /// ``` + pub fn map(&self, closure: impl FnOnce(&Self) -> OUT) -> OUT { + if self.is_empty() { + Default::default() + } else { + closure(self) + } + } } impl Default for ChildrenRenderer { @@ -218,3 +240,18 @@ pub struct ChildrenProps { #[prop_or_default] pub children: Children, } + +#[cfg(test)] +mod tests { + use super::*; + + #[test] + fn children_map() { + let children = Children::new(vec![]); + let res = children.map(|children| Some(children.clone())); + assert!(res.is_none()); + let children = Children::new(vec![Default::default()]); + let res = children.map(|children| Some(children.clone())); + assert!(res.is_some()); + } +} diff --git a/packages/yew/src/utils/mod.rs b/packages/yew/src/utils/mod.rs index 2091349ec11..56926bfb637 100644 --- a/packages/yew/src/utils/mod.rs +++ b/packages/yew/src/utils/mod.rs @@ -50,6 +50,15 @@ impl, OUT> From> for NodeSeq { } } +impl + Clone, OUT> From<&ChildrenRenderer> for NodeSeq { + fn from(val: &ChildrenRenderer) -> Self { + Self( + val.iter().map(|x| x.into()).collect(), + PhantomData::default(), + ) + } +} + impl IntoIterator for NodeSeq { type IntoIter = std::vec::IntoIter; type Item = OUT; From ec4eca4fcb50b0fb672dcbc8fc0988abf5dde789 Mon Sep 17 00:00:00 2001 From: Brian Donovan <1938+eventualbuddha@users.noreply.github.com> Date: Sun, 8 Jan 2023 06:03:04 -0800 Subject: [PATCH 19/76] docs: fix markdown link in the debugging section (#3081) * docs: fix markdown link It was missing the closing parenthesis. * docs: fix markdown link It was missing the closing parenthesis. --- website/docs/more/debugging.mdx | 2 +- website/versioned_docs/version-0.20/more/debugging.mdx | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/website/docs/more/debugging.mdx b/website/docs/more/debugging.mdx index 0224d2dd1c9..cf15776aa99 100644 --- a/website/docs/more/debugging.mdx +++ b/website/docs/more/debugging.mdx @@ -43,7 +43,7 @@ fn main() { ### [`tracing-web`](https://crates.io/crates/tracing-web) -`tracing-web` can be used with [`tracing-subscriber`](https://crates.io/crates/tracing-subscriber to output messages to the browser console. +`tracing-web` can be used with [`tracing-subscriber`](https://crates.io/crates/tracing-subscriber) to output messages to the browser console. ```rust, ignore use tracing_subscriber::{ diff --git a/website/versioned_docs/version-0.20/more/debugging.mdx b/website/versioned_docs/version-0.20/more/debugging.mdx index 0224d2dd1c9..cf15776aa99 100644 --- a/website/versioned_docs/version-0.20/more/debugging.mdx +++ b/website/versioned_docs/version-0.20/more/debugging.mdx @@ -43,7 +43,7 @@ fn main() { ### [`tracing-web`](https://crates.io/crates/tracing-web) -`tracing-web` can be used with [`tracing-subscriber`](https://crates.io/crates/tracing-subscriber to output messages to the browser console. +`tracing-web` can be used with [`tracing-subscriber`](https://crates.io/crates/tracing-subscriber) to output messages to the browser console. ```rust, ignore use tracing_subscriber::{ From b55be12d3c852a652d906b5883726f63dcc4f752 Mon Sep 17 00:00:00 2001 From: Kaede Hoshikawa Date: Sun, 8 Jan 2023 23:09:49 +0900 Subject: [PATCH 20/76] Prefer pop_first if it is available (#3084) --- packages/yew/src/scheduler.rs | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/packages/yew/src/scheduler.rs b/packages/yew/src/scheduler.rs index c7f37dbca09..6f9113bf346 100644 --- a/packages/yew/src/scheduler.rs +++ b/packages/yew/src/scheduler.rs @@ -46,12 +46,20 @@ impl TopologicalQueue { } /// Take a single entry, preferring parents over children + #[rustversion::before(1.66)] fn pop_topmost(&mut self) -> Option { - // To be replaced with BTreeMap::pop_first once it is stable. + // BTreeMap::pop_first is available after 1.66. let key = *self.inner.keys().next()?; self.inner.remove(&key) } + /// Take a single entry, preferring parents over children + #[rustversion::since(1.66)] + #[inline] + fn pop_topmost(&mut self) -> Option { + self.inner.pop_first().map(|(_, v)| v) + } + /// Drain all entries, such that children are queued before parents fn drain_post_order_into(&mut self, queue: &mut Vec) { if self.inner.is_empty() { From 30a05fcf07167698a69c14ff7afe7af379c5d55e Mon Sep 17 00:00:00 2001 From: finga Date: Mon, 9 Jan 2023 14:41:33 +0100 Subject: [PATCH 21/76] docs: Fix router documentation (#3078) Fix passing the route instead of borrowing it as it results in an error. Co-authored-by: finga --- website/docs/concepts/router.mdx | 2 +- website/versioned_docs/version-0.20/concepts/router.mdx | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/website/docs/concepts/router.mdx b/website/docs/concepts/router.mdx index 3569d31e181..574cbcb1630 100644 --- a/website/docs/concepts/router.mdx +++ b/website/docs/concepts/router.mdx @@ -120,7 +120,7 @@ enum Route { Misc { path: String }, } -fn switch(route: &Route) -> Html { +fn switch(route: Route) -> Html { match route { Route::Home => html! {

{ "Home" }

}, Route::Post { id } => html! {

{format!("You are looking at Post {}", id)}

}, diff --git a/website/versioned_docs/version-0.20/concepts/router.mdx b/website/versioned_docs/version-0.20/concepts/router.mdx index 43bfafc0af6..95c18cc790d 100644 --- a/website/versioned_docs/version-0.20/concepts/router.mdx +++ b/website/versioned_docs/version-0.20/concepts/router.mdx @@ -120,7 +120,7 @@ enum Route { Misc { path: String }, } -fn switch(route: &Route) -> Html { +fn switch(route: Route) -> Html { match route { Route::Home => html! {

{ "Home" }

}, Route::Post { id } => html! {

{format!("You are looking at Post {}", id)}

}, From c5ffe601f2822c5e2a4fcd08aa502c7f63775354 Mon Sep 17 00:00:00 2001 From: WorldSEnder Date: Mon, 9 Jan 2023 14:08:08 +0000 Subject: [PATCH 22/76] Implement an internal DomSlot for positioning instead of NodeRef (#3048) use instead of NodeRef, decoupling the two fixes #3043 * implement internal DomSlot * move DomSlot into submodule of dom_bundle * hide behind feature csr * add test cases * write get in continuation style, this saves a clone * private DomSlot::get --- packages/yew/src/app_handle.rs | 15 +- packages/yew/src/dom_bundle/bcomp.rs | 70 +++-- packages/yew/src/dom_bundle/blist.rs | 120 ++++----- packages/yew/src/dom_bundle/bnode.rs | 132 ++++------ packages/yew/src/dom_bundle/bportal.rs | 60 ++--- packages/yew/src/dom_bundle/braw.rs | 135 ++++------ packages/yew/src/dom_bundle/bsuspense.rs | 87 +++---- packages/yew/src/dom_bundle/btag/mod.rs | 106 ++++---- packages/yew/src/dom_bundle/btext.rs | 100 ++++---- packages/yew/src/dom_bundle/fragment.rs | 38 +-- packages/yew/src/dom_bundle/mod.rs | 24 +- packages/yew/src/dom_bundle/position.rs | 256 +++++++++++++++++++ packages/yew/src/dom_bundle/traits.rs | 34 +-- packages/yew/src/dom_bundle/utils.rs | 36 +-- packages/yew/src/html/component/lifecycle.rs | 117 ++++----- packages/yew/src/html/component/scope.rs | 54 ++-- packages/yew/src/html/mod.rs | 70 +---- packages/yew/src/tests/layout_tests.rs | 25 +- packages/yew/src/virtual_dom/vcomp.rs | 28 +- packages/yew/src/virtual_dom/vportal.rs | 4 +- 20 files changed, 759 insertions(+), 752 deletions(-) create mode 100644 packages/yew/src/dom_bundle/position.rs diff --git a/packages/yew/src/app_handle.rs b/packages/yew/src/app_handle.rs index 4b407ee9146..577d34165c7 100644 --- a/packages/yew/src/app_handle.rs +++ b/packages/yew/src/app_handle.rs @@ -5,11 +5,10 @@ use std::rc::Rc; use web_sys::Element; -use crate::dom_bundle::BSubtree; -use crate::html::{BaseComponent, NodeRef, Scope, Scoped}; +use crate::dom_bundle::{BSubtree, DomSlot, DynamicDomSlot}; +use crate::html::{BaseComponent, Scope, Scoped}; /// An instance of an application. -#[cfg(feature = "csr")] #[derive(Debug)] pub struct AppHandle { /// `Scope` holder @@ -38,8 +37,8 @@ where app.scope.mount_in_place( hosting_root, host, - NodeRef::default(), - NodeRef::default(), + DomSlot::at_end(), + DynamicDomSlot::new_debug_trapped(), props, ); @@ -58,7 +57,7 @@ where skip_all, )] pub fn update(&mut self, new_props: COMP::Properties) { - self.scope.reuse(Rc::new(new_props), NodeRef::default()) + self.scope.reuse(Rc::new(new_props), DomSlot::at_end()) } /// Schedule the app for destruction @@ -115,11 +114,11 @@ mod feat_hydration { hosting_root, host.clone(), &mut fragment, - NodeRef::default(), + DynamicDomSlot::new_debug_trapped(), Rc::clone(&props), ); #[cfg(debug_assertions)] // Fix trapped next_sibling at the root - app.scope.reuse(props, NodeRef::default()); + app.scope.reuse(props, DomSlot::at_end()); // We remove all remaining nodes, this mimics the clear_element behaviour in // mount_with_props. diff --git a/packages/yew/src/dom_bundle/bcomp.rs b/packages/yew/src/dom_bundle/bcomp.rs index f9a406bfa2c..5e6130f5497 100644 --- a/packages/yew/src/dom_bundle/bcomp.rs +++ b/packages/yew/src/dom_bundle/bcomp.rs @@ -6,18 +6,17 @@ use std::fmt; use web_sys::Element; -use super::{BNode, BSubtree, Reconcilable, ReconcileTarget}; +use super::{BNode, BSubtree, DomSlot, DynamicDomSlot, Reconcilable, ReconcileTarget}; use crate::html::{AnyScope, Scoped}; use crate::virtual_dom::{Key, VComp}; -use crate::NodeRef; /// A virtual component. Compare with [VComp]. pub(super) struct BComp { type_id: TypeId, scope: Box, - // A internal NodeRef passed around to track this components position. This - // is "stable", i.e. does not change when reconciled. - internal_ref: NodeRef, + /// An internal [`DomSlot`] passed around to track this components position. This + /// will dynamically adjust when a lifecycle changes the render state of this component. + own_position: DynamicDomSlot, key: Option, } @@ -41,10 +40,10 @@ impl ReconcileTarget for BComp { self.scope.destroy_boxed(parent_to_detach); } - fn shift(&self, next_parent: &Element, next_sibling: NodeRef) -> NodeRef { - self.scope.shift_node(next_parent.clone(), next_sibling); + fn shift(&self, next_parent: &Element, slot: DomSlot) -> DomSlot { + self.scope.shift_node(next_parent.clone(), slot); - self.internal_ref.clone() + self.own_position.to_position() } } @@ -56,29 +55,29 @@ impl Reconcilable for VComp { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, - ) -> (NodeRef, Self::Bundle) { + slot: DomSlot, + ) -> (DomSlot, Self::Bundle) { let VComp { type_id, mountable, key, .. } = self; - let internal_ref = NodeRef::default(); + let internal_ref = DynamicDomSlot::new_debug_trapped(); let scope = mountable.mount( root, parent_scope, parent.to_owned(), + slot, internal_ref.clone(), - next_sibling, ); ( - internal_ref.clone(), + internal_ref.to_position(), BComp { type_id, - internal_ref, + own_position: internal_ref, key, scope, }, @@ -90,17 +89,17 @@ impl Reconcilable for VComp { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, + slot: DomSlot, bundle: &mut BNode, - ) -> NodeRef { + ) -> DomSlot { match bundle { // If the existing bundle is the same type, reuse it and update its properties BNode::Comp(ref mut bcomp) if self.type_id == bcomp.type_id && self.key == bcomp.key => { - self.reconcile(root, parent_scope, parent, next_sibling, bcomp) + self.reconcile(root, parent_scope, parent, slot, bcomp) } - _ => self.replace(root, parent_scope, parent, next_sibling, bundle), + _ => self.replace(root, parent_scope, parent, slot, bundle), } } @@ -109,14 +108,14 @@ impl Reconcilable for VComp { _root: &BSubtree, _parent_scope: &AnyScope, _parent: &Element, - next_sibling: NodeRef, + slot: DomSlot, bcomp: &mut Self::Bundle, - ) -> NodeRef { + ) -> DomSlot { let VComp { mountable, key, .. } = self; bcomp.key = key; - mountable.reuse(bcomp.scope.borrow(), next_sibling); - bcomp.internal_ref.clone() + mountable.reuse(bcomp.scope.borrow(), slot); + bcomp.own_position.to_position() } } @@ -132,14 +131,14 @@ mod feat_hydration { parent_scope: &AnyScope, parent: &Element, fragment: &mut Fragment, - ) -> (NodeRef, Self::Bundle) { + ) -> Self::Bundle { let VComp { type_id, mountable, key, .. } = self; - let internal_ref = NodeRef::default(); + let internal_ref = DynamicDomSlot::new_debug_trapped(); let scoped = mountable.hydrate( root.clone(), @@ -149,15 +148,12 @@ mod feat_hydration { fragment, ); - ( - internal_ref.clone(), - BComp { - type_id, - scope: scoped, - internal_ref, - key, - }, - ) + BComp { + type_id, + scope: scoped, + own_position: internal_ref, + key, + } } } } @@ -172,7 +168,7 @@ mod tests { use super::*; use crate::dom_bundle::Reconcilable; use crate::virtual_dom::{Key, VChild, VNode}; - use crate::{html, scheduler, Children, Component, Context, Html, NodeRef, Properties}; + use crate::{html, scheduler, Children, Component, Context, Html, Properties}; wasm_bindgen_test_configure!(run_in_browser); @@ -208,12 +204,12 @@ mod tests { let (root, scope, parent) = setup_parent(); let comp = html! { }; - let (_, mut bundle) = comp.attach(&root, &scope, &parent, NodeRef::default()); + let (_, mut bundle) = comp.attach(&root, &scope, &parent, DomSlot::at_end()); scheduler::start_now(); for _ in 0..10000 { let node = html! { }; - node.reconcile_node(&root, &scope, &parent, NodeRef::default(), &mut bundle); + node.reconcile_node(&root, &scope, &parent, DomSlot::at_end(), &mut bundle); scheduler::start_now(); } } @@ -344,7 +340,7 @@ mod tests { // clear parent parent.set_inner_html(""); - node.attach(root, scope, parent, NodeRef::default()); + node.attach(root, scope, parent, DomSlot::at_end()); scheduler::start_now(); parent.inner_html() } diff --git a/packages/yew/src/dom_bundle/blist.rs b/packages/yew/src/dom_bundle/blist.rs index 40908699571..4575b848aaa 100644 --- a/packages/yew/src/dom_bundle/blist.rs +++ b/packages/yew/src/dom_bundle/blist.rs @@ -7,9 +7,9 @@ use std::ops::Deref; use web_sys::Element; -use super::{test_log, BNode, BSubtree}; +use super::{test_log, BNode, BSubtree, DomSlot}; use crate::dom_bundle::{Reconcilable, ReconcileTarget}; -use crate::html::{AnyScope, NodeRef}; +use crate::html::AnyScope; use crate::virtual_dom::{Key, VList, VNode, VText}; /// This struct represents a mounted [VList] @@ -36,7 +36,7 @@ struct NodeWriter<'s> { root: &'s BSubtree, parent_scope: &'s AnyScope, parent: &'s Element, - next_sibling: NodeRef, + slot: DomSlot, } impl<'s> NodeWriter<'s> { @@ -44,48 +44,33 @@ impl<'s> NodeWriter<'s> { fn add(self, node: VNode) -> (Self, BNode) { test_log!("adding: {:?}", node); test_log!( - " parent={:?}, next_sibling={:?}", + " parent={:?}, slot={:?}", self.parent.outer_html(), - self.next_sibling + self.slot ); - let (next, bundle) = - node.attach(self.root, self.parent_scope, self.parent, self.next_sibling); - test_log!(" next_position: {:?}", next); - ( - Self { - next_sibling: next, - ..self - }, - bundle, - ) + let (next, bundle) = node.attach(self.root, self.parent_scope, self.parent, self.slot); + test_log!(" next_slot: {:?}", next); + (Self { slot: next, ..self }, bundle) } /// Shift a bundle into place without patching it fn shift(&self, bundle: &mut BNode) { - bundle.shift(self.parent, self.next_sibling.clone()); + bundle.shift(self.parent, self.slot.clone()); } /// Patch a bundle with a new node fn patch(self, node: VNode, bundle: &mut BNode) -> Self { test_log!("patching: {:?} -> {:?}", bundle, node); test_log!( - " parent={:?}, next_sibling={:?}", + " parent={:?}, slot={:?}", self.parent.outer_html(), - self.next_sibling + self.slot ); // Advance the next sibling reference (from right to left) - let next = node.reconcile_node( - self.root, - self.parent_scope, - self.parent, - self.next_sibling, - bundle, - ); + let next = + node.reconcile_node(self.root, self.parent_scope, self.parent, self.slot, bundle); test_log!(" next_position: {:?}", next); - Self { - next_sibling: next, - ..self - } + Self { slot: next, ..self } } } /// Helper struct implementing [Eq] and [Hash] by only looking at a node's key @@ -148,15 +133,15 @@ impl BList { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, + slot: DomSlot, lefts: Vec, rights: &mut Vec, - ) -> NodeRef { + ) -> DomSlot { let mut writer = NodeWriter { root, parent_scope, parent, - next_sibling, + slot, }; // Remove extra nodes @@ -178,7 +163,7 @@ impl BList { rights.push(el); writer = next_writer; } - writer.next_sibling + writer.slot } /// Diff and patch fully keyed child lists. @@ -189,10 +174,10 @@ impl BList { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, + slot: DomSlot, left_vdoms: Vec, rev_bundles: &mut Vec, - ) -> NodeRef { + ) -> DomSlot { macro_rules! key { ($v:expr) => { $v.key().expect("unkeyed child in fully keyed list") @@ -216,14 +201,7 @@ impl BList { // Corresponds to adding or removing items from the back of the list if matching_len_end == std::cmp::min(left_vdoms.len(), rev_bundles.len()) { // No key changes - return Self::apply_unkeyed( - root, - parent_scope, - parent, - next_sibling, - left_vdoms, - rev_bundles, - ); + return Self::apply_unkeyed(root, parent_scope, parent, slot, left_vdoms, rev_bundles); } // We partially drain the new vnodes in several steps. @@ -232,7 +210,7 @@ impl BList { root, parent_scope, parent, - next_sibling, + slot, }; // Step 1. Diff matching children at the end let lefts_to = lefts.len() - matching_len_end; @@ -369,7 +347,7 @@ impl BList { writer = writer.patch(l, r); } - writer.next_sibling + writer.slot } } @@ -380,14 +358,12 @@ impl ReconcileTarget for BList { } } - fn shift(&self, next_parent: &Element, next_sibling: NodeRef) -> NodeRef { - let mut next_sibling = next_sibling; - + fn shift(&self, next_parent: &Element, mut slot: DomSlot) -> DomSlot { for node in self.rev_children.iter() { - next_sibling = node.shift(next_parent, next_sibling.clone()); + slot = node.shift(next_parent, slot); } - next_sibling + slot } } @@ -399,10 +375,10 @@ impl Reconcilable for VList { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, - ) -> (NodeRef, Self::Bundle) { + slot: DomSlot, + ) -> (DomSlot, Self::Bundle) { let mut self_ = BList::new(); - let node_ref = self.reconcile(root, parent_scope, parent, next_sibling, &mut self_); + let node_ref = self.reconcile(root, parent_scope, parent, slot, &mut self_); (node_ref, self_) } @@ -411,13 +387,13 @@ impl Reconcilable for VList { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, + slot: DomSlot, bundle: &mut BNode, - ) -> NodeRef { + ) -> DomSlot { // 'Forcefully' pretend the existing node is a list. Creates a // singleton list if it isn't already. let blist = bundle.make_list(); - self.reconcile(root, parent_scope, parent, next_sibling, blist) + self.reconcile(root, parent_scope, parent, slot, blist) } fn reconcile( @@ -425,9 +401,9 @@ impl Reconcilable for VList { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, + slot: DomSlot, blist: &mut BList, - ) -> NodeRef { + ) -> DomSlot { // Here, we will try to diff the previous list elements with the new // ones we want to insert. For that, we will use two lists: // - lefts: new elements to render in the DOM @@ -454,9 +430,9 @@ impl Reconcilable for VList { rights.reserve_exact(additional); } let first = if fully_keyed && blist.fully_keyed { - BList::apply_keyed(root, parent_scope, parent, next_sibling, lefts, rights) + BList::apply_keyed(root, parent_scope, parent, slot, lefts, rights) } else { - BList::apply_unkeyed(root, parent_scope, parent, next_sibling, lefts, rights) + BList::apply_unkeyed(root, parent_scope, parent, slot, lefts, rights) }; blist.fully_keyed = fully_keyed; blist.key = self.key; @@ -477,32 +453,24 @@ mod feat_hydration { parent_scope: &AnyScope, parent: &Element, fragment: &mut Fragment, - ) -> (NodeRef, Self::Bundle) { - let node_ref = NodeRef::default(); + ) -> Self::Bundle { let fully_keyed = self.fully_keyed(); let vchildren = self.children; let mut children = Vec::with_capacity(vchildren.len()); - for (index, child) in vchildren.into_iter().enumerate() { - let (child_node_ref, child) = child.hydrate(root, parent_scope, parent, fragment); - - if index == 0 { - node_ref.link(child_node_ref); - } + for child in vchildren.into_iter() { + let child = child.hydrate(root, parent_scope, parent, fragment); children.push(child); } children.reverse(); - ( - node_ref, - BList { - rev_children: children, - fully_keyed, - key: self.key, - }, - ) + BList { + rev_children: children, + fully_keyed, + key: self.key, + } } } } diff --git a/packages/yew/src/dom_bundle/bnode.rs b/packages/yew/src/dom_bundle/bnode.rs index 616832af0a4..6646cf78f94 100644 --- a/packages/yew/src/dom_bundle/bnode.rs +++ b/packages/yew/src/dom_bundle/bnode.rs @@ -4,9 +4,9 @@ use std::fmt; use web_sys::{Element, Node}; -use super::{BComp, BList, BPortal, BRaw, BSubtree, BSuspense, BTag, BText}; +use super::{BComp, BList, BPortal, BRaw, BSubtree, BSuspense, BTag, BText, DomSlot}; use crate::dom_bundle::{Reconcilable, ReconcileTarget}; -use crate::html::{AnyScope, NodeRef}; +use crate::html::AnyScope; use crate::virtual_dom::{Key, VNode}; /// The bundle implementation to [VNode]. @@ -65,22 +65,20 @@ impl ReconcileTarget for BNode { } } - fn shift(&self, next_parent: &Element, next_sibling: NodeRef) -> NodeRef { + fn shift(&self, next_parent: &Element, slot: DomSlot) -> DomSlot { match self { - Self::Tag(ref vtag) => vtag.shift(next_parent, next_sibling), - Self::Text(ref btext) => btext.shift(next_parent, next_sibling), - Self::Comp(ref bsusp) => bsusp.shift(next_parent, next_sibling), - Self::List(ref vlist) => vlist.shift(next_parent, next_sibling), + Self::Tag(ref vtag) => vtag.shift(next_parent, slot), + Self::Text(ref btext) => btext.shift(next_parent, slot), + Self::Comp(ref bsusp) => bsusp.shift(next_parent, slot), + Self::List(ref vlist) => vlist.shift(next_parent, slot), Self::Ref(ref node) => { - next_parent - .insert_before(node, next_sibling.get().as_ref()) - .unwrap(); + slot.insert(next_parent, node); - NodeRef::new(node.clone()) + DomSlot::at(node.clone()) } - Self::Portal(ref vportal) => vportal.shift(next_parent, next_sibling), - Self::Suspense(ref vsuspense) => vsuspense.shift(next_parent, next_sibling), - Self::Raw(ref braw) => braw.shift(next_parent, next_sibling), + Self::Portal(ref vportal) => vportal.shift(next_parent, slot), + Self::Suspense(ref vsuspense) => vsuspense.shift(next_parent, slot), + Self::Raw(ref braw) => braw.shift(next_parent, slot), } } } @@ -93,40 +91,39 @@ impl Reconcilable for VNode { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, - ) -> (NodeRef, Self::Bundle) { + slot: DomSlot, + ) -> (DomSlot, Self::Bundle) { match self { VNode::VTag(vtag) => { - let (node_ref, tag) = vtag.attach(root, parent_scope, parent, next_sibling); + let (node_ref, tag) = vtag.attach(root, parent_scope, parent, slot); (node_ref, tag.into()) } VNode::VText(vtext) => { - let (node_ref, text) = vtext.attach(root, parent_scope, parent, next_sibling); + let (node_ref, text) = vtext.attach(root, parent_scope, parent, slot); (node_ref, text.into()) } VNode::VComp(vcomp) => { - let (node_ref, comp) = vcomp.attach(root, parent_scope, parent, next_sibling); + let (node_ref, comp) = vcomp.attach(root, parent_scope, parent, slot); (node_ref, comp.into()) } VNode::VList(vlist) => { - let (node_ref, list) = vlist.attach(root, parent_scope, parent, next_sibling); + let (node_ref, list) = vlist.attach(root, parent_scope, parent, slot); (node_ref, list.into()) } VNode::VRef(node) => { - super::insert_node(&node, parent, next_sibling.get().as_ref()); - (NodeRef::new(node.clone()), BNode::Ref(node)) + slot.insert(parent, &node); + (DomSlot::at(node.clone()), BNode::Ref(node)) } VNode::VPortal(vportal) => { - let (node_ref, portal) = vportal.attach(root, parent_scope, parent, next_sibling); + let (node_ref, portal) = vportal.attach(root, parent_scope, parent, slot); (node_ref, portal.into()) } VNode::VSuspense(vsuspsense) => { - let (node_ref, suspsense) = - vsuspsense.attach(root, parent_scope, parent, next_sibling); + let (node_ref, suspsense) = vsuspsense.attach(root, parent_scope, parent, slot); (node_ref, suspsense.into()) } VNode::VRaw(vraw) => { - let (node_ref, raw) = vraw.attach(root, parent_scope, parent, next_sibling); + let (node_ref, raw) = vraw.attach(root, parent_scope, parent, slot); (node_ref, raw.into()) } } @@ -137,10 +134,10 @@ impl Reconcilable for VNode { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, + slot: DomSlot, bundle: &mut BNode, - ) -> NodeRef { - self.reconcile(root, parent_scope, parent, next_sibling, bundle) + ) -> DomSlot { + self.reconcile(root, parent_scope, parent, slot, bundle) } fn reconcile( @@ -148,46 +145,25 @@ impl Reconcilable for VNode { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, + slot: DomSlot, bundle: &mut BNode, - ) -> NodeRef { + ) -> DomSlot { match self { - VNode::VTag(vtag) => { - vtag.reconcile_node(root, parent_scope, parent, next_sibling, bundle) - } - VNode::VText(vtext) => { - vtext.reconcile_node(root, parent_scope, parent, next_sibling, bundle) - } - VNode::VComp(vcomp) => { - vcomp.reconcile_node(root, parent_scope, parent, next_sibling, bundle) - } - VNode::VList(vlist) => { - vlist.reconcile_node(root, parent_scope, parent, next_sibling, bundle) - } - VNode::VRef(node) => { - let _existing = match bundle { - BNode::Ref(ref n) if &node == n => n, - _ => { - return VNode::VRef(node).replace( - root, - parent_scope, - parent, - next_sibling, - bundle, - ); - } - }; - NodeRef::new(node) - } + VNode::VTag(vtag) => vtag.reconcile_node(root, parent_scope, parent, slot, bundle), + VNode::VText(vtext) => vtext.reconcile_node(root, parent_scope, parent, slot, bundle), + VNode::VComp(vcomp) => vcomp.reconcile_node(root, parent_scope, parent, slot, bundle), + VNode::VList(vlist) => vlist.reconcile_node(root, parent_scope, parent, slot, bundle), + VNode::VRef(node) => match bundle { + BNode::Ref(ref n) if &node == n => DomSlot::at(node), + _ => VNode::VRef(node).replace(root, parent_scope, parent, slot, bundle), + }, VNode::VPortal(vportal) => { - vportal.reconcile_node(root, parent_scope, parent, next_sibling, bundle) + vportal.reconcile_node(root, parent_scope, parent, slot, bundle) } VNode::VSuspense(vsuspsense) => { - vsuspsense.reconcile_node(root, parent_scope, parent, next_sibling, bundle) - } - VNode::VRaw(vraw) => { - vraw.reconcile_node(root, parent_scope, parent, next_sibling, bundle) + vsuspsense.reconcile_node(root, parent_scope, parent, slot, bundle) } + VNode::VRaw(vraw) => vraw.reconcile_node(root, parent_scope, parent, slot, bundle), } } } @@ -268,24 +244,12 @@ mod feat_hydration { parent_scope: &AnyScope, parent: &Element, fragment: &mut Fragment, - ) -> (NodeRef, Self::Bundle) { + ) -> Self::Bundle { match self { - VNode::VTag(vtag) => { - let (node_ref, tag) = vtag.hydrate(root, parent_scope, parent, fragment); - (node_ref, tag.into()) - } - VNode::VText(vtext) => { - let (node_ref, text) = vtext.hydrate(root, parent_scope, parent, fragment); - (node_ref, text.into()) - } - VNode::VComp(vcomp) => { - let (node_ref, comp) = vcomp.hydrate(root, parent_scope, parent, fragment); - (node_ref, comp.into()) - } - VNode::VList(vlist) => { - let (node_ref, list) = vlist.hydrate(root, parent_scope, parent, fragment); - (node_ref, list.into()) - } + VNode::VTag(vtag) => vtag.hydrate(root, parent_scope, parent, fragment).into(), + VNode::VText(vtext) => vtext.hydrate(root, parent_scope, parent, fragment).into(), + VNode::VComp(vcomp) => vcomp.hydrate(root, parent_scope, parent, fragment).into(), + VNode::VList(vlist) => vlist.hydrate(root, parent_scope, parent, fragment).into(), // You cannot hydrate a VRef. VNode::VRef(_) => { panic!( @@ -300,11 +264,9 @@ mod feat_hydration { use_effect." ) } - VNode::VSuspense(vsuspense) => { - let (node_ref, suspense) = - vsuspense.hydrate(root, parent_scope, parent, fragment); - (node_ref, suspense.into()) - } + VNode::VSuspense(vsuspense) => vsuspense + .hydrate(root, parent_scope, parent, fragment) + .into(), VNode::VRaw(_) => { panic!("VRaw is not hydratable (raw HTML string cannot be hydrated)") } diff --git a/packages/yew/src/dom_bundle/bportal.rs b/packages/yew/src/dom_bundle/bportal.rs index 2fa79453f85..a7e5d76c9a0 100644 --- a/packages/yew/src/dom_bundle/bportal.rs +++ b/packages/yew/src/dom_bundle/bportal.rs @@ -1,10 +1,10 @@ //! This module contains the bundle implementation of a portal [BPortal]. -use web_sys::Element; +use web_sys::{Element, Node}; -use super::{test_log, BNode, BSubtree}; +use super::{test_log, BNode, BSubtree, DomSlot}; use crate::dom_bundle::{Reconcilable, ReconcileTarget}; -use crate::html::{AnyScope, NodeRef}; +use crate::html::AnyScope; use crate::virtual_dom::{Key, VPortal}; /// The bundle implementation to [VPortal]. @@ -15,7 +15,7 @@ pub struct BPortal { /// The element under which the content is inserted. host: Element, /// The next sibling after the inserted content - inner_sibling: NodeRef, + inner_sibling: Option, /// The inserted node node: Box, } @@ -26,10 +26,9 @@ impl ReconcileTarget for BPortal { self.node.detach(&self.inner_root, &self.host, false); } - fn shift(&self, _next_parent: &Element, next_sibling: NodeRef) -> NodeRef { - // portals have nothing in it's original place of DOM, we also do nothing. - - next_sibling + fn shift(&self, _next_parent: &Element, slot: DomSlot) -> DomSlot { + // portals have nothing in its original place of DOM, we also do nothing. + slot } } @@ -41,22 +40,18 @@ impl Reconcilable for VPortal { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - host_next_sibling: NodeRef, - ) -> (NodeRef, Self::Bundle) { + host_slot: DomSlot, + ) -> (DomSlot, Self::Bundle) { let Self { host, inner_sibling, node, } = self; - let inner_sibling = { - let sib_ref = NodeRef::default(); - sib_ref.set(inner_sibling); - sib_ref - }; + let inner_slot = DomSlot::create(inner_sibling.clone()); let inner_root = root.create_subroot(parent.clone(), &host); - let (_, inner) = node.attach(&inner_root, parent_scope, &host, inner_sibling.clone()); + let (_, inner) = node.attach(&inner_root, parent_scope, &host, inner_slot); ( - host_next_sibling, + host_slot, BPortal { inner_root, host, @@ -71,14 +66,12 @@ impl Reconcilable for VPortal { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, + slot: DomSlot, bundle: &mut BNode, - ) -> NodeRef { + ) -> DomSlot { match bundle { - BNode::Portal(portal) => { - self.reconcile(root, parent_scope, parent, next_sibling, portal) - } - _ => self.replace(root, parent_scope, parent, next_sibling, bundle), + BNode::Portal(portal) => self.reconcile(root, parent_scope, parent, slot, portal), + _ => self.replace(root, parent_scope, parent, slot, bundle), } } @@ -87,9 +80,9 @@ impl Reconcilable for VPortal { _root: &BSubtree, parent_scope: &AnyScope, _parent: &Element, - next_sibling: NodeRef, + host_slot: DomSlot, portal: &mut Self::Bundle, - ) -> NodeRef { + ) -> DomSlot { let Self { host, inner_sibling, @@ -98,23 +91,23 @@ impl Reconcilable for VPortal { let old_host = std::mem::replace(&mut portal.host, host); - let should_shift = old_host != portal.host || portal.inner_sibling.get() != inner_sibling; - portal.inner_sibling.set(inner_sibling); + let should_shift = old_host != portal.host || portal.inner_sibling != inner_sibling; + portal.inner_sibling = inner_sibling; + let inner_slot = DomSlot::create(portal.inner_sibling.clone()); if should_shift { // Remount the inner node somewhere else instead of diffing // Move the node, but keep the state - let inner_sibling = portal.inner_sibling.clone(); - portal.node.shift(&portal.host, inner_sibling); + portal.node.shift(&portal.host, inner_slot.clone()); } node.reconcile_node( &portal.inner_root, parent_scope, &portal.host, - portal.inner_sibling.clone(), + inner_slot, &mut portal.node, ); - next_sibling + host_slot } } @@ -136,6 +129,7 @@ mod layout_tests { use yew::virtual_dom::VPortal; use super::*; + use crate::html::NodeRef; use crate::tests::layout_tests::{diff_layouts, TestLayout}; use crate::virtual_dom::VNode; use crate::{create_portal, html}; @@ -252,13 +246,13 @@ mod layout_tests { ); let (_, mut bundle) = portal .clone() - .attach(&root, &scope, &parent, NodeRef::default()); + .attach(&root, &scope, &parent, DomSlot::at_end()); // Focus the input, then reconcile again let input_el = input_ref.cast::().unwrap(); input_el.focus().unwrap(); - let _ = portal.reconcile_node(&root, &scope, &parent, NodeRef::default(), &mut bundle); + let _ = portal.reconcile_node(&root, &scope, &parent, DomSlot::at_end(), &mut bundle); let new_input_el = input_ref.cast::().unwrap(); assert_eq!(input_el, new_input_el); diff --git a/packages/yew/src/dom_bundle/braw.rs b/packages/yew/src/dom_bundle/braw.rs index d0b3828e316..18452c885cd 100644 --- a/packages/yew/src/dom_bundle/braw.rs +++ b/packages/yew/src/dom_bundle/braw.rs @@ -1,26 +1,23 @@ use wasm_bindgen::JsCast; -use web_sys::Element; +use web_sys::{Element, Node}; -use crate::dom_bundle::bnode::BNode; -use crate::dom_bundle::traits::{Reconcilable, ReconcileTarget}; -use crate::dom_bundle::utils::insert_node; -use crate::dom_bundle::BSubtree; +use super::{BNode, BSubtree, DomSlot, Reconcilable, ReconcileTarget}; use crate::html::AnyScope; use crate::virtual_dom::VRaw; -use crate::{AttrValue, NodeRef}; +use crate::AttrValue; #[derive(Debug)] pub struct BRaw { - reference: NodeRef, + reference: Option, children_count: usize, html: AttrValue, } impl BRaw { - fn create_elements(html: &str) -> Vec { + fn create_elements(html: &str) -> Vec { let div = gloo::utils::document().create_element("div").unwrap(); div.set_inner_html(html); - let children = div.children(); + let children = div.child_nodes(); let children = js_sys::Array::from(&children); let children = children.to_vec(); children @@ -30,7 +27,7 @@ impl BRaw { } fn detach_bundle(&self, parent: &Element) { - let mut next_node = self.reference.get(); + let mut next_node = self.reference.clone(); for _ in 0..self.children_count { if let Some(node) = next_node { next_node = node.next_sibling(); @@ -38,6 +35,13 @@ impl BRaw { } } } + + fn position(&self, next_slot: DomSlot) -> DomSlot { + self.reference + .as_ref() + .map(|n| DomSlot::at(n.clone())) + .unwrap_or(next_slot) + } } impl ReconcileTarget for BRaw { @@ -45,29 +49,15 @@ impl ReconcileTarget for BRaw { self.detach_bundle(parent); } - fn shift(&self, next_parent: &Element, next_sibling: NodeRef) -> NodeRef { - let mut next_node = match self.reference.get() { - Some(n) => n, - None => return NodeRef::default(), - }; - let insert = |n| { - next_parent - .insert_before(&n, next_sibling.get().as_ref()) - .unwrap() - }; + fn shift(&self, next_parent: &Element, slot: DomSlot) -> DomSlot { + let mut next_node = self.reference.clone(); for _ in 0..self.children_count { - let current = next_node; - next_node = match current.next_sibling() { - Some(n) => n, - None => { - // if nothing is next, add whatever is the current node and return early - insert(current.clone()); - return NodeRef::new(current); - } - }; - insert(current); + if let Some(node) = next_node { + next_node = node.next_sibling(); + slot.insert(next_parent, &node); + } } - NodeRef::new(next_node) + self.position(slot) } } @@ -79,37 +69,24 @@ impl Reconcilable for VRaw { _root: &BSubtree, _parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, - ) -> (NodeRef, Self::Bundle) { + slot: DomSlot, + ) -> (DomSlot, Self::Bundle) { let elements = BRaw::create_elements(&self.html); - if elements.is_empty() { - return ( - next_sibling.clone(), - BRaw { - reference: next_sibling, - children_count: 0, - html: self.html, - }, - ); - } - let node_ref = NodeRef::default(); - let count = elements.len(); let mut iter = elements.into_iter(); - let first = iter.next().unwrap(); - insert_node(&first, parent, next_sibling.get().as_ref()); - node_ref.set(Some(first.into())); - for child in iter { - insert_node(&child, parent, next_sibling.get().as_ref()); + let reference = iter.next(); + if let Some(ref first) = reference { + slot.insert(parent, first); + for ref child in iter { + slot.insert(parent, child); + } } - ( - node_ref.clone(), - BRaw { - reference: node_ref, - children_count: count, - html: self.html, - }, - ) + let this = BRaw { + reference, + children_count: count, + html: self.html, + }; + (this.position(slot), this) } fn reconcile_node( @@ -117,13 +94,13 @@ impl Reconcilable for VRaw { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, + slot: DomSlot, bundle: &mut BNode, - ) -> NodeRef { + ) -> DomSlot { match bundle { - BNode::Raw(raw) if raw.html == self.html => raw.reference.clone(), - BNode::Raw(raw) => self.reconcile(root, parent_scope, parent, next_sibling, raw), - _ => self.replace(root, parent_scope, parent, next_sibling, bundle), + BNode::Raw(raw) if raw.html == self.html => raw.position(slot), + BNode::Raw(raw) => self.reconcile(root, parent_scope, parent, slot, raw), + _ => self.replace(root, parent_scope, parent, slot, bundle), } } @@ -132,18 +109,18 @@ impl Reconcilable for VRaw { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, + slot: DomSlot, bundle: &mut Self::Bundle, - ) -> NodeRef { + ) -> DomSlot { if self.html != bundle.html { // we don't have a way to diff what's changed in the string so we remove the node and // reattach it bundle.detach_bundle(parent); - let (node_ref, braw) = self.attach(root, parent_scope, parent, next_sibling); + let (node_ref, braw) = self.attach(root, parent_scope, parent, slot); *bundle = braw; node_ref } else { - bundle.reference.clone() + bundle.position(slot) } } } @@ -166,7 +143,7 @@ mod tests { const HTML: &str = "text"; let elem = VNode::from_html_unchecked(HTML.into()); - let (_, mut elem) = elem.attach(&root, &scope, &parent, NodeRef::default()); + let (_, mut elem) = elem.attach(&root, &scope, &parent, DomSlot::at_end()); assert_braw(&mut elem); assert_eq!(parent.inner_html(), HTML) } @@ -177,7 +154,7 @@ mod tests { const HTML: &str = ""; let elem = VNode::from_html_unchecked(HTML.into()); - let (_, mut elem) = elem.attach(&root, &scope, &parent, NodeRef::default()); + let (_, mut elem) = elem.attach(&root, &scope, &parent, DomSlot::at_end()); assert_braw(&mut elem); assert_eq!(parent.inner_html(), HTML) } @@ -189,7 +166,7 @@ mod tests { const HTML: &str = r#"

one link more paragraph

here
"#; let elem = VNode::from_html_unchecked(HTML.into()); - let (_, mut elem) = elem.attach(&root, &scope, &parent, NodeRef::default()); + let (_, mut elem) = elem.attach(&root, &scope, &parent, DomSlot::at_end()); assert_braw(&mut elem); assert_eq!(parent.inner_html(), HTML) } @@ -199,7 +176,7 @@ mod tests { const HTML: &str = r#"

paragraph

link"#; let elem = VNode::from_html_unchecked(HTML.into()); - let (_, mut elem) = elem.attach(&root, &scope, &parent, NodeRef::default()); + let (_, mut elem) = elem.attach(&root, &scope, &parent, DomSlot::at_end()); assert_braw(&mut elem); assert_eq!(parent.inner_html(), HTML) } @@ -210,7 +187,7 @@ mod tests { const HTML: &str = r#"

paragraph

link"#; let elem = VNode::from_html_unchecked(HTML.into()); - let (_, mut elem) = elem.attach(&root, &scope, &parent, NodeRef::default()); + let (_, mut elem) = elem.attach(&root, &scope, &parent, DomSlot::at_end()); assert_braw(&mut elem); assert_eq!(parent.inner_html(), HTML); elem.detach(&root, &parent, false); @@ -223,7 +200,7 @@ mod tests { const HTML: &str = r#"

paragraph

"#; let elem = VNode::from_html_unchecked(HTML.into()); - let (_, mut elem) = elem.attach(&root, &scope, &parent, NodeRef::default()); + let (_, mut elem) = elem.attach(&root, &scope, &parent, DomSlot::at_end()); assert_braw(&mut elem); assert_eq!(parent.inner_html(), HTML); elem.detach(&root, &parent, false); @@ -236,7 +213,7 @@ mod tests { const HTML: &str = ""; let elem = VNode::from_html_unchecked(HTML.into()); - let (_, mut elem) = elem.attach(&root, &scope, &parent, NodeRef::default()); + let (_, mut elem) = elem.attach(&root, &scope, &parent, DomSlot::at_end()); assert_braw(&mut elem); assert_eq!(parent.inner_html(), HTML); elem.detach(&root, &parent, false); @@ -332,14 +309,14 @@ mod tests { const HTML: &str = r#"

paragraph

"#; let elem = VNode::from_html_unchecked(HTML.into()); - let (_, mut elem) = elem.attach(&root, &scope, &parent, NodeRef::default()); + let (_, mut elem) = elem.attach(&root, &scope, &parent, DomSlot::at_end()); assert_braw(&mut elem); assert_eq!(parent.inner_html(), HTML); let new_parent = document().create_element("section").unwrap(); document().body().unwrap().append_child(&parent).unwrap(); - elem.shift(&new_parent, NodeRef::default()); + elem.shift(&new_parent, DomSlot::at_end()); assert_eq!(new_parent.inner_html(), HTML); assert_eq!(parent.inner_html(), ""); @@ -360,7 +337,7 @@ mod tests { let new_sibling = document().create_text_node(SIBLING_CONTENT); new_parent.append_child(&new_sibling).unwrap(); - let new_sibling_ref = NodeRef::new(new_sibling.into()); + let new_sibling_ref = DomSlot::at(new_sibling.into()); elem.shift(&new_parent, new_sibling_ref); @@ -378,14 +355,14 @@ mod tests { const HTML: &str = r#"

paragraph

link"#; let elem = VNode::from_html_unchecked(HTML.into()); - let (_, mut elem) = elem.attach(&root, &scope, &parent, NodeRef::default()); + let (_, mut elem) = elem.attach(&root, &scope, &parent, DomSlot::at_end()); assert_braw(&mut elem); assert_eq!(parent.inner_html(), HTML); let new_parent = document().create_element("section").unwrap(); document().body().unwrap().append_child(&parent).unwrap(); - elem.shift(&new_parent, NodeRef::default()); + elem.shift(&new_parent, DomSlot::at_end()); assert_eq!(parent.inner_html(), ""); assert_eq!(new_parent.inner_html(), HTML); diff --git a/packages/yew/src/dom_bundle/bsuspense.rs b/packages/yew/src/dom_bundle/bsuspense.rs index d9ecb216063..38bb3cf7bb0 100644 --- a/packages/yew/src/dom_bundle/bsuspense.rs +++ b/packages/yew/src/dom_bundle/bsuspense.rs @@ -5,10 +5,9 @@ use web_sys::Element; #[cfg(feature = "hydration")] use super::Fragment; -use super::{BNode, BSubtree, Reconcilable, ReconcileTarget}; +use super::{BNode, BSubtree, DomSlot, Reconcilable, ReconcileTarget}; use crate::html::AnyScope; use crate::virtual_dom::{Key, VSuspense}; -use crate::NodeRef; #[derive(Debug)] enum Fallback { @@ -60,12 +59,12 @@ impl ReconcileTarget for BSuspense { } } - fn shift(&self, next_parent: &Element, next_sibling: NodeRef) -> NodeRef { + fn shift(&self, next_parent: &Element, slot: DomSlot) -> DomSlot { match self.fallback.as_ref() { - Some(Fallback::Bundle(bundle)) => bundle.shift(next_parent, next_sibling), + Some(Fallback::Bundle(bundle)) => bundle.shift(next_parent, slot), #[cfg(feature = "hydration")] - Some(Fallback::Fragment(fragment)) => fragment.shift(next_parent, next_sibling), - None => self.children_bundle.shift(next_parent, next_sibling), + Some(Fallback::Fragment(fragment)) => fragment.shift(next_parent, slot), + None => self.children_bundle.shift(next_parent, slot), } } } @@ -78,8 +77,8 @@ impl Reconcilable for VSuspense { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, - ) -> (NodeRef, Self::Bundle) { + slot: DomSlot, + ) -> (DomSlot, Self::Bundle) { let VSuspense { children, fallback, @@ -94,9 +93,8 @@ impl Reconcilable for VSuspense { // tree while rendering fallback UI into the original place where children resides in. if suspended { let (_child_ref, children_bundle) = - children.attach(root, parent_scope, &detached_parent, NodeRef::default()); - let (fallback_ref, fallback) = - fallback.attach(root, parent_scope, parent, next_sibling); + children.attach(root, parent_scope, &detached_parent, DomSlot::at_end()); + let (fallback_ref, fallback) = fallback.attach(root, parent_scope, parent, slot); ( fallback_ref, BSuspense { @@ -107,8 +105,7 @@ impl Reconcilable for VSuspense { }, ) } else { - let (child_ref, children_bundle) = - children.attach(root, parent_scope, parent, next_sibling); + let (child_ref, children_bundle) = children.attach(root, parent_scope, parent, slot); ( child_ref, BSuspense { @@ -126,15 +123,15 @@ impl Reconcilable for VSuspense { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, + slot: DomSlot, bundle: &mut BNode, - ) -> NodeRef { + ) -> DomSlot { match bundle { // We only preserve the child state if they are the same suspense. BNode::Suspense(m) if m.key == self.key => { - self.reconcile(root, parent_scope, parent, next_sibling, m) + self.reconcile(root, parent_scope, parent, slot, m) } - _ => self.replace(root, parent_scope, parent, next_sibling, bundle), + _ => self.replace(root, parent_scope, parent, slot, bundle), } } @@ -143,9 +140,9 @@ impl Reconcilable for VSuspense { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, + slot: DomSlot, suspense: &mut Self::Bundle, - ) -> NodeRef { + ) -> DomSlot { let VSuspense { children, fallback: vfallback, @@ -165,41 +162,40 @@ impl Reconcilable for VSuspense { root, parent_scope, &suspense.detached_parent, - NodeRef::default(), + DomSlot::at_end(), children_bundle, ); match fallback { Fallback::Bundle(bundle) => { - vfallback.reconcile_node(root, parent_scope, parent, next_sibling, bundle) + vfallback.reconcile_node(root, parent_scope, parent, slot, bundle) } #[cfg(feature = "hydration")] Fallback::Fragment(fragment) => match fragment.front().cloned() { - Some(m) => NodeRef::new(m), - None => next_sibling, + Some(m) => DomSlot::at(m), + None => slot, }, } } // Not suspended, just reconcile the children into the DOM (false, None) => { - children.reconcile_node(root, parent_scope, parent, next_sibling, children_bundle) + children.reconcile_node(root, parent_scope, parent, slot, children_bundle) } // Freshly suspended. Shift children into the detached parent, then add fallback to the // DOM (true, None) => { - children_bundle.shift(&suspense.detached_parent, NodeRef::default()); + children_bundle.shift(&suspense.detached_parent, DomSlot::at_end()); children.reconcile_node( root, parent_scope, &suspense.detached_parent, - NodeRef::default(), + DomSlot::at_end(), children_bundle, ); // first render of fallback - let (fallback_ref, fallback) = - vfallback.attach(root, parent_scope, parent, next_sibling); + let (fallback_ref, fallback) = vfallback.attach(root, parent_scope, parent, slot); suspense.fallback = Some(Fallback::Bundle(fallback)); fallback_ref } @@ -218,8 +214,8 @@ impl Reconcilable for VSuspense { } }; - children_bundle.shift(parent, next_sibling.clone()); - children.reconcile_node(root, parent_scope, parent, next_sibling, children_bundle) + children_bundle.shift(parent, slot.clone()); + children.reconcile_node(root, parent_scope, parent, slot, children_bundle) } } } @@ -238,7 +234,7 @@ mod feat_hydration { parent_scope: &AnyScope, parent: &Element, fragment: &mut Fragment, - ) -> (NodeRef, Self::Bundle) { + ) -> Self::Bundle { let detached_parent = document() .create_element("div") .expect("failed to create detached element"); @@ -254,33 +250,24 @@ mod feat_hydration { // Even if initially suspended, these children correspond to the first non-suspended // content Refer to VSuspense::render_to_string - let (_, children_bundle) = + let children_bundle = self.children .hydrate(root, parent_scope, &detached_parent, &mut nodes); // We trim all leading text nodes before checking as it's likely these are whitespaces. - nodes.trim_start_text_nodes(&detached_parent); + nodes.trim_start_text_nodes(); assert!(nodes.is_empty(), "expected end of suspense, found node."); - let node_ref = fallback_fragment - .front() - .cloned() - .map(NodeRef::new) - .unwrap_or_default(); + BSuspense { + children_bundle, + detached_parent, + key: self.key, - ( - node_ref, - BSuspense { - children_bundle, - detached_parent, - key: self.key, - - // We start hydration with the BSuspense being suspended. - // A subsequent render will resume the BSuspense if not needed to be suspended. - fallback: Some(Fallback::Fragment(fallback_fragment)), - }, - ) + // We start hydration with the BSuspense being suspended. + // A subsequent render will resume the BSuspense if not needed to be suspended. + fallback: Some(Fallback::Fragment(fallback_fragment)), + } } } } diff --git a/packages/yew/src/dom_bundle/btag/mod.rs b/packages/yew/src/dom_bundle/btag/mod.rs index 87218d6f8d4..8bb4b51f97e 100644 --- a/packages/yew/src/dom_bundle/btag/mod.rs +++ b/packages/yew/src/dom_bundle/btag/mod.rs @@ -13,7 +13,7 @@ pub use listeners::Registry; use wasm_bindgen::JsCast; use web_sys::{Element, HtmlTextAreaElement as TextAreaElement}; -use super::{insert_node, BList, BNode, BSubtree, Reconcilable, ReconcileTarget}; +use super::{BList, BNode, BSubtree, DomSlot, Reconcilable, ReconcileTarget}; use crate::html::AnyScope; use crate::virtual_dom::vtag::{InputFields, VTagInner, Value, SVG_NAMESPACE}; use crate::virtual_dom::{Attributes, Key, VTag}; @@ -93,12 +93,10 @@ impl ReconcileTarget for BTag { } } - fn shift(&self, next_parent: &Element, next_sibling: NodeRef) -> NodeRef { - next_parent - .insert_before(&self.reference, next_sibling.get().as_ref()) - .unwrap(); + fn shift(&self, next_parent: &Element, slot: DomSlot) -> DomSlot { + slot.insert(next_parent, &self.reference); - self.node_ref.clone() + DomSlot::at(self.reference.clone().into()) } } @@ -110,8 +108,8 @@ impl Reconcilable for VTag { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, - ) -> (NodeRef, Self::Bundle) { + slot: DomSlot, + ) -> (DomSlot, Self::Bundle) { let el = self.create_element(parent); let Self { listeners, @@ -120,7 +118,7 @@ impl Reconcilable for VTag { key, .. } = self; - insert_node(&el, parent, next_sibling.get().as_ref()); + slot.insert(parent, &el); let attributes = attributes.apply(root, &el); let listeners = listeners.apply(root, &el); @@ -135,14 +133,13 @@ impl Reconcilable for VTag { BTagInner::Textarea { value } } VTagInner::Other { children, tag } => { - let (_, child_bundle) = - children.attach(root, parent_scope, &el, NodeRef::default()); + let (_, child_bundle) = children.attach(root, parent_scope, &el, DomSlot::at_end()); BTagInner::Other { child_bundle, tag } } }; node_ref.set(Some(el.clone().into())); ( - node_ref.clone(), + DomSlot::at(el.clone().into()), BTag { inner, listeners, @@ -159,9 +156,9 @@ impl Reconcilable for VTag { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, + slot: DomSlot, bundle: &mut BNode, - ) -> NodeRef { + ) -> DomSlot { // This kind of branching patching routine reduces branch predictor misses and the need to // unpack the enums (including `Option`s) all the time, resulting in a more streamlined // patching flow @@ -179,18 +176,12 @@ impl Reconcilable for VTag { } _ => false, } { - return self.reconcile( - root, - parent_scope, - parent, - next_sibling, - ex.deref_mut(), - ); + return self.reconcile(root, parent_scope, parent, slot, ex.deref_mut()); } } _ => {} }; - self.replace(root, parent_scope, parent, next_sibling, bundle) + self.replace(root, parent_scope, parent, slot, bundle) } fn reconcile( @@ -198,9 +189,9 @@ impl Reconcilable for VTag { root: &BSubtree, parent_scope: &AnyScope, _parent: &Element, - _next_sibling: NodeRef, + _slot: DomSlot, tag: &mut Self::Bundle, - ) -> NodeRef { + ) -> DomSlot { let el = &tag.reference; self.attributes.apply_diff(root, el, &mut tag.attributes); self.listeners.apply_diff(root, el, &mut tag.listeners); @@ -218,7 +209,7 @@ impl Reconcilable for VTag { child_bundle: old, .. }, ) => { - new.reconcile(root, parent_scope, el, NodeRef::default(), old); + new.reconcile(root, parent_scope, el, DomSlot::at_end(), old); } // Can not happen, because we checked for tag equability above _ => unsafe { unreachable_unchecked() }, @@ -234,7 +225,7 @@ impl Reconcilable for VTag { tag.node_ref.set(Some(el.clone().into())); } - tag.node_ref.clone() + DomSlot::at(el.clone().into()) } } @@ -302,9 +293,9 @@ mod feat_hydration { self, root: &BSubtree, parent_scope: &AnyScope, - parent: &Element, + _parent: &Element, fragment: &mut Fragment, - ) -> (NodeRef, Self::Bundle) { + ) -> Self::Bundle { let tag_name = self.tag().to_owned(); let Self { @@ -316,7 +307,7 @@ mod feat_hydration { } = self; // We trim all text nodes as it's likely these are whitespaces. - fragment.trim_start_text_nodes(parent); + fragment.trim_start_text_nodes(); let node = fragment .pop_front() @@ -355,9 +346,9 @@ mod feat_hydration { } VTagInner::Other { children, tag } => { let mut nodes = Fragment::collect_children(&el); - let (_, child_bundle) = children.hydrate(root, parent_scope, &el, &mut nodes); + let child_bundle = children.hydrate(root, parent_scope, &el, &mut nodes); - nodes.trim_start_text_nodes(parent); + nodes.trim_start_text_nodes(); assert!(nodes.is_empty(), "expected EOF, found node."); @@ -367,17 +358,14 @@ mod feat_hydration { node_ref.set(Some((*el).clone())); - ( - node_ref.clone(), - BTag { - inner, - listeners, - attributes, - reference: el, - node_ref, - key, - }, - ) + BTag { + inner, + listeners, + attributes, + reference: el, + node_ref, + key, + } } } } @@ -586,17 +574,17 @@ mod tests { let svg_node = html! { {path_node} }; let svg_tag = assert_vtag(svg_node); - let (_, svg_tag) = svg_tag.attach(&root, &scope, &parent, NodeRef::default()); + let (_, svg_tag) = svg_tag.attach(&root, &scope, &parent, DomSlot::at_end()); assert_namespace(&svg_tag, SVG_NAMESPACE); let path_tag = assert_btag_ref(svg_tag.children().get(0).unwrap()); assert_namespace(path_tag, SVG_NAMESPACE); let g_tag = assert_vtag(g_node.clone()); - let (_, g_tag) = g_tag.attach(&root, &scope, &parent, NodeRef::default()); + let (_, g_tag) = g_tag.attach(&root, &scope, &parent, DomSlot::at_end()); assert_namespace(&g_tag, HTML_NAMESPACE); let g_tag = assert_vtag(g_node); - let (_, g_tag) = g_tag.attach(&root, &scope, &svg_el, NodeRef::default()); + let (_, g_tag) = g_tag.attach(&root, &scope, &svg_el, DomSlot::at_end()); assert_namespace(&g_tag, SVG_NAMESPACE); } @@ -695,7 +683,7 @@ mod tests { let (root, scope, parent) = setup_parent(); let elem = html! {
}; - let (_, mut elem) = elem.attach(&root, &scope, &parent, NodeRef::default()); + let (_, mut elem) = elem.attach(&root, &scope, &parent, DomSlot::at_end()); let vtag = assert_btag_mut(&mut elem); // test if the className has not been set assert!(!vtag.reference().has_attribute("class")); @@ -705,7 +693,7 @@ mod tests { let (root, scope, parent) = setup_parent(); let elem = gen_html(); - let (_, mut elem) = elem.attach(&root, &scope, &parent, NodeRef::default()); + let (_, mut elem) = elem.attach(&root, &scope, &parent, DomSlot::at_end()); let vtag = assert_btag_mut(&mut elem); // test if the className has been set assert!(vtag.reference().has_attribute("class")); @@ -729,7 +717,7 @@ mod tests { // Initial state let elem = html! { }; - let (_, mut elem) = elem.attach(&root, &scope, &parent, NodeRef::default()); + let (_, mut elem) = elem.attach(&root, &scope, &parent, DomSlot::at_end()); let vtag = assert_btag_ref(&elem); // User input @@ -741,7 +729,7 @@ mod tests { let elem_vtag = assert_vtag(next_elem); // Sync happens here - elem_vtag.reconcile_node(&root, &scope, &parent, NodeRef::default(), &mut elem); + elem_vtag.reconcile_node(&root, &scope, &parent, DomSlot::at_end(), &mut elem); let vtag = assert_btag_ref(&elem); // Get new current value of the input element @@ -760,7 +748,7 @@ mod tests { // Initial state let elem = html! { }; - let (_, mut elem) = elem.attach(&root, &scope, &parent, NodeRef::default()); + let (_, mut elem) = elem.attach(&root, &scope, &parent, DomSlot::at_end()); let vtag = assert_btag_ref(&elem); // User input @@ -772,7 +760,7 @@ mod tests { let elem_vtag = assert_vtag(next_elem); // Value should not be refreshed - elem_vtag.reconcile_node(&root, &scope, &parent, NodeRef::default(), &mut elem); + elem_vtag.reconcile_node(&root, &scope, &parent, DomSlot::at_end(), &mut elem); let vtag = assert_btag_ref(&elem); // Get user value of the input element @@ -799,7 +787,7 @@ mod tests { builder }/> }; - let (_, mut elem) = elem.attach(&root, &scope, &parent, NodeRef::default()); + let (_, mut elem) = elem.attach(&root, &scope, &parent, DomSlot::at_end()); let vtag = assert_btag_mut(&mut elem); // make sure the new tag name is used internally assert_eq!(vtag.tag(), "a"); @@ -857,7 +845,7 @@ mod tests { let node_ref = NodeRef::default(); let elem: VNode = html! {
}; assert_vtag_ref(&elem); - let (_, elem) = elem.attach(&root, &scope, &parent, NodeRef::default()); + let (_, elem) = elem.attach(&root, &scope, &parent, DomSlot::at_end()); assert_eq!(node_ref.get(), parent.first_child()); elem.detach(&root, &parent, false); assert!(node_ref.get().is_none()); @@ -869,14 +857,14 @@ mod tests { let node_ref_a = NodeRef::default(); let elem_a = html! {
}; - let (_, mut elem) = elem_a.attach(&root, &scope, &parent, NodeRef::default()); + let (_, mut elem) = elem_a.attach(&root, &scope, &parent, DomSlot::at_end()); // save the Node to check later that it has been reused. let node_a = node_ref_a.get().unwrap(); let node_ref_b = NodeRef::default(); let elem_b = html! {
}; - elem_b.reconcile_node(&root, &scope, &parent, NodeRef::default(), &mut elem); + elem_b.reconcile_node(&root, &scope, &parent, DomSlot::at_end(), &mut elem); let node_b = node_ref_b.get().unwrap(); @@ -906,8 +894,8 @@ mod tests { // The point of this diff is to first render the "after" div and then detach the "before" // div, while both should be bound to the same node ref - let (_, mut elem) = before.attach(&root, &scope, &parent, NodeRef::default()); - after.reconcile_node(&root, &scope, &parent, NodeRef::default(), &mut elem); + let (_, mut elem) = before.attach(&root, &scope, &parent, DomSlot::at_end()); + after.reconcile_node(&root, &scope, &parent, DomSlot::at_end(), &mut elem); assert_eq!( test_ref @@ -938,7 +926,7 @@ mod tests { let elem = VNode::VTag(Box::new(vtag)); - let (_, mut elem) = elem.attach(&root, &scope, &parent, NodeRef::default()); + let (_, mut elem) = elem.attach(&root, &scope, &parent, DomSlot::at_end()); // Create
(removed first attribute "disabled") let mut vtag = VTag::new("div"); @@ -949,7 +937,7 @@ mod tests { // Sync happens here // this should remove the the "disabled" attribute - elem_vtag.reconcile_node(&root, &scope, &parent, NodeRef::default(), &mut elem); + elem_vtag.reconcile_node(&root, &scope, &parent, DomSlot::at_end(), &mut elem); assert_eq!( test_ref diff --git a/packages/yew/src/dom_bundle/btext.rs b/packages/yew/src/dom_bundle/btext.rs index e482883f6cb..881f1a34000 100644 --- a/packages/yew/src/dom_bundle/btext.rs +++ b/packages/yew/src/dom_bundle/btext.rs @@ -3,10 +3,9 @@ use gloo::utils::document; use web_sys::{Element, Text as TextNode}; -use super::{insert_node, BNode, BSubtree, Reconcilable, ReconcileTarget}; +use super::{BNode, BSubtree, DomSlot, Reconcilable, ReconcileTarget}; use crate::html::AnyScope; use crate::virtual_dom::{AttrValue, VText}; -use crate::NodeRef; /// The bundle implementation to [VText] pub(super) struct BText { @@ -25,14 +24,10 @@ impl ReconcileTarget for BText { } } - fn shift(&self, next_parent: &Element, next_sibling: NodeRef) -> NodeRef { - let node = &self.text_node; + fn shift(&self, next_parent: &Element, slot: DomSlot) -> DomSlot { + slot.insert(next_parent, &self.text_node); - next_parent - .insert_before(node, next_sibling.get().as_ref()) - .unwrap(); - - NodeRef::new(self.text_node.clone().into()) + DomSlot::at(self.text_node.clone().into()) } } @@ -44,12 +39,12 @@ impl Reconcilable for VText { _root: &BSubtree, _parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, - ) -> (NodeRef, Self::Bundle) { + slot: DomSlot, + ) -> (DomSlot, Self::Bundle) { let Self { text } = self; let text_node = document().create_text_node(&text); - insert_node(&text_node, parent, next_sibling.get().as_ref()); - let node_ref = NodeRef::new(text_node.clone().into()); + slot.insert(parent, &text_node); + let node_ref = DomSlot::at(text_node.clone().into()); (node_ref, BText { text, text_node }) } @@ -59,12 +54,12 @@ impl Reconcilable for VText { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, + slot: DomSlot, bundle: &mut BNode, - ) -> NodeRef { + ) -> DomSlot { match bundle { - BNode::Text(btext) => self.reconcile(root, parent_scope, parent, next_sibling, btext), - _ => self.replace(root, parent_scope, parent, next_sibling, bundle), + BNode::Text(btext) => self.reconcile(root, parent_scope, parent, slot, btext), + _ => self.replace(root, parent_scope, parent, slot, bundle), } } @@ -73,15 +68,15 @@ impl Reconcilable for VText { _root: &BSubtree, _parent_scope: &AnyScope, _parent: &Element, - _next_sibling: NodeRef, + _slot: DomSlot, btext: &mut Self::Bundle, - ) -> NodeRef { + ) -> DomSlot { let Self { text } = self; let ancestor_text = std::mem::replace(&mut btext.text, text); if btext.text != ancestor_text { btext.text_node.set_node_value(Some(&btext.text)); } - NodeRef::new(btext.text_node.clone().into()) + DomSlot::at(btext.text_node.clone().into()) } } @@ -102,52 +97,47 @@ mod feat_hydration { impl Hydratable for VText { fn hydrate( self, - root: &BSubtree, - parent_scope: &AnyScope, + _root: &BSubtree, + _parent_scope: &AnyScope, parent: &Element, fragment: &mut Fragment, - ) -> (NodeRef, Self::Bundle) { - if let Some(m) = fragment.front().cloned() { + ) -> Self::Bundle { + let next_sibling = if let Some(m) = fragment.front().cloned() { // better safe than sorry. if m.node_type() == Node::TEXT_NODE { - if let Ok(m) = m.dyn_into::() { - // pop current node. - fragment.pop_front(); - - // TODO: It may make sense to assert the text content in the text node - // against the VText when #[cfg(debug_assertions)] - // is true, but this may be complicated. - // We always replace the text value for now. - // - // Please see the next comment for a detailed explanation. - m.set_node_value(Some(self.text.as_ref())); - - return ( - NodeRef::new(m.clone().into()), - BText { - text: self.text, - text_node: m, - }, - ); - } + let m = m.unchecked_into::(); + // pop current node. + fragment.pop_front(); + + // TODO: It may make sense to assert the text content in the text node + // against the VText when #[cfg(debug_assertions)] + // is true, but this may be complicated. + // We always replace the text value for now. + // + // Please see the next comment for a detailed explanation. + m.set_node_value(Some(self.text.as_ref())); + + return BText { + text: self.text, + text_node: m, + }; } - } + Some(m) + } else { + fragment.sibling_at_end().cloned() + }; // If there are multiple text nodes placed back-to-back in SSR, it may be parsed as a // single text node by browser, hence we need to add extra text nodes here // if the next node is not a text node. Similarly, the value of the text // node may be a combination of multiple VText vnodes. So we always need to // override their values. - self.attach( - root, - parent_scope, - parent, - fragment - .front() - .cloned() - .map(NodeRef::new) - .unwrap_or_default(), - ) + let text_node = document().create_text_node(""); + DomSlot::create(next_sibling).insert(parent, &text_node); + BText { + text: "".into(), + text_node, + } } } } diff --git a/packages/yew/src/dom_bundle/fragment.rs b/packages/yew/src/dom_bundle/fragment.rs index d8696bbb8f6..4ae51273138 100644 --- a/packages/yew/src/dom_bundle/fragment.rs +++ b/packages/yew/src/dom_bundle/fragment.rs @@ -1,15 +1,15 @@ use std::collections::VecDeque; use std::ops::{Deref, DerefMut}; +use wasm_bindgen::JsCast; use web_sys::{Element, Node}; -use crate::dom_bundle::BSubtree; -use crate::html::NodeRef; +use super::{BSubtree, DomSlot}; use crate::virtual_dom::Collectable; /// A Hydration Fragment #[derive(Default, Debug, Clone, PartialEq, Eq)] -pub struct Fragment(VecDeque); +pub(crate) struct Fragment(VecDeque, Option); impl Deref for Fragment { type Target = VecDeque; @@ -39,7 +39,7 @@ impl Fragment { fragment.push_back(m); } - Self(fragment) + Self(fragment, None) } /// Collects nodes for a Component Bundle or a BSuspense. @@ -63,7 +63,7 @@ impl Fragment { }; // We trim all leading text nodes as it's likely these are whitespaces. - collect_from.trim_start_text_nodes(parent); + collect_from.trim_start_text_nodes(); let first_node = collect_from .pop_front() @@ -115,19 +115,20 @@ impl Fragment { } } - nodes.push_back(current_node.clone()); + nodes.push_back(current_node); } - Self(nodes) + let next_child = collect_from.0.front().cloned(); + Self(nodes, next_child) } /// Remove child nodes until first non-text node. - pub fn trim_start_text_nodes(&mut self, parent: &Element) { + pub fn trim_start_text_nodes(&mut self) { while let Some(ref m) = self.front().cloned() { if m.node_type() == Node::TEXT_NODE { self.pop_front(); - parent.remove_child(m).unwrap(); + m.unchecked_ref::().remove(); } else { break; } @@ -141,7 +142,8 @@ impl Fragment { .map(|m| m.clone_node_with_deep(true).expect("failed to clone node.")) .collect::>(); - Self(nodes) + // the cloned nodes are disconnected from the real dom, so next_child is `None` + Self(nodes, None) } // detaches current fragment. @@ -156,16 +158,16 @@ impl Fragment { } /// Shift current Fragment into a different position in the dom. - pub fn shift(&self, next_parent: &Element, next_sibling: NodeRef) -> NodeRef { + pub fn shift(&self, next_parent: &Element, slot: DomSlot) -> DomSlot { for node in self.iter() { - next_parent - .insert_before(node, next_sibling.get().as_ref()) - .unwrap(); + slot.insert(next_parent, node); } - self.front() - .cloned() - .map(NodeRef::new) - .unwrap_or(next_sibling) + self.front().cloned().map(DomSlot::at).unwrap_or(slot) + } + + /// Return the node that comes after all the nodes in this fragment + pub fn sibling_at_end(&self) -> Option<&Node> { + self.1.as_ref() } } diff --git a/packages/yew/src/dom_bundle/mod.rs b/packages/yew/src/dom_bundle/mod.rs index 9e18a1672d1..d35225a0a7d 100644 --- a/packages/yew/src/dom_bundle/mod.rs +++ b/packages/yew/src/dom_bundle/mod.rs @@ -7,7 +7,7 @@ use web_sys::Element; -use crate::html::{AnyScope, NodeRef}; +use crate::html::AnyScope; use crate::virtual_dom::VNode; mod bcomp; @@ -18,6 +18,7 @@ mod braw; mod bsuspense; mod btag; mod btext; +mod position; mod subtree_root; mod traits; @@ -31,10 +32,11 @@ use braw::BRaw; use bsuspense::BSuspense; use btag::{BTag, Registry}; use btext::BText; +pub(crate) use position::{DomSlot, DynamicDomSlot}; use subtree_root::EventDescriptor; pub use subtree_root::{set_event_bubbling, BSubtree}; use traits::{Reconcilable, ReconcileTarget}; -use utils::{insert_node, test_log}; +use utils::test_log; /// A Bundle. /// @@ -53,8 +55,8 @@ impl Bundle { } /// Shifts the bundle into a different position. - pub fn shift(&self, next_parent: &Element, next_sibling: NodeRef) { - self.0.shift(next_parent, next_sibling); + pub fn shift(&self, next_parent: &Element, slot: DomSlot) { + self.0.shift(next_parent, slot); } /// Applies a virtual dom layout to current bundle. @@ -63,10 +65,10 @@ impl Bundle { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, + slot: DomSlot, next_node: VNode, - ) -> NodeRef { - next_node.reconcile_node(root, parent_scope, parent, next_sibling, &mut self.0) + ) -> DomSlot { + next_node.reconcile_node(root, parent_scope, parent, slot, &mut self.0) } /// Detaches current bundle. @@ -82,7 +84,7 @@ mod feat_hydration { pub(super) use super::utils::node_type_str; #[path = "./fragment.rs"] mod fragment; - pub use fragment::Fragment; + pub(crate) use fragment::Fragment; use super::*; impl Bundle { @@ -93,9 +95,9 @@ mod feat_hydration { parent: &Element, fragment: &mut Fragment, node: VNode, - ) -> (NodeRef, Self) { - let (node_ref, bundle) = node.hydrate(root, parent_scope, parent, fragment); - (node_ref, Self(bundle)) + ) -> Self { + let bundle = node.hydrate(root, parent_scope, parent, fragment); + Self(bundle) } } } diff --git a/packages/yew/src/dom_bundle/position.rs b/packages/yew/src/dom_bundle/position.rs new file mode 100644 index 00000000000..8a493a4e1a6 --- /dev/null +++ b/packages/yew/src/dom_bundle/position.rs @@ -0,0 +1,256 @@ +//! Structs for keeping track where in the DOM a node belongs + +use std::cell::RefCell; +use std::rc::Rc; + +use web_sys::{Element, Node}; + +/// A position in the list of children of an implicit parent [`Element`]. +/// +/// This can either be in front of a `DomSlot::at(next_sibling)`, at the end of the list with +/// `DomSlot::at_end()`, or a dynamic position in the list with [`DynamicDomSlot::to_position`]. +#[derive(Clone)] +pub(crate) struct DomSlot { + variant: DomSlotVariant, +} + +#[derive(Clone)] +enum DomSlotVariant { + Node(Option), + Chained(DynamicDomSlot), +} + +/// A dynamic dom slot can be reassigned. This change is also seen by the [`DomSlot`] from +/// [`Self::to_position`] before the reassignment took place. +#[derive(Clone)] +pub(crate) struct DynamicDomSlot { + target: Rc>, +} + +impl std::fmt::Debug for DomSlot { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + self.with_next_sibling(|n| { + write!( + f, + "DomSlot {{ next_sibling: {:?} }}", + n.map(crate::utils::print_node) + ) + }) + } +} + +impl std::fmt::Debug for DynamicDomSlot { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + write!(f, "{:#?}", *self.target.borrow()) + } +} + +#[cfg(debug_assertions)] +thread_local! { + // A special marker element that should not be referenced + static TRAP: Node = gloo::utils::document().create_element("div").unwrap().into(); +} + +impl DomSlot { + /// Denotes the position just before the given node in its parent's list of children. + pub fn at(next_sibling: Node) -> Self { + Self::create(Some(next_sibling)) + } + + /// Denotes the position at the end of a list of children. The parent is implicit. + pub fn at_end() -> Self { + Self::create(None) + } + + pub fn create(next_sibling: Option) -> Self { + Self { + variant: DomSlotVariant::Node(next_sibling), + } + } + + /// A new "placeholder" [DomSlot] that should not be used to insert nodes + #[inline] + pub fn new_debug_trapped() -> Self { + #[cfg(debug_assertions)] + { + Self::at(TRAP.with(|trap| trap.clone())) + } + #[cfg(not(debug_assertions))] + { + Self::at_end() + } + } + + /// Get the [Node] that comes just after the position, or `None` if this denotes the position at + /// the end + fn with_next_sibling(&self, f: impl FnOnce(Option<&Node>) -> R) -> R { + let checkedf = |node: Option<&Node>| { + #[cfg(debug_assertions)] + TRAP.with(|trap| { + assert!( + node != Some(trap), + "Should not use a trapped DomSlot. Please report this as an internal bug in \ + yew." + ) + }); + f(node) + }; + + match &self.variant { + DomSlotVariant::Node(ref n) => checkedf(n.as_ref()), + DomSlotVariant::Chained(ref chain) => chain.with_next_sibling(checkedf), + } + } + + /// Insert a [Node] at the position denoted by this slot. `parent` must be the actual parent + /// element of the children that this slot is implicitly a part of. + pub(super) fn insert(&self, parent: &Element, node: &Node) { + self.with_next_sibling(|next_sibling| { + parent + .insert_before(node, next_sibling) + .unwrap_or_else(|err| { + let msg = if next_sibling.is_some() { + "failed to insert node before next sibling" + } else { + "failed to append child" + }; + // Log normally, so we can inspect the nodes in console + gloo::console::error!(msg, err, parent, next_sibling, node); + // Log via tracing for consistency + tracing::error!(msg); + // Panic to short-curcuit and fail + panic!("{}", msg) + }); + }); + } + + #[cfg(target_arch = "wasm32")] + #[cfg(test)] + fn get(&self) -> Option { + self.with_next_sibling(|n| n.cloned()) + } +} + +impl DynamicDomSlot { + /// Create a dynamic dom slot that initially represents ("targets") the same slot as the + /// argument. + pub fn new(initial_position: DomSlot) -> Self { + Self { + target: Rc::new(RefCell::new(initial_position)), + } + } + + pub fn new_debug_trapped() -> Self { + Self::new(DomSlot::new_debug_trapped()) + } + + /// Change the [`DomSlot`] that is targeted. Subsequently, this will behave as if `self` was + /// created from the passed DomSlot in the first place. + pub fn reassign(&self, next_position: DomSlot) { + // TODO: is not defensive against accidental reference loops + *self.target.borrow_mut() = next_position; + } + + /// Get a [`DomSlot`] that gets automatically updated when `self` gets reassigned. All such + /// slots are equivalent to each other and point to the same position. + pub fn to_position(&self) -> DomSlot { + DomSlot { + variant: DomSlotVariant::Chained(self.clone()), + } + } + + fn with_next_sibling(&self, f: impl FnOnce(Option<&Node>) -> R) -> R { + // we use an iterative approach to traverse a possible long chain for references + // see for example issue #3043 why a recursive call is impossible for large lists in vdom + + // TODO: there could be some data structure that performs better here. E.g. a balanced tree + // with parent pointers come to mind, but they are a bit fiddly to implement in rust + let mut this = self.target.clone(); + loop { + // v------- borrow lives for this match expression + let next_this = match &this.borrow().variant { + DomSlotVariant::Node(ref n) => break f(n.as_ref()), + // We clone an Rc here temporarily, so that we don't have to consume stack + // space. The alternative would be to keep the + // `Ref<'_, DomSlot>` above in some temporary buffer + DomSlotVariant::Chained(ref chain) => chain.target.clone(), + }; + this = next_this; + } + } +} + +#[cfg(target_arch = "wasm32")] +#[cfg(test)] +mod layout_tests { + use gloo::utils::document; + use wasm_bindgen_test::{wasm_bindgen_test as test, wasm_bindgen_test_configure}; + + use super::*; + + wasm_bindgen_test_configure!(run_in_browser); + + #[test] + fn new_at_and_get() { + let node = document().create_element("p").unwrap(); + let position = DomSlot::at(node.clone().into()); + assert_eq!( + position.get().unwrap(), + node.clone().into(), + "expected the DomSlot to be at {node:#?}" + ); + } + + #[test] + fn new_at_end_and_get() { + let position = DomSlot::at_end(); + assert!( + position.get().is_none(), + "expected the DomSlot to not have a next sibling" + ); + } + + #[test] + fn get_through_dynamic() { + let original = DomSlot::at(document().create_element("p").unwrap().into()); + let target = DynamicDomSlot::new(original.clone()); + assert_eq!( + target.to_position().get(), + original.get(), + "expected {target:#?} to point to the same position as {original:#?}" + ); + } + + #[test] + fn get_after_reassign() { + let target = DynamicDomSlot::new(DomSlot::at_end()); + let target_pos = target.to_position(); + // We reassign *after* we called `to_position` here to be strict in the test + let replacement = DomSlot::at(document().create_element("p").unwrap().into()); + target.reassign(replacement.clone()); + assert_eq!( + target_pos.get(), + replacement.get(), + "expected {target:#?} to point to the same position as {replacement:#?}" + ); + } + + #[test] + fn get_chain_after_reassign() { + let middleman = DynamicDomSlot::new(DomSlot::at_end()); + let target = DynamicDomSlot::new(middleman.to_position()); + let target_pos = target.to_position(); + assert!( + target.to_position().get().is_none(), + "should not yet point to a node" + ); + // Now reassign the middle man, but get the node from `target` + let replacement = DomSlot::at(document().create_element("p").unwrap().into()); + middleman.reassign(replacement.clone()); + assert_eq!( + target_pos.get(), + replacement.get(), + "expected {target:#?} to point to the same position as {replacement:#?}" + ); + } +} diff --git a/packages/yew/src/dom_bundle/traits.rs b/packages/yew/src/dom_bundle/traits.rs index 6a1d5e5cf19..16a423d7c23 100644 --- a/packages/yew/src/dom_bundle/traits.rs +++ b/packages/yew/src/dom_bundle/traits.rs @@ -1,7 +1,7 @@ use web_sys::Element; -use super::{BNode, BSubtree}; -use crate::html::{AnyScope, NodeRef}; +use super::{BNode, BSubtree, DomSlot}; +use crate::html::AnyScope; /// A Reconcile Target. /// @@ -16,7 +16,7 @@ pub(super) trait ReconcileTarget { /// Move elements from one parent to another parent. /// This is for example used by `VSuspense` to preserve component state without detaching /// (which destroys component state). - fn shift(&self, next_parent: &Element, next_sibling: NodeRef) -> NodeRef; + fn shift(&self, next_parent: &Element, slot: DomSlot) -> DomSlot; } /// This trait provides features to update a tree by calculating a difference against another tree. @@ -29,19 +29,19 @@ pub(super) trait Reconcilable { /// - `root`: bundle of the subtree root /// - `parent_scope`: the parent `Scope` used for passing messages to the parent `Component`. /// - `parent`: the parent node in the DOM. - /// - `next_sibling`: to find where to put the node. + /// - `slot`: to find where to put the node. /// /// Returns a reference to the newly inserted element. - /// The [`NodeRef`] points the first element (if there are multiple nodes created), - /// or is the passed in next_sibling if there are no element is created. + /// The [`DomSlot`] points the first element (if there are multiple nodes created), + /// or is the passed in `slot` if there are no element is created. fn attach( self, root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, - ) -> (NodeRef, Self::Bundle); + slot: DomSlot, + ) -> (DomSlot, Self::Bundle); /// Scoped diff apply to other tree. /// @@ -52,7 +52,7 @@ pub(super) trait Reconcilable { /// Parameters: /// - `parent_scope`: the parent `Scope` used for passing messages to the parent `Component`. /// - `parent`: the parent node in the DOM. - /// - `next_sibling`: the next sibling, used to efficiently find where to put the node. + /// - `slot`: the slot in `parent`'s children where to put the node. /// - `bundle`: the node that this node will be replacing in the DOM. This method will remove /// the `bundle` from the `parent` if it is of the wrong kind, and otherwise reuse it. /// @@ -63,18 +63,18 @@ pub(super) trait Reconcilable { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, + slot: DomSlot, bundle: &mut BNode, - ) -> NodeRef; + ) -> DomSlot; fn reconcile( self, root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, + slot: DomSlot, bundle: &mut Self::Bundle, - ) -> NodeRef; + ) -> DomSlot; /// Replace an existing bundle by attaching self and detaching the existing one fn replace( @@ -83,14 +83,14 @@ pub(super) trait Reconcilable { root: &BSubtree, parent_scope: &AnyScope, parent: &Element, - next_sibling: NodeRef, + slot: DomSlot, bundle: &mut BNode, - ) -> NodeRef + ) -> DomSlot where Self: Sized, Self::Bundle: Into, { - let (self_ref, self_) = self.attach(root, parent_scope, parent, next_sibling); + let (self_ref, self_) = self.attach(root, parent_scope, parent, slot); let ancestor = std::mem::replace(bundle, self_.into()); ancestor.detach(root, parent, false); self_ref @@ -116,7 +116,7 @@ mod feat_hydration { parent_scope: &AnyScope, parent: &Element, fragment: &mut Fragment, - ) -> (NodeRef, Self::Bundle); + ) -> Self::Bundle; } } diff --git a/packages/yew/src/dom_bundle/utils.rs b/packages/yew/src/dom_bundle/utils.rs index 5582b2c20c8..1a66e32c8fa 100644 --- a/packages/yew/src/dom_bundle/utils.rs +++ b/packages/yew/src/dom_bundle/utils.rs @@ -1,28 +1,3 @@ -use web_sys::{Element, Node}; - -/// Insert a concrete [Node] into the DOM -pub(super) fn insert_node(node: &Node, parent: &Element, next_sibling: Option<&Node>) { - match next_sibling { - Some(next_sibling) => parent - .insert_before(node, Some(next_sibling)) - .unwrap_or_else(|err| { - // Log normally, so we can inspect the nodes in console - gloo::console::error!( - "failed to insert node before next sibling", - err, - parent, - next_sibling, - node - ); - // Log via tracing for consistency - tracing::error!("failed to insert node before next sibling"); - // Panic to short-curcuit and fail - panic!("failed to insert node before next sibling") - }), - None => parent.append_child(node).expect("failed to append child"), - }; -} - #[cfg(all(test, target_arch = "wasm32", verbose_tests))] macro_rules! test_log { ($fmt:literal, $($arg:expr),* $(,)?) => { @@ -45,9 +20,7 @@ mod feat_hydration { use std::borrow::Cow; use wasm_bindgen::JsCast; - use web_sys::Element; - - use super::*; + use web_sys::{Element, Node}; pub(in crate::dom_bundle) fn node_type_str(node: &Node) -> Cow<'static, str> { match node.node_type() { @@ -85,9 +58,8 @@ mod tests { use gloo::utils::document; use web_sys::Element; - use crate::dom_bundle::BSubtree; + use crate::dom_bundle::{BSubtree, DomSlot}; use crate::html::AnyScope; - use crate::NodeRef; pub fn setup_parent() -> (BSubtree, AnyScope, Element) { let scope = AnyScope::test(); @@ -101,7 +73,7 @@ mod tests { pub const SIBLING_CONTENT: &str = "END"; - pub fn setup_parent_and_sibling() -> (BSubtree, AnyScope, Element, NodeRef) { + pub(crate) fn setup_parent_and_sibling() -> (BSubtree, AnyScope, Element, DomSlot) { let scope = AnyScope::test(); let parent = document().create_element("div").unwrap(); let root = BSubtree::create_root(&parent); @@ -110,7 +82,7 @@ mod tests { let end = document().create_text_node(SIBLING_CONTENT); parent.append_child(&end).unwrap(); - let sibling = NodeRef::new(end.into()); + let sibling = DomSlot::at(end.into()); (root, scope, parent, sibling) } diff --git a/packages/yew/src/html/component/lifecycle.rs b/packages/yew/src/html/component/lifecycle.rs index cd2acc126b5..ad5ee160965 100644 --- a/packages/yew/src/html/component/lifecycle.rs +++ b/packages/yew/src/html/component/lifecycle.rs @@ -11,9 +11,7 @@ use super::BaseComponent; #[cfg(feature = "hydration")] use crate::dom_bundle::Fragment; #[cfg(feature = "csr")] -use crate::dom_bundle::{BSubtree, Bundle}; -#[cfg(feature = "csr")] -use crate::html::NodeRef; +use crate::dom_bundle::{BSubtree, Bundle, DomSlot, DynamicDomSlot}; #[cfg(feature = "hydration")] use crate::html::RenderMode; use crate::html::{Html, RenderError}; @@ -27,16 +25,19 @@ pub(crate) enum ComponentRenderState { bundle: Bundle, root: BSubtree, parent: Element, - next_sibling: NodeRef, - internal_ref: NodeRef, + /// The dom position in front of the next sibling + sibling_slot: DynamicDomSlot, + /// The dom position in front of this component. Adjusted whenever this component + /// re-renders. + own_slot: DynamicDomSlot, }, #[cfg(feature = "hydration")] Hydration { fragment: Fragment, root: BSubtree, parent: Element, - next_sibling: NodeRef, - internal_ref: NodeRef, + sibling_slot: DynamicDomSlot, + own_slot: DynamicDomSlot, }, #[cfg(feature = "ssr")] Ssr { @@ -52,31 +53,31 @@ impl std::fmt::Debug for ComponentRenderState { ref bundle, root, ref parent, - ref next_sibling, - ref internal_ref, + ref sibling_slot, + ref own_slot, } => f .debug_struct("ComponentRenderState::Render") .field("bundle", bundle) .field("root", root) .field("parent", parent) - .field("next_sibling", next_sibling) - .field("internal_ref", internal_ref) + .field("sibling_slot", sibling_slot) + .field("own_slot", own_slot) .finish(), #[cfg(feature = "hydration")] Self::Hydration { ref fragment, ref parent, - ref next_sibling, - ref internal_ref, + ref sibling_slot, + ref own_slot, ref root, } => f .debug_struct("ComponentRenderState::Hydration") .field("fragment", fragment) .field("root", root) .field("parent", parent) - .field("next_sibling", next_sibling) - .field("internal_ref", internal_ref) + .field("sibling_slot", sibling_slot) + .field("own_slot", own_slot) .finish(), #[cfg(feature = "ssr")] @@ -96,31 +97,31 @@ impl std::fmt::Debug for ComponentRenderState { #[cfg(feature = "csr")] impl ComponentRenderState { - pub(crate) fn shift(&mut self, next_parent: Element, next_next_sibling: NodeRef) { + pub(crate) fn shift(&mut self, next_parent: Element, next_slot: DomSlot) { match self { #[cfg(feature = "csr")] Self::Render { bundle, parent, - next_sibling, + sibling_slot, .. } => { - bundle.shift(&next_parent, next_next_sibling.clone()); + bundle.shift(&next_parent, next_slot.clone()); *parent = next_parent; - next_sibling.link(next_next_sibling); + sibling_slot.reassign(next_slot); } #[cfg(feature = "hydration")] Self::Hydration { fragment, parent, - next_sibling, + sibling_slot, .. } => { - fragment.shift(&next_parent, next_next_sibling.clone()); + fragment.shift(&next_parent, next_slot.clone()); *parent = next_parent; - next_sibling.link(next_next_sibling); + sibling_slot.reassign(next_slot); } #[cfg(feature = "ssr")] @@ -386,13 +387,10 @@ impl ComponentState { ComponentRenderState::Render { bundle, ref parent, - ref internal_ref, ref root, .. } => { bundle.detach(root, parent, parent_to_detach); - - internal_ref.set(None); } // We need to detach the hydrate fragment if the component is not hydrated. #[cfg(feature = "hydration")] @@ -400,12 +398,9 @@ impl ComponentState { ref root, fragment, ref parent, - ref internal_ref, .. } => { fragment.detach(root, parent, parent_to_detach); - - internal_ref.set(None); } #[cfg(feature = "ssr")] @@ -496,18 +491,15 @@ impl ComponentState { ref mut bundle, ref parent, ref root, - ref next_sibling, - ref internal_ref, + ref sibling_slot, + ref mut own_slot, .. } => { let scope = self.inner.any_scope(); - #[cfg(feature = "hydration")] - next_sibling.debug_assert_not_trapped(); - let new_node_ref = - bundle.reconcile(root, &scope, parent, next_sibling.clone(), new_root); - internal_ref.link(new_node_ref); + bundle.reconcile(root, &scope, parent, sibling_slot.to_position(), new_root); + own_slot.reassign(new_node_ref); let first_render = !self.has_rendered; self.has_rendered = true; @@ -526,12 +518,12 @@ impl ComponentState { ComponentRenderState::Hydration { ref mut fragment, ref parent, - ref internal_ref, - ref next_sibling, + ref mut own_slot, + ref mut sibling_slot, ref root, } => { // We schedule a "first" render to run immediately after hydration, - // to fix NodeRefs (first_node and next_sibling). + // to fix NodeRefs (first_node and slot). scheduler::push_component_priority_render( self.comp_id, Box::new(RenderRunner { @@ -544,21 +536,22 @@ impl ComponentState { // This first node is not guaranteed to be correct here. // As it may be a comment node that is removed afterwards. // but we link it anyways. - let (node, bundle) = Bundle::hydrate(root, &scope, parent, fragment, new_root); + let bundle = Bundle::hydrate(root, &scope, parent, fragment, new_root); // We trim all text nodes before checking as it's likely these are whitespaces. - fragment.trim_start_text_nodes(parent); + fragment.trim_start_text_nodes(); assert!(fragment.is_empty(), "expected end of component, found node"); - internal_ref.link(node); - self.render_state = ComponentRenderState::Render { root: root.clone(), bundle, parent: parent.clone(), - internal_ref: internal_ref.clone(), - next_sibling: next_sibling.clone(), + own_slot: std::mem::replace(own_slot, DynamicDomSlot::new_debug_trapped()), + sibling_slot: std::mem::replace( + sibling_slot, + DynamicDomSlot::new_debug_trapped(), + ), }; } @@ -592,7 +585,7 @@ mod feat_csr { pub(crate) struct PropsUpdateRunner { pub state: Shared>, pub props: Option>, - pub next_sibling: Option, + pub next_sibling_slot: Option, } impl ComponentState { @@ -601,26 +594,24 @@ mod feat_csr { skip(self), fields(component.id = self.comp_id) )] - fn changed(&mut self, props: Option>, next_sibling: Option) -> bool { - if let Some(next_sibling) = next_sibling { + fn changed( + &mut self, + props: Option>, + next_sibling_slot: Option, + ) -> bool { + if let Some(next_sibling_slot) = next_sibling_slot { // When components are updated, their siblings were likely also updated // We also need to shift the bundle so next sibling will be synced to child // components. - match self.render_state { + match &mut self.render_state { #[cfg(feature = "csr")] - ComponentRenderState::Render { - next_sibling: ref current_next_sibling, - .. - } => { - current_next_sibling.link(next_sibling); + ComponentRenderState::Render { sibling_slot, .. } => { + sibling_slot.reassign(next_sibling_slot); } #[cfg(feature = "hydration")] - ComponentRenderState::Hydration { - next_sibling: ref current_next_sibling, - .. - } => { - current_next_sibling.link(next_sibling); + ComponentRenderState::Hydration { sibling_slot, .. } => { + sibling_slot.reassign(next_sibling_slot); } #[cfg(feature = "ssr")] @@ -681,13 +672,13 @@ mod feat_csr { impl Runnable for PropsUpdateRunner { fn run(self: Box) { let Self { - next_sibling, + next_sibling_slot, props, state: shared_state, } = *self; if let Some(state) = shared_state.borrow_mut().as_mut() { - let schedule_render = state.changed(props, next_sibling); + let schedule_render = state.changed(props, next_sibling_slot); if schedule_render { scheduler::push_component_render( @@ -738,7 +729,7 @@ mod feat_csr { scheduler::push_component_props_update(Box::new(PropsUpdateRunner { state: self.state.clone(), props: None, - next_sibling: None, + next_sibling_slot: None, })); } } @@ -886,8 +877,8 @@ mod tests { scope.mount_in_place( root, parent, - NodeRef::default(), - NodeRef::default(), + DomSlot::at_end(), + DynamicDomSlot::new_debug_trapped(), Rc::new(props), ); crate::scheduler::start_now(); diff --git a/packages/yew/src/html/component/scope.rs b/packages/yew/src/html/component/scope.rs index bca6f17e2b8..f4b0fbd4b65 100644 --- a/packages/yew/src/html/component/scope.rs +++ b/packages/yew/src/html/component/scope.rs @@ -520,11 +520,10 @@ mod feat_csr { use web_sys::Element; use super::*; - use crate::dom_bundle::{BSubtree, Bundle}; + use crate::dom_bundle::{BSubtree, Bundle, DomSlot, DynamicDomSlot}; use crate::html::component::lifecycle::{ ComponentRenderState, CreateRunner, DestroyRunner, PropsUpdateRunner, RenderRunner, }; - use crate::html::NodeRef; use crate::scheduler; impl AnyScope { @@ -541,11 +540,11 @@ mod feat_csr { fn schedule_props_update( state: Shared>, props: Rc, - next_sibling: NodeRef, + next_sibling_slot: DomSlot, ) { scheduler::push_component_props_update(Box::new(PropsUpdateRunner { state, - next_sibling: Some(next_sibling), + next_sibling_slot: Some(next_sibling_slot), props: Some(props), })); // Not guaranteed to already have the scheduler started @@ -561,20 +560,20 @@ mod feat_csr { &self, root: BSubtree, parent: Element, - next_sibling: NodeRef, - internal_ref: NodeRef, + slot: DomSlot, + internal_ref: DynamicDomSlot, props: Rc, ) { let bundle = Bundle::new(); - internal_ref.link(next_sibling.clone()); - let stable_next_sibling = NodeRef::default(); - stable_next_sibling.link(next_sibling); + let sibling_slot = DynamicDomSlot::new(slot); + internal_ref.reassign(sibling_slot.to_position()); + let state = ComponentRenderState::Render { bundle, root, - internal_ref, + own_slot: internal_ref, parent, - next_sibling: stable_next_sibling, + sibling_slot, }; scheduler::push_component_create( @@ -594,8 +593,8 @@ mod feat_csr { scheduler::start(); } - pub(crate) fn reuse(&self, props: Rc, next_sibling: NodeRef) { - schedule_props_update(self.state.clone(), props, next_sibling) + pub(crate) fn reuse(&self, props: Rc, slot: DomSlot) { + schedule_props_update(self.state.clone(), props, slot) } } @@ -604,7 +603,7 @@ mod feat_csr { /// Get the render state if it hasn't already been destroyed fn render_state(&self) -> Option>; /// Shift the node associated with this scope to a new place - fn shift_node(&self, parent: Element, next_sibling: NodeRef); + fn shift_node(&self, parent: Element, slot: DomSlot); /// Process an event to destroy a component fn destroy(self, parent_to_detach: bool); fn destroy_boxed(self: Box, parent_to_detach: bool); @@ -640,10 +639,10 @@ mod feat_csr { self.destroy(parent_to_detach) } - fn shift_node(&self, parent: Element, next_sibling: NodeRef) { + fn shift_node(&self, parent: Element, slot: DomSlot) { let mut state_ref = self.state.borrow_mut(); if let Some(render_state) = state_ref.as_mut() { - render_state.render_state.shift(parent, next_sibling) + render_state.render_state.shift(parent, slot) } } } @@ -657,9 +656,8 @@ mod feat_hydration { use web_sys::{Element, HtmlScriptElement}; use super::*; - use crate::dom_bundle::{BSubtree, Fragment}; + use crate::dom_bundle::{BSubtree, DomSlot, DynamicDomSlot, Fragment}; use crate::html::component::lifecycle::{ComponentRenderState, CreateRunner, RenderRunner}; - use crate::html::NodeRef; use crate::scheduler; use crate::virtual_dom::Collectable; @@ -680,7 +678,7 @@ mod feat_hydration { root: BSubtree, parent: Element, fragment: &mut Fragment, - internal_ref: NodeRef, + internal_ref: DynamicDomSlot, props: Rc, ) { // This is very helpful to see which component is failing during hydration @@ -695,14 +693,12 @@ mod feat_hydration { let collectable = Collectable::for_component::(); let mut fragment = Fragment::collect_between(fragment, &collectable, &parent); - match fragment.front().cloned() { - front @ Some(_) => internal_ref.set(front), - None => - { - #[cfg(debug_assertions)] - internal_ref.link(NodeRef::new_debug_trapped()) - } - } + let next_sibling = if let Some(n) = fragment.front() { + Some(n.clone()) + } else { + fragment.sibling_at_end().cloned() + }; + internal_ref.reassign(DomSlot::create(next_sibling)); let prepared_state = match fragment .back() @@ -720,8 +716,8 @@ mod feat_hydration { let state = ComponentRenderState::Hydration { parent, root, - internal_ref, - next_sibling: NodeRef::new_debug_trapped(), + own_slot: internal_ref, + sibling_slot: DynamicDomSlot::new_debug_trapped(), fragment, }; diff --git a/packages/yew/src/html/mod.rs b/packages/yew/src/html/mod.rs index 28fa84af2b4..87e3cc03372 100644 --- a/packages/yew/src/html/mod.rs +++ b/packages/yew/src/html/mod.rs @@ -92,7 +92,7 @@ pub struct NodeRef(Rc>); impl PartialEq for NodeRef { fn eq(&self, other: &Self) -> bool { - self.0.as_ptr() == other.0.as_ptr() || Some(self) == other.0.borrow().link.as_ref() + self.0.as_ptr() == other.0.as_ptr() } } @@ -109,14 +109,13 @@ impl std::fmt::Debug for NodeRef { #[derive(PartialEq, Debug, Default, Clone)] struct NodeRefInner { node: Option, - link: Option, } impl NodeRef { /// Get the wrapped Node reference if it exists pub fn get(&self) -> Option { let inner = self.0.borrow(); - inner.node.clone().or_else(|| inner.link.as_ref()?.get()) + inner.node.clone() } /// Try converting the node reference into another form @@ -131,68 +130,9 @@ mod feat_csr { use super::*; impl NodeRef { - /// Link a downstream `NodeRef` - pub(crate) fn link(&self, node_ref: Self) { - // Avoid circular references - debug_assert!( - self != &node_ref, - "no circular references allowed! Report this as a bug in yew" - ); - - let mut this = self.0.borrow_mut(); - this.node = None; - this.link = Some(node_ref); - } - - /// Wrap an existing `Node` in a `NodeRef` - pub(crate) fn new(node: Node) -> Self { - let node_ref = NodeRef::default(); - node_ref.set(Some(node)); - node_ref - } - - /// Place a Node in a reference for later use - pub(crate) fn set(&self, node: Option) { - let mut this = self.0.borrow_mut(); - this.node = node; - this.link = None; - } - } -} - -#[cfg(feature = "hydration")] -mod feat_hydration { - use super::*; - - #[cfg(debug_assertions)] - thread_local! { - // A special marker element that should not be referenced - static TRAP: Node = gloo::utils::document().create_element("div").unwrap().into(); - } - - impl NodeRef { - // A new "placeholder" node ref that should not be accessed - #[inline] - pub(crate) fn new_debug_trapped() -> Self { - #[cfg(debug_assertions)] - { - Self::new(TRAP.with(|trap| trap.clone())) - } - #[cfg(not(debug_assertions))] - { - Self::default() - } - } - - #[inline] - pub(crate) fn debug_assert_not_trapped(&self) { - #[cfg(debug_assertions)] - TRAP.with(|trap| { - assert!( - self.get().as_ref() != Some(trap), - "should not use a trapped node ref" - ) - }) + pub(crate) fn set(&self, new_ref: Option) { + let mut inner = self.0.borrow_mut(); + inner.node = new_ref; } } } diff --git a/packages/yew/src/tests/layout_tests.rs b/packages/yew/src/tests/layout_tests.rs index 85a54419a4b..657cc96a9d5 100644 --- a/packages/yew/src/tests/layout_tests.rs +++ b/packages/yew/src/tests/layout_tests.rs @@ -2,9 +2,8 @@ //! //! This tests must be run in browser and thus require the `csr` feature to be enabled use gloo::console::log; -use yew::NodeRef; -use crate::dom_bundle::{BSubtree, Bundle}; +use crate::dom_bundle::{BSubtree, Bundle, DomSlot}; use crate::html::AnyScope; use crate::virtual_dom::VNode; use crate::{scheduler, Component, Context, Html}; @@ -48,14 +47,14 @@ pub fn diff_layouts(layouts: Vec>) { parent_element.append_child(&end_node).unwrap(); // Tests each layout independently - let next_sibling = NodeRef::new(end_node.into()); + let slot = DomSlot::at(end_node.into()); for layout in layouts.iter() { // Apply the layout let vnode = layout.node.clone(); log!("Independently apply layout '{}'", layout.name); let mut bundle = Bundle::new(); - bundle.reconcile(&root, &scope, &parent_element, next_sibling.clone(), vnode); + bundle.reconcile(&root, &scope, &parent_element, slot.clone(), vnode); scheduler::start_now(); assert_eq!( parent_element.inner_html(), @@ -69,7 +68,7 @@ pub fn diff_layouts(layouts: Vec>) { log!("Independently reapply layout '{}'", layout.name); - bundle.reconcile(&root, &scope, &parent_element, next_sibling.clone(), vnode); + bundle.reconcile(&root, &scope, &parent_element, slot.clone(), vnode); scheduler::start_now(); assert_eq!( parent_element.inner_html(), @@ -95,13 +94,7 @@ pub fn diff_layouts(layouts: Vec>) { let next_vnode = layout.node.clone(); log!("Sequentially apply layout '{}'", layout.name); - bundle.reconcile( - &root, - &scope, - &parent_element, - next_sibling.clone(), - next_vnode, - ); + bundle.reconcile(&root, &scope, &parent_element, slot.clone(), next_vnode); scheduler::start_now(); assert_eq!( @@ -117,13 +110,7 @@ pub fn diff_layouts(layouts: Vec>) { let next_vnode = layout.node.clone(); log!("Sequentially detach layout '{}'", layout.name); - bundle.reconcile( - &root, - &scope, - &parent_element, - next_sibling.clone(), - next_vnode, - ); + bundle.reconcile(&root, &scope, &parent_element, slot.clone(), next_vnode); scheduler::start_now(); assert_eq!( diff --git a/packages/yew/src/virtual_dom/vcomp.rs b/packages/yew/src/virtual_dom/vcomp.rs index 7d16b16cffe..81d644f5252 100644 --- a/packages/yew/src/virtual_dom/vcomp.rs +++ b/packages/yew/src/virtual_dom/vcomp.rs @@ -10,15 +10,15 @@ use futures::future::{FutureExt, LocalBoxFuture}; use web_sys::Element; use super::Key; -#[cfg(feature = "csr")] -use crate::dom_bundle::BSubtree; #[cfg(feature = "hydration")] use crate::dom_bundle::Fragment; +#[cfg(feature = "csr")] +use crate::dom_bundle::{BSubtree, DomSlot, DynamicDomSlot}; use crate::html::BaseComponent; +#[cfg(feature = "csr")] +use crate::html::Scoped; #[cfg(any(feature = "ssr", feature = "csr"))] use crate::html::{AnyScope, Scope}; -#[cfg(feature = "csr")] -use crate::html::{NodeRef, Scoped}; #[cfg(feature = "ssr")] use crate::platform::fmt::BufWriter; @@ -61,12 +61,12 @@ pub(crate) trait Mountable { root: &BSubtree, parent_scope: &AnyScope, parent: Element, - internal_ref: NodeRef, - next_sibling: NodeRef, + slot: DomSlot, + internal_ref: DynamicDomSlot, ) -> Box; #[cfg(feature = "csr")] - fn reuse(self: Box, scope: &dyn Scoped, next_sibling: NodeRef); + fn reuse(self: Box, scope: &dyn Scoped, slot: DomSlot); #[cfg(feature = "ssr")] fn render_into_stream<'a>( @@ -82,7 +82,7 @@ pub(crate) trait Mountable { root: BSubtree, parent_scope: &AnyScope, parent: Element, - internal_ref: NodeRef, + internal_ref: DynamicDomSlot, fragment: &mut Fragment, ) -> Box; } @@ -111,19 +111,19 @@ impl Mountable for PropsWrapper { root: &BSubtree, parent_scope: &AnyScope, parent: Element, - internal_ref: NodeRef, - next_sibling: NodeRef, + slot: DomSlot, + internal_ref: DynamicDomSlot, ) -> Box { let scope: Scope = Scope::new(Some(parent_scope.clone())); - scope.mount_in_place(root.clone(), parent, next_sibling, internal_ref, self.props); + scope.mount_in_place(root.clone(), parent, slot, internal_ref, self.props); Box::new(scope) } #[cfg(feature = "csr")] - fn reuse(self: Box, scope: &dyn Scoped, next_sibling: NodeRef) { + fn reuse(self: Box, scope: &dyn Scoped, slot: DomSlot) { let scope: Scope = scope.to_any().downcast::(); - scope.reuse(self.props, next_sibling); + scope.reuse(self.props, slot); } #[cfg(feature = "ssr")] @@ -149,7 +149,7 @@ impl Mountable for PropsWrapper { root: BSubtree, parent_scope: &AnyScope, parent: Element, - internal_ref: NodeRef, + internal_ref: DynamicDomSlot, fragment: &mut Fragment, ) -> Box { let scope: Scope = Scope::new(Some(parent_scope.clone())); diff --git a/packages/yew/src/virtual_dom/vportal.rs b/packages/yew/src/virtual_dom/vportal.rs index 28091132412..4b1cf09da59 100644 --- a/packages/yew/src/virtual_dom/vportal.rs +++ b/packages/yew/src/virtual_dom/vportal.rs @@ -25,8 +25,8 @@ impl VPortal { } /// Creates a [VPortal] rendering `content` in the DOM hierarchy under `host`. - /// If `next_sibling` is given, the content is inserted before that [Node]. - /// The parent of `next_sibling`, if given, must be `host`. + /// If `inner_sibling` is given, the content is inserted before that [Node]. + /// The parent of `inner_sibling`, if given, must be `host`. pub fn new_before(content: VNode, host: Element, inner_sibling: Option) -> Self { Self { host, From 352a0853d0cd7928a07bde8af48182f40f03195f Mon Sep 17 00:00:00 2001 From: Luke Pendleton <46588002+lukependleton@users.noreply.github.com> Date: Mon, 30 Jan 2023 06:27:51 -0500 Subject: [PATCH 23/76] Fix typo in html! concept docs (#3096) I am learning Yew and noticed this small typo in the docs as I was reading through it, so I thought I'd fix it :) --- .../version-0.20/concepts/basic-web-technologies/html.mdx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/website/versioned_docs/version-0.20/concepts/basic-web-technologies/html.mdx b/website/versioned_docs/version-0.20/concepts/basic-web-technologies/html.mdx index 8861c3f5c80..3a1f051e025 100644 --- a/website/versioned_docs/version-0.20/concepts/basic-web-technologies/html.mdx +++ b/website/versioned_docs/version-0.20/concepts/basic-web-technologies/html.mdx @@ -39,7 +39,7 @@ let combined_html: Html = html! { }; ``` -One rule major rule comes with use of `html!` - you can only return 1 wrapping node. +One major rule comes with the use of `html!` - you can only return 1 wrapping node. To render a list of multiple elements, `html!` allows fragments. Fragments are tags without a name, that produce no html element by themselves. From 837ddadf22e6b4a03dc2edb45bbdbbeffa50f81b Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 1 Feb 2023 23:37:40 +0900 Subject: [PATCH 24/76] Bump @typescript-eslint/parser from 5.45.0 to 5.50.0 in /website (#3103) Bumps [@typescript-eslint/parser](https://github.com/typescript-eslint/typescript-eslint/tree/HEAD/packages/parser) from 5.45.0 to 5.50.0. - [Release notes](https://github.com/typescript-eslint/typescript-eslint/releases) - [Changelog](https://github.com/typescript-eslint/typescript-eslint/blob/main/packages/parser/CHANGELOG.md) - [Commits](https://github.com/typescript-eslint/typescript-eslint/commits/v5.50.0/packages/parser) --- updated-dependencies: - dependency-name: "@typescript-eslint/parser" dependency-type: direct:development update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- website/package-lock.json | 94 +++++++++++++++++++-------------------- website/package.json | 2 +- 2 files changed, 48 insertions(+), 48 deletions(-) diff --git a/website/package-lock.json b/website/package-lock.json index a587e5231b6..ea202faa755 100644 --- a/website/package-lock.json +++ b/website/package-lock.json @@ -32,7 +32,7 @@ "@types/react-helmet": "^6.1.6", "@types/react-router-dom": "^5.3.3", "@typescript-eslint/eslint-plugin": "^5.47.1", - "@typescript-eslint/parser": "^5.45.0", + "@typescript-eslint/parser": "^5.50.0", "dir-compare": "^4.0.0", "prettier": "2.8.1", "typescript": "^4.8.3" @@ -4491,14 +4491,14 @@ } }, "node_modules/@typescript-eslint/parser": { - "version": "5.45.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-5.45.0.tgz", - "integrity": "sha512-brvs/WSM4fKUmF5Ot/gEve6qYiCMjm6w4HkHPfS6ZNmxTS0m0iNN4yOChImaCkqc1hRwFGqUyanMXuGal6oyyQ==", + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-5.50.0.tgz", + "integrity": "sha512-KCcSyNaogUDftK2G9RXfQyOCt51uB5yqC6pkUYqhYh8Kgt+DwR5M0EwEAxGPy/+DH6hnmKeGsNhiZRQxjH71uQ==", "dev": true, "dependencies": { - "@typescript-eslint/scope-manager": "5.45.0", - "@typescript-eslint/types": "5.45.0", - "@typescript-eslint/typescript-estree": "5.45.0", + "@typescript-eslint/scope-manager": "5.50.0", + "@typescript-eslint/types": "5.50.0", + "@typescript-eslint/typescript-estree": "5.50.0", "debug": "^4.3.4" }, "engines": { @@ -4518,13 +4518,13 @@ } }, "node_modules/@typescript-eslint/scope-manager": { - "version": "5.45.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.45.0.tgz", - "integrity": "sha512-noDMjr87Arp/PuVrtvN3dXiJstQR1+XlQ4R1EvzG+NMgXi8CuMCXpb8JqNtFHKceVSQ985BZhfRdowJzbv4yKw==", + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.50.0.tgz", + "integrity": "sha512-rt03kaX+iZrhssaT974BCmoUikYtZI24Vp/kwTSy841XhiYShlqoshRFDvN1FKKvU2S3gK+kcBW1EA7kNUrogg==", "dev": true, "dependencies": { - "@typescript-eslint/types": "5.45.0", - "@typescript-eslint/visitor-keys": "5.45.0" + "@typescript-eslint/types": "5.50.0", + "@typescript-eslint/visitor-keys": "5.50.0" }, "engines": { "node": "^12.22.0 || ^14.17.0 || >=16.0.0" @@ -4619,9 +4619,9 @@ } }, "node_modules/@typescript-eslint/types": { - "version": "5.45.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.45.0.tgz", - "integrity": "sha512-QQij+u/vgskA66azc9dCmx+rev79PzX8uDHpsqSjEFtfF2gBUTRCpvYMh2gw2ghkJabNkPlSUCimsyBEQZd1DA==", + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.50.0.tgz", + "integrity": "sha512-atruOuJpir4OtyNdKahiHZobPKFvZnBnfDiyEaBf6d9vy9visE7gDjlmhl+y29uxZ2ZDgvXijcungGFjGGex7w==", "dev": true, "engines": { "node": "^12.22.0 || ^14.17.0 || >=16.0.0" @@ -4632,13 +4632,13 @@ } }, "node_modules/@typescript-eslint/typescript-estree": { - "version": "5.45.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.45.0.tgz", - "integrity": "sha512-maRhLGSzqUpFcZgXxg1qc/+H0bT36lHK4APhp0AEUVrpSwXiRAomm/JGjSG+kNUio5kAa3uekCYu/47cnGn5EQ==", + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.50.0.tgz", + "integrity": "sha512-Gq4zapso+OtIZlv8YNAStFtT6d05zyVCK7Fx3h5inlLBx2hWuc/0465C2mg/EQDDU2LKe52+/jN4f0g9bd+kow==", "dev": true, "dependencies": { - "@typescript-eslint/types": "5.45.0", - "@typescript-eslint/visitor-keys": "5.45.0", + "@typescript-eslint/types": "5.50.0", + "@typescript-eslint/visitor-keys": "5.50.0", "debug": "^4.3.4", "globby": "^11.1.0", "is-glob": "^4.0.3", @@ -4759,12 +4759,12 @@ } }, "node_modules/@typescript-eslint/visitor-keys": { - "version": "5.45.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.45.0.tgz", - "integrity": "sha512-jc6Eccbn2RtQPr1s7th6jJWQHBHI6GBVQkCHoJFQ5UreaKm59Vxw+ynQUPPY2u2Amquc+7tmEoC2G52ApsGNNg==", + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.50.0.tgz", + "integrity": "sha512-cdMeD9HGu6EXIeGOh2yVW6oGf9wq8asBgZx7nsR/D36gTfQ0odE5kcRYe5M81vjEFAcPeugXrHg78Imu55F6gg==", "dev": true, "dependencies": { - "@typescript-eslint/types": "5.45.0", + "@typescript-eslint/types": "5.50.0", "eslint-visitor-keys": "^3.3.0" }, "engines": { @@ -17170,25 +17170,25 @@ } }, "@typescript-eslint/parser": { - "version": "5.45.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-5.45.0.tgz", - "integrity": "sha512-brvs/WSM4fKUmF5Ot/gEve6qYiCMjm6w4HkHPfS6ZNmxTS0m0iNN4yOChImaCkqc1hRwFGqUyanMXuGal6oyyQ==", + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-5.50.0.tgz", + "integrity": "sha512-KCcSyNaogUDftK2G9RXfQyOCt51uB5yqC6pkUYqhYh8Kgt+DwR5M0EwEAxGPy/+DH6hnmKeGsNhiZRQxjH71uQ==", "dev": true, "requires": { - "@typescript-eslint/scope-manager": "5.45.0", - "@typescript-eslint/types": "5.45.0", - "@typescript-eslint/typescript-estree": "5.45.0", + "@typescript-eslint/scope-manager": "5.50.0", + "@typescript-eslint/types": "5.50.0", + "@typescript-eslint/typescript-estree": "5.50.0", "debug": "^4.3.4" } }, "@typescript-eslint/scope-manager": { - "version": "5.45.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.45.0.tgz", - "integrity": "sha512-noDMjr87Arp/PuVrtvN3dXiJstQR1+XlQ4R1EvzG+NMgXi8CuMCXpb8JqNtFHKceVSQ985BZhfRdowJzbv4yKw==", + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.50.0.tgz", + "integrity": "sha512-rt03kaX+iZrhssaT974BCmoUikYtZI24Vp/kwTSy841XhiYShlqoshRFDvN1FKKvU2S3gK+kcBW1EA7kNUrogg==", "dev": true, "requires": { - "@typescript-eslint/types": "5.45.0", - "@typescript-eslint/visitor-keys": "5.45.0" + "@typescript-eslint/types": "5.50.0", + "@typescript-eslint/visitor-keys": "5.50.0" } }, "@typescript-eslint/type-utils": { @@ -17237,19 +17237,19 @@ } }, "@typescript-eslint/types": { - "version": "5.45.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.45.0.tgz", - "integrity": "sha512-QQij+u/vgskA66azc9dCmx+rev79PzX8uDHpsqSjEFtfF2gBUTRCpvYMh2gw2ghkJabNkPlSUCimsyBEQZd1DA==", + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.50.0.tgz", + "integrity": "sha512-atruOuJpir4OtyNdKahiHZobPKFvZnBnfDiyEaBf6d9vy9visE7gDjlmhl+y29uxZ2ZDgvXijcungGFjGGex7w==", "dev": true }, "@typescript-eslint/typescript-estree": { - "version": "5.45.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.45.0.tgz", - "integrity": "sha512-maRhLGSzqUpFcZgXxg1qc/+H0bT36lHK4APhp0AEUVrpSwXiRAomm/JGjSG+kNUio5kAa3uekCYu/47cnGn5EQ==", + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.50.0.tgz", + "integrity": "sha512-Gq4zapso+OtIZlv8YNAStFtT6d05zyVCK7Fx3h5inlLBx2hWuc/0465C2mg/EQDDU2LKe52+/jN4f0g9bd+kow==", "dev": true, "requires": { - "@typescript-eslint/types": "5.45.0", - "@typescript-eslint/visitor-keys": "5.45.0", + "@typescript-eslint/types": "5.50.0", + "@typescript-eslint/visitor-keys": "5.50.0", "debug": "^4.3.4", "globby": "^11.1.0", "is-glob": "^4.0.3", @@ -17317,12 +17317,12 @@ } }, "@typescript-eslint/visitor-keys": { - "version": "5.45.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.45.0.tgz", - "integrity": "sha512-jc6Eccbn2RtQPr1s7th6jJWQHBHI6GBVQkCHoJFQ5UreaKm59Vxw+ynQUPPY2u2Amquc+7tmEoC2G52ApsGNNg==", + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.50.0.tgz", + "integrity": "sha512-cdMeD9HGu6EXIeGOh2yVW6oGf9wq8asBgZx7nsR/D36gTfQ0odE5kcRYe5M81vjEFAcPeugXrHg78Imu55F6gg==", "dev": true, "requires": { - "@typescript-eslint/types": "5.45.0", + "@typescript-eslint/types": "5.50.0", "eslint-visitor-keys": "^3.3.0" } }, diff --git a/website/package.json b/website/package.json index 5d79a76c38f..ed778d065a4 100644 --- a/website/package.json +++ b/website/package.json @@ -53,7 +53,7 @@ "@types/react-helmet": "^6.1.6", "@types/react-router-dom": "^5.3.3", "@typescript-eslint/eslint-plugin": "^5.47.1", - "@typescript-eslint/parser": "^5.45.0", + "@typescript-eslint/parser": "^5.50.0", "dir-compare": "^4.0.0", "prettier": "2.8.1", "typescript": "^4.8.3" From 2b7856823e7e316dc96ccb0dda5ffdcbf2db3ef3 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 1 Feb 2023 23:38:27 +0900 Subject: [PATCH 25/76] Bump jetli/trunk-action from 0.2.0 to 0.4.0 (#3106) Bumps [jetli/trunk-action](https://github.com/jetli/trunk-action) from 0.2.0 to 0.4.0. - [Release notes](https://github.com/jetli/trunk-action/releases) - [Commits](https://github.com/jetli/trunk-action/compare/v0.2.0...v0.4.0) --- updated-dependencies: - dependency-name: jetli/trunk-action dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- .github/workflows/publish-examples.yml | 2 +- .github/workflows/size-cmp.yml | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/publish-examples.yml b/.github/workflows/publish-examples.yml index c8c2a74fef2..6637eb96566 100644 --- a/.github/workflows/publish-examples.yml +++ b/.github/workflows/publish-examples.yml @@ -26,7 +26,7 @@ jobs: - uses: Swatinem/rust-cache@v2 - - uses: jetli/trunk-action@v0.2.0 + - uses: jetli/trunk-action@v0.4.0 with: version: 'latest' diff --git a/.github/workflows/size-cmp.yml b/.github/workflows/size-cmp.yml index 42eeadef941..fb935523a4e 100644 --- a/.github/workflows/size-cmp.yml +++ b/.github/workflows/size-cmp.yml @@ -49,7 +49,7 @@ jobs: key: pr - name: Setup Trunk - uses: jetli/trunk-action@v0.2.0 + uses: jetli/trunk-action@v0.4.0 with: version: 'latest' From 5ec6689fc8f9cf4ecb3f510c9d8bb12b9ec071d9 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 1 Feb 2023 23:40:27 +0900 Subject: [PATCH 26/76] Bump @docusaurus/core from 2.2.0 to 2.3.0 in /website (#3102) Bumps [@docusaurus/core](https://github.com/facebook/docusaurus/tree/HEAD/packages/docusaurus) from 2.2.0 to 2.3.0. - [Release notes](https://github.com/facebook/docusaurus/releases) - [Changelog](https://github.com/facebook/docusaurus/blob/main/CHANGELOG.md) - [Commits](https://github.com/facebook/docusaurus/commits/v2.3.0/packages/docusaurus) --- updated-dependencies: - dependency-name: "@docusaurus/core" dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- website/package-lock.json | 1221 +++++++++++++++++++++++++++++++++---- website/package.json | 2 +- 2 files changed, 1090 insertions(+), 133 deletions(-) diff --git a/website/package-lock.json b/website/package-lock.json index ea202faa755..86f99efa7e5 100644 --- a/website/package-lock.json +++ b/website/package-lock.json @@ -8,7 +8,7 @@ "name": "yew-docs", "version": "0.0.0", "dependencies": { - "@docusaurus/core": "~2.2.0", + "@docusaurus/core": "~2.3.0", "@docusaurus/plugin-client-redirects": "~2.2.0", "@docusaurus/plugin-content-docs": "~2.2.0", "@docusaurus/plugin-content-pages": "~2.2.0", @@ -1842,9 +1842,9 @@ } }, "node_modules/@docusaurus/core": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/@docusaurus/core/-/core-2.2.0.tgz", - "integrity": "sha512-Vd6XOluKQqzG12fEs9prJgDtyn6DPok9vmUWDR2E6/nV5Fl9SVkhEQOBxwObjk3kQh7OY7vguFaLh0jqdApWsA==", + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@docusaurus/core/-/core-2.3.0.tgz", + "integrity": "sha512-2AU5HfKyExO+/mi41SBnx5uY0aGZFXr3D93wntBY4lN1gsDKUpi7EE4lPBAXm9CoH4Pw6N24yDHy9CPR3sh/uA==", "dependencies": { "@babel/core": "^7.18.6", "@babel/generator": "^7.18.7", @@ -1856,13 +1856,13 @@ "@babel/runtime": "^7.18.6", "@babel/runtime-corejs3": "^7.18.6", "@babel/traverse": "^7.18.8", - "@docusaurus/cssnano-preset": "2.2.0", - "@docusaurus/logger": "2.2.0", - "@docusaurus/mdx-loader": "2.2.0", + "@docusaurus/cssnano-preset": "2.3.0", + "@docusaurus/logger": "2.3.0", + "@docusaurus/mdx-loader": "2.3.0", "@docusaurus/react-loadable": "5.5.2", - "@docusaurus/utils": "2.2.0", - "@docusaurus/utils-common": "2.2.0", - "@docusaurus/utils-validation": "2.2.0", + "@docusaurus/utils": "2.3.0", + "@docusaurus/utils-common": "2.3.0", + "@docusaurus/utils-validation": "2.3.0", "@slorber/static-site-generator-webpack-plugin": "^4.0.7", "@svgr/webpack": "^6.2.1", "autoprefixer": "^10.4.7", @@ -1930,9 +1930,9 @@ } }, "node_modules/@docusaurus/core/node_modules/@docusaurus/logger": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/@docusaurus/logger/-/logger-2.2.0.tgz", - "integrity": "sha512-DF3j1cA5y2nNsu/vk8AG7xwpZu6f5MKkPPMaaIbgXLnWGfm6+wkOeW7kNrxnM95YOhKUkJUophX69nGUnLsm0A==", + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@docusaurus/logger/-/logger-2.3.0.tgz", + "integrity": "sha512-GO8s+FJpNT0vwt6kr/BZ/B1iB8EgHH/CF590i55Epy3TP2baQHGEHcAnQWvz5067OXIEke7Sa8sUNi0V9FrcJw==", "dependencies": { "chalk": "^4.1.2", "tslib": "^2.4.0" @@ -1942,14 +1942,14 @@ } }, "node_modules/@docusaurus/core/node_modules/@docusaurus/mdx-loader": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/@docusaurus/mdx-loader/-/mdx-loader-2.2.0.tgz", - "integrity": "sha512-X2bzo3T0jW0VhUU+XdQofcEeozXOTmKQMvc8tUnWRdTnCvj4XEcBVdC3g+/jftceluiwSTNRAX4VBOJdNt18jA==", + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@docusaurus/mdx-loader/-/mdx-loader-2.3.0.tgz", + "integrity": "sha512-uxownG7dlg/l19rTIfUP0KDsbI8lTCgziWsdubMcWpGvOgXgm1p4mKSmWPzAwkRENn+un4L8DBhl3j1toeJy1A==", "dependencies": { "@babel/parser": "^7.18.8", "@babel/traverse": "^7.18.8", - "@docusaurus/logger": "2.2.0", - "@docusaurus/utils": "2.2.0", + "@docusaurus/logger": "2.3.0", + "@docusaurus/utils": "2.3.0", "@mdx-js/mdx": "^1.6.22", "escape-html": "^1.0.3", "file-loader": "^6.2.0", @@ -1973,12 +1973,13 @@ } }, "node_modules/@docusaurus/core/node_modules/@docusaurus/utils": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/@docusaurus/utils/-/utils-2.2.0.tgz", - "integrity": "sha512-oNk3cjvx7Tt1Lgh/aeZAmFpGV2pDr5nHKrBVx6hTkzGhrnMuQqLt6UPlQjdYQ3QHXwyF/ZtZMO1D5Pfi0lu7SA==", + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@docusaurus/utils/-/utils-2.3.0.tgz", + "integrity": "sha512-6+GCurDsePHHbLM3ktcjv8N4zrjgrl1O7gOQNG4UMktcwHssFFVm+geVcB4M8siOmwUjV2VaNrp0hpGy8DOQHw==", "dependencies": { - "@docusaurus/logger": "2.2.0", + "@docusaurus/logger": "2.3.0", "@svgr/webpack": "^6.2.1", + "escape-string-regexp": "^4.0.0", "file-loader": "^6.2.0", "fs-extra": "^10.1.0", "github-slugger": "^1.4.0", @@ -2006,9 +2007,9 @@ } }, "node_modules/@docusaurus/core/node_modules/@docusaurus/utils-common": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/@docusaurus/utils-common/-/utils-common-2.2.0.tgz", - "integrity": "sha512-qebnerHp+cyovdUseDQyYFvMW1n1nv61zGe5JJfoNQUnjKuApch3IVsz+/lZ9a38pId8kqehC1Ao2bW/s0ntDA==", + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@docusaurus/utils-common/-/utils-common-2.3.0.tgz", + "integrity": "sha512-nu5An+26FS7SQTwvyFR4g9lw3NU1u2RLcxJPZF+NCOG8Ne96ciuQosa7+N1kllm/heEJqfTaAUD0sFxpTZrDtw==", "dependencies": { "tslib": "^2.4.0" }, @@ -2025,12 +2026,12 @@ } }, "node_modules/@docusaurus/core/node_modules/@docusaurus/utils-validation": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/@docusaurus/utils-validation/-/utils-validation-2.2.0.tgz", - "integrity": "sha512-I1hcsG3yoCkasOL5qQAYAfnmVoLei7apugT6m4crQjmDGxq+UkiRrq55UqmDDyZlac/6ax/JC0p+usZ6W4nVyg==", + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@docusaurus/utils-validation/-/utils-validation-2.3.0.tgz", + "integrity": "sha512-TBJCLqwAoiQQJ6dbgBpuLvzsn/XiTgbZkd6eJFUIQYLb1d473Zv58QrHXVmVQDLWiCgmJpHW2LpMfumTpCDgJw==", "dependencies": { - "@docusaurus/logger": "2.2.0", - "@docusaurus/utils": "2.2.0", + "@docusaurus/logger": "2.3.0", + "@docusaurus/utils": "2.3.0", "joi": "^17.6.0", "js-yaml": "^4.1.0", "tslib": "^2.4.0" @@ -2040,9 +2041,9 @@ } }, "node_modules/@docusaurus/cssnano-preset": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/@docusaurus/cssnano-preset/-/cssnano-preset-2.2.0.tgz", - "integrity": "sha512-mAAwCo4n66TMWBH1kXnHVZsakW9VAXJzTO4yZukuL3ro4F+JtkMwKfh42EG75K/J/YIFQG5I/Bzy0UH/hFxaTg==", + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@docusaurus/cssnano-preset/-/cssnano-preset-2.3.0.tgz", + "integrity": "sha512-igmsXc1Q95lMeq07A1xua0/5wOPygDQ/ENSV7VVbiGhnvMv4gzkba8ZvbAtc7PmqK+kpYRfPzNCOk0GnQCvibg==", "dependencies": { "cssnano-preset-advanced": "^5.3.8", "postcss": "^8.4.14", @@ -2157,6 +2158,108 @@ "react-dom": "^16.8.4 || ^17.0.0" } }, + "node_modules/@docusaurus/plugin-client-redirects/node_modules/@docusaurus/core": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/core/-/core-2.2.0.tgz", + "integrity": "sha512-Vd6XOluKQqzG12fEs9prJgDtyn6DPok9vmUWDR2E6/nV5Fl9SVkhEQOBxwObjk3kQh7OY7vguFaLh0jqdApWsA==", + "dependencies": { + "@babel/core": "^7.18.6", + "@babel/generator": "^7.18.7", + "@babel/plugin-syntax-dynamic-import": "^7.8.3", + "@babel/plugin-transform-runtime": "^7.18.6", + "@babel/preset-env": "^7.18.6", + "@babel/preset-react": "^7.18.6", + "@babel/preset-typescript": "^7.18.6", + "@babel/runtime": "^7.18.6", + "@babel/runtime-corejs3": "^7.18.6", + "@babel/traverse": "^7.18.8", + "@docusaurus/cssnano-preset": "2.2.0", + "@docusaurus/logger": "2.2.0", + "@docusaurus/mdx-loader": "2.2.0", + "@docusaurus/react-loadable": "5.5.2", + "@docusaurus/utils": "2.2.0", + "@docusaurus/utils-common": "2.2.0", + "@docusaurus/utils-validation": "2.2.0", + "@slorber/static-site-generator-webpack-plugin": "^4.0.7", + "@svgr/webpack": "^6.2.1", + "autoprefixer": "^10.4.7", + "babel-loader": "^8.2.5", + "babel-plugin-dynamic-import-node": "^2.3.3", + "boxen": "^6.2.1", + "chalk": "^4.1.2", + "chokidar": "^3.5.3", + "clean-css": "^5.3.0", + "cli-table3": "^0.6.2", + "combine-promises": "^1.1.0", + "commander": "^5.1.0", + "copy-webpack-plugin": "^11.0.0", + "core-js": "^3.23.3", + "css-loader": "^6.7.1", + "css-minimizer-webpack-plugin": "^4.0.0", + "cssnano": "^5.1.12", + "del": "^6.1.1", + "detect-port": "^1.3.0", + "escape-html": "^1.0.3", + "eta": "^1.12.3", + "file-loader": "^6.2.0", + "fs-extra": "^10.1.0", + "html-minifier-terser": "^6.1.0", + "html-tags": "^3.2.0", + "html-webpack-plugin": "^5.5.0", + "import-fresh": "^3.3.0", + "leven": "^3.1.0", + "lodash": "^4.17.21", + "mini-css-extract-plugin": "^2.6.1", + "postcss": "^8.4.14", + "postcss-loader": "^7.0.0", + "prompts": "^2.4.2", + "react-dev-utils": "^12.0.1", + "react-helmet-async": "^1.3.0", + "react-loadable": "npm:@docusaurus/react-loadable@5.5.2", + "react-loadable-ssr-addon-v5-slorber": "^1.0.1", + "react-router": "^5.3.3", + "react-router-config": "^5.1.1", + "react-router-dom": "^5.3.3", + "rtl-detect": "^1.0.4", + "semver": "^7.3.7", + "serve-handler": "^6.1.3", + "shelljs": "^0.8.5", + "terser-webpack-plugin": "^5.3.3", + "tslib": "^2.4.0", + "update-notifier": "^5.1.0", + "url-loader": "^4.1.1", + "wait-on": "^6.0.1", + "webpack": "^5.73.0", + "webpack-bundle-analyzer": "^4.5.0", + "webpack-dev-server": "^4.9.3", + "webpack-merge": "^5.8.0", + "webpackbar": "^5.0.2" + }, + "bin": { + "docusaurus": "bin/docusaurus.mjs" + }, + "engines": { + "node": ">=16.14" + }, + "peerDependencies": { + "react": "^16.8.4 || ^17.0.0", + "react-dom": "^16.8.4 || ^17.0.0" + } + }, + "node_modules/@docusaurus/plugin-client-redirects/node_modules/@docusaurus/cssnano-preset": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/cssnano-preset/-/cssnano-preset-2.2.0.tgz", + "integrity": "sha512-mAAwCo4n66TMWBH1kXnHVZsakW9VAXJzTO4yZukuL3ro4F+JtkMwKfh42EG75K/J/YIFQG5I/Bzy0UH/hFxaTg==", + "dependencies": { + "cssnano-preset-advanced": "^5.3.8", + "postcss": "^8.4.14", + "postcss-sort-media-queries": "^4.2.1", + "tslib": "^2.4.0" + }, + "engines": { + "node": ">=16.14" + } + }, "node_modules/@docusaurus/plugin-client-redirects/node_modules/@docusaurus/logger": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/@docusaurus/logger/-/logger-2.2.0.tgz", @@ -2169,6 +2272,37 @@ "node": ">=16.14" } }, + "node_modules/@docusaurus/plugin-client-redirects/node_modules/@docusaurus/mdx-loader": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/mdx-loader/-/mdx-loader-2.2.0.tgz", + "integrity": "sha512-X2bzo3T0jW0VhUU+XdQofcEeozXOTmKQMvc8tUnWRdTnCvj4XEcBVdC3g+/jftceluiwSTNRAX4VBOJdNt18jA==", + "dependencies": { + "@babel/parser": "^7.18.8", + "@babel/traverse": "^7.18.8", + "@docusaurus/logger": "2.2.0", + "@docusaurus/utils": "2.2.0", + "@mdx-js/mdx": "^1.6.22", + "escape-html": "^1.0.3", + "file-loader": "^6.2.0", + "fs-extra": "^10.1.0", + "image-size": "^1.0.1", + "mdast-util-to-string": "^2.0.0", + "remark-emoji": "^2.2.0", + "stringify-object": "^3.3.0", + "tslib": "^2.4.0", + "unified": "^9.2.2", + "unist-util-visit": "^2.0.3", + "url-loader": "^4.1.1", + "webpack": "^5.73.0" + }, + "engines": { + "node": ">=16.14" + }, + "peerDependencies": { + "react": "^16.8.4 || ^17.0.0", + "react-dom": "^16.8.4 || ^17.0.0" + } + }, "node_modules/@docusaurus/plugin-client-redirects/node_modules/@docusaurus/utils": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/@docusaurus/utils/-/utils-2.2.0.tgz", @@ -2398,43 +2532,145 @@ "react-dom": "^16.8.4 || ^17.0.0" } }, - "node_modules/@docusaurus/plugin-content-docs/node_modules/@docusaurus/logger": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/@docusaurus/logger/-/logger-2.2.0.tgz", - "integrity": "sha512-DF3j1cA5y2nNsu/vk8AG7xwpZu6f5MKkPPMaaIbgXLnWGfm6+wkOeW7kNrxnM95YOhKUkJUophX69nGUnLsm0A==", - "dependencies": { - "chalk": "^4.1.2", - "tslib": "^2.4.0" - }, - "engines": { - "node": ">=16.14" - } - }, - "node_modules/@docusaurus/plugin-content-docs/node_modules/@docusaurus/mdx-loader": { + "node_modules/@docusaurus/plugin-content-docs/node_modules/@docusaurus/core": { "version": "2.2.0", - "resolved": "https://registry.npmjs.org/@docusaurus/mdx-loader/-/mdx-loader-2.2.0.tgz", - "integrity": "sha512-X2bzo3T0jW0VhUU+XdQofcEeozXOTmKQMvc8tUnWRdTnCvj4XEcBVdC3g+/jftceluiwSTNRAX4VBOJdNt18jA==", + "resolved": "https://registry.npmjs.org/@docusaurus/core/-/core-2.2.0.tgz", + "integrity": "sha512-Vd6XOluKQqzG12fEs9prJgDtyn6DPok9vmUWDR2E6/nV5Fl9SVkhEQOBxwObjk3kQh7OY7vguFaLh0jqdApWsA==", "dependencies": { - "@babel/parser": "^7.18.8", + "@babel/core": "^7.18.6", + "@babel/generator": "^7.18.7", + "@babel/plugin-syntax-dynamic-import": "^7.8.3", + "@babel/plugin-transform-runtime": "^7.18.6", + "@babel/preset-env": "^7.18.6", + "@babel/preset-react": "^7.18.6", + "@babel/preset-typescript": "^7.18.6", + "@babel/runtime": "^7.18.6", + "@babel/runtime-corejs3": "^7.18.6", "@babel/traverse": "^7.18.8", + "@docusaurus/cssnano-preset": "2.2.0", "@docusaurus/logger": "2.2.0", + "@docusaurus/mdx-loader": "2.2.0", + "@docusaurus/react-loadable": "5.5.2", "@docusaurus/utils": "2.2.0", - "@mdx-js/mdx": "^1.6.22", + "@docusaurus/utils-common": "2.2.0", + "@docusaurus/utils-validation": "2.2.0", + "@slorber/static-site-generator-webpack-plugin": "^4.0.7", + "@svgr/webpack": "^6.2.1", + "autoprefixer": "^10.4.7", + "babel-loader": "^8.2.5", + "babel-plugin-dynamic-import-node": "^2.3.3", + "boxen": "^6.2.1", + "chalk": "^4.1.2", + "chokidar": "^3.5.3", + "clean-css": "^5.3.0", + "cli-table3": "^0.6.2", + "combine-promises": "^1.1.0", + "commander": "^5.1.0", + "copy-webpack-plugin": "^11.0.0", + "core-js": "^3.23.3", + "css-loader": "^6.7.1", + "css-minimizer-webpack-plugin": "^4.0.0", + "cssnano": "^5.1.12", + "del": "^6.1.1", + "detect-port": "^1.3.0", "escape-html": "^1.0.3", + "eta": "^1.12.3", "file-loader": "^6.2.0", "fs-extra": "^10.1.0", - "image-size": "^1.0.1", - "mdast-util-to-string": "^2.0.0", - "remark-emoji": "^2.2.0", - "stringify-object": "^3.3.0", + "html-minifier-terser": "^6.1.0", + "html-tags": "^3.2.0", + "html-webpack-plugin": "^5.5.0", + "import-fresh": "^3.3.0", + "leven": "^3.1.0", + "lodash": "^4.17.21", + "mini-css-extract-plugin": "^2.6.1", + "postcss": "^8.4.14", + "postcss-loader": "^7.0.0", + "prompts": "^2.4.2", + "react-dev-utils": "^12.0.1", + "react-helmet-async": "^1.3.0", + "react-loadable": "npm:@docusaurus/react-loadable@5.5.2", + "react-loadable-ssr-addon-v5-slorber": "^1.0.1", + "react-router": "^5.3.3", + "react-router-config": "^5.1.1", + "react-router-dom": "^5.3.3", + "rtl-detect": "^1.0.4", + "semver": "^7.3.7", + "serve-handler": "^6.1.3", + "shelljs": "^0.8.5", + "terser-webpack-plugin": "^5.3.3", "tslib": "^2.4.0", - "unified": "^9.2.2", - "unist-util-visit": "^2.0.3", + "update-notifier": "^5.1.0", "url-loader": "^4.1.1", - "webpack": "^5.73.0" - }, - "engines": { - "node": ">=16.14" + "wait-on": "^6.0.1", + "webpack": "^5.73.0", + "webpack-bundle-analyzer": "^4.5.0", + "webpack-dev-server": "^4.9.3", + "webpack-merge": "^5.8.0", + "webpackbar": "^5.0.2" + }, + "bin": { + "docusaurus": "bin/docusaurus.mjs" + }, + "engines": { + "node": ">=16.14" + }, + "peerDependencies": { + "react": "^16.8.4 || ^17.0.0", + "react-dom": "^16.8.4 || ^17.0.0" + } + }, + "node_modules/@docusaurus/plugin-content-docs/node_modules/@docusaurus/cssnano-preset": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/cssnano-preset/-/cssnano-preset-2.2.0.tgz", + "integrity": "sha512-mAAwCo4n66TMWBH1kXnHVZsakW9VAXJzTO4yZukuL3ro4F+JtkMwKfh42EG75K/J/YIFQG5I/Bzy0UH/hFxaTg==", + "dependencies": { + "cssnano-preset-advanced": "^5.3.8", + "postcss": "^8.4.14", + "postcss-sort-media-queries": "^4.2.1", + "tslib": "^2.4.0" + }, + "engines": { + "node": ">=16.14" + } + }, + "node_modules/@docusaurus/plugin-content-docs/node_modules/@docusaurus/logger": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/logger/-/logger-2.2.0.tgz", + "integrity": "sha512-DF3j1cA5y2nNsu/vk8AG7xwpZu6f5MKkPPMaaIbgXLnWGfm6+wkOeW7kNrxnM95YOhKUkJUophX69nGUnLsm0A==", + "dependencies": { + "chalk": "^4.1.2", + "tslib": "^2.4.0" + }, + "engines": { + "node": ">=16.14" + } + }, + "node_modules/@docusaurus/plugin-content-docs/node_modules/@docusaurus/mdx-loader": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/mdx-loader/-/mdx-loader-2.2.0.tgz", + "integrity": "sha512-X2bzo3T0jW0VhUU+XdQofcEeozXOTmKQMvc8tUnWRdTnCvj4XEcBVdC3g+/jftceluiwSTNRAX4VBOJdNt18jA==", + "dependencies": { + "@babel/parser": "^7.18.8", + "@babel/traverse": "^7.18.8", + "@docusaurus/logger": "2.2.0", + "@docusaurus/utils": "2.2.0", + "@mdx-js/mdx": "^1.6.22", + "escape-html": "^1.0.3", + "file-loader": "^6.2.0", + "fs-extra": "^10.1.0", + "image-size": "^1.0.1", + "mdast-util-to-string": "^2.0.0", + "remark-emoji": "^2.2.0", + "stringify-object": "^3.3.0", + "tslib": "^2.4.0", + "unified": "^9.2.2", + "unist-util-visit": "^2.0.3", + "url-loader": "^4.1.1", + "webpack": "^5.73.0" + }, + "engines": { + "node": ">=16.14" }, "peerDependencies": { "react": "^16.8.4 || ^17.0.0", @@ -2493,6 +2729,25 @@ } } }, + "node_modules/@docusaurus/plugin-content-docs/node_modules/@docusaurus/utils-common": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/utils-common/-/utils-common-2.2.0.tgz", + "integrity": "sha512-qebnerHp+cyovdUseDQyYFvMW1n1nv61zGe5JJfoNQUnjKuApch3IVsz+/lZ9a38pId8kqehC1Ao2bW/s0ntDA==", + "dependencies": { + "tslib": "^2.4.0" + }, + "engines": { + "node": ">=16.14" + }, + "peerDependencies": { + "@docusaurus/types": "*" + }, + "peerDependenciesMeta": { + "@docusaurus/types": { + "optional": true + } + } + }, "node_modules/@docusaurus/plugin-content-docs/node_modules/@docusaurus/utils-validation": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/@docusaurus/utils-validation/-/utils-validation-2.2.0.tgz", @@ -2530,6 +2785,108 @@ "react-dom": "^16.8.4 || ^17.0.0" } }, + "node_modules/@docusaurus/plugin-content-pages/node_modules/@docusaurus/core": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/core/-/core-2.2.0.tgz", + "integrity": "sha512-Vd6XOluKQqzG12fEs9prJgDtyn6DPok9vmUWDR2E6/nV5Fl9SVkhEQOBxwObjk3kQh7OY7vguFaLh0jqdApWsA==", + "dependencies": { + "@babel/core": "^7.18.6", + "@babel/generator": "^7.18.7", + "@babel/plugin-syntax-dynamic-import": "^7.8.3", + "@babel/plugin-transform-runtime": "^7.18.6", + "@babel/preset-env": "^7.18.6", + "@babel/preset-react": "^7.18.6", + "@babel/preset-typescript": "^7.18.6", + "@babel/runtime": "^7.18.6", + "@babel/runtime-corejs3": "^7.18.6", + "@babel/traverse": "^7.18.8", + "@docusaurus/cssnano-preset": "2.2.0", + "@docusaurus/logger": "2.2.0", + "@docusaurus/mdx-loader": "2.2.0", + "@docusaurus/react-loadable": "5.5.2", + "@docusaurus/utils": "2.2.0", + "@docusaurus/utils-common": "2.2.0", + "@docusaurus/utils-validation": "2.2.0", + "@slorber/static-site-generator-webpack-plugin": "^4.0.7", + "@svgr/webpack": "^6.2.1", + "autoprefixer": "^10.4.7", + "babel-loader": "^8.2.5", + "babel-plugin-dynamic-import-node": "^2.3.3", + "boxen": "^6.2.1", + "chalk": "^4.1.2", + "chokidar": "^3.5.3", + "clean-css": "^5.3.0", + "cli-table3": "^0.6.2", + "combine-promises": "^1.1.0", + "commander": "^5.1.0", + "copy-webpack-plugin": "^11.0.0", + "core-js": "^3.23.3", + "css-loader": "^6.7.1", + "css-minimizer-webpack-plugin": "^4.0.0", + "cssnano": "^5.1.12", + "del": "^6.1.1", + "detect-port": "^1.3.0", + "escape-html": "^1.0.3", + "eta": "^1.12.3", + "file-loader": "^6.2.0", + "fs-extra": "^10.1.0", + "html-minifier-terser": "^6.1.0", + "html-tags": "^3.2.0", + "html-webpack-plugin": "^5.5.0", + "import-fresh": "^3.3.0", + "leven": "^3.1.0", + "lodash": "^4.17.21", + "mini-css-extract-plugin": "^2.6.1", + "postcss": "^8.4.14", + "postcss-loader": "^7.0.0", + "prompts": "^2.4.2", + "react-dev-utils": "^12.0.1", + "react-helmet-async": "^1.3.0", + "react-loadable": "npm:@docusaurus/react-loadable@5.5.2", + "react-loadable-ssr-addon-v5-slorber": "^1.0.1", + "react-router": "^5.3.3", + "react-router-config": "^5.1.1", + "react-router-dom": "^5.3.3", + "rtl-detect": "^1.0.4", + "semver": "^7.3.7", + "serve-handler": "^6.1.3", + "shelljs": "^0.8.5", + "terser-webpack-plugin": "^5.3.3", + "tslib": "^2.4.0", + "update-notifier": "^5.1.0", + "url-loader": "^4.1.1", + "wait-on": "^6.0.1", + "webpack": "^5.73.0", + "webpack-bundle-analyzer": "^4.5.0", + "webpack-dev-server": "^4.9.3", + "webpack-merge": "^5.8.0", + "webpackbar": "^5.0.2" + }, + "bin": { + "docusaurus": "bin/docusaurus.mjs" + }, + "engines": { + "node": ">=16.14" + }, + "peerDependencies": { + "react": "^16.8.4 || ^17.0.0", + "react-dom": "^16.8.4 || ^17.0.0" + } + }, + "node_modules/@docusaurus/plugin-content-pages/node_modules/@docusaurus/cssnano-preset": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/cssnano-preset/-/cssnano-preset-2.2.0.tgz", + "integrity": "sha512-mAAwCo4n66TMWBH1kXnHVZsakW9VAXJzTO4yZukuL3ro4F+JtkMwKfh42EG75K/J/YIFQG5I/Bzy0UH/hFxaTg==", + "dependencies": { + "cssnano-preset-advanced": "^5.3.8", + "postcss": "^8.4.14", + "postcss-sort-media-queries": "^4.2.1", + "tslib": "^2.4.0" + }, + "engines": { + "node": ">=16.14" + } + }, "node_modules/@docusaurus/plugin-content-pages/node_modules/@docusaurus/logger": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/@docusaurus/logger/-/logger-2.2.0.tgz", @@ -2625,6 +2982,25 @@ } } }, + "node_modules/@docusaurus/plugin-content-pages/node_modules/@docusaurus/utils-common": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/utils-common/-/utils-common-2.2.0.tgz", + "integrity": "sha512-qebnerHp+cyovdUseDQyYFvMW1n1nv61zGe5JJfoNQUnjKuApch3IVsz+/lZ9a38pId8kqehC1Ao2bW/s0ntDA==", + "dependencies": { + "tslib": "^2.4.0" + }, + "engines": { + "node": ">=16.14" + }, + "peerDependencies": { + "@docusaurus/types": "*" + }, + "peerDependenciesMeta": { + "@docusaurus/types": { + "optional": true + } + } + }, "node_modules/@docusaurus/plugin-content-pages/node_modules/@docusaurus/utils-validation": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/@docusaurus/utils-validation/-/utils-validation-2.2.0.tgz", @@ -2658,6 +3034,108 @@ "react-dom": "^16.8.4 || ^17.0.0" } }, + "node_modules/@docusaurus/plugin-google-analytics/node_modules/@docusaurus/core": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/core/-/core-2.2.0.tgz", + "integrity": "sha512-Vd6XOluKQqzG12fEs9prJgDtyn6DPok9vmUWDR2E6/nV5Fl9SVkhEQOBxwObjk3kQh7OY7vguFaLh0jqdApWsA==", + "dependencies": { + "@babel/core": "^7.18.6", + "@babel/generator": "^7.18.7", + "@babel/plugin-syntax-dynamic-import": "^7.8.3", + "@babel/plugin-transform-runtime": "^7.18.6", + "@babel/preset-env": "^7.18.6", + "@babel/preset-react": "^7.18.6", + "@babel/preset-typescript": "^7.18.6", + "@babel/runtime": "^7.18.6", + "@babel/runtime-corejs3": "^7.18.6", + "@babel/traverse": "^7.18.8", + "@docusaurus/cssnano-preset": "2.2.0", + "@docusaurus/logger": "2.2.0", + "@docusaurus/mdx-loader": "2.2.0", + "@docusaurus/react-loadable": "5.5.2", + "@docusaurus/utils": "2.2.0", + "@docusaurus/utils-common": "2.2.0", + "@docusaurus/utils-validation": "2.2.0", + "@slorber/static-site-generator-webpack-plugin": "^4.0.7", + "@svgr/webpack": "^6.2.1", + "autoprefixer": "^10.4.7", + "babel-loader": "^8.2.5", + "babel-plugin-dynamic-import-node": "^2.3.3", + "boxen": "^6.2.1", + "chalk": "^4.1.2", + "chokidar": "^3.5.3", + "clean-css": "^5.3.0", + "cli-table3": "^0.6.2", + "combine-promises": "^1.1.0", + "commander": "^5.1.0", + "copy-webpack-plugin": "^11.0.0", + "core-js": "^3.23.3", + "css-loader": "^6.7.1", + "css-minimizer-webpack-plugin": "^4.0.0", + "cssnano": "^5.1.12", + "del": "^6.1.1", + "detect-port": "^1.3.0", + "escape-html": "^1.0.3", + "eta": "^1.12.3", + "file-loader": "^6.2.0", + "fs-extra": "^10.1.0", + "html-minifier-terser": "^6.1.0", + "html-tags": "^3.2.0", + "html-webpack-plugin": "^5.5.0", + "import-fresh": "^3.3.0", + "leven": "^3.1.0", + "lodash": "^4.17.21", + "mini-css-extract-plugin": "^2.6.1", + "postcss": "^8.4.14", + "postcss-loader": "^7.0.0", + "prompts": "^2.4.2", + "react-dev-utils": "^12.0.1", + "react-helmet-async": "^1.3.0", + "react-loadable": "npm:@docusaurus/react-loadable@5.5.2", + "react-loadable-ssr-addon-v5-slorber": "^1.0.1", + "react-router": "^5.3.3", + "react-router-config": "^5.1.1", + "react-router-dom": "^5.3.3", + "rtl-detect": "^1.0.4", + "semver": "^7.3.7", + "serve-handler": "^6.1.3", + "shelljs": "^0.8.5", + "terser-webpack-plugin": "^5.3.3", + "tslib": "^2.4.0", + "update-notifier": "^5.1.0", + "url-loader": "^4.1.1", + "wait-on": "^6.0.1", + "webpack": "^5.73.0", + "webpack-bundle-analyzer": "^4.5.0", + "webpack-dev-server": "^4.9.3", + "webpack-merge": "^5.8.0", + "webpackbar": "^5.0.2" + }, + "bin": { + "docusaurus": "bin/docusaurus.mjs" + }, + "engines": { + "node": ">=16.14" + }, + "peerDependencies": { + "react": "^16.8.4 || ^17.0.0", + "react-dom": "^16.8.4 || ^17.0.0" + } + }, + "node_modules/@docusaurus/plugin-google-analytics/node_modules/@docusaurus/cssnano-preset": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/cssnano-preset/-/cssnano-preset-2.2.0.tgz", + "integrity": "sha512-mAAwCo4n66TMWBH1kXnHVZsakW9VAXJzTO4yZukuL3ro4F+JtkMwKfh42EG75K/J/YIFQG5I/Bzy0UH/hFxaTg==", + "dependencies": { + "cssnano-preset-advanced": "^5.3.8", + "postcss": "^8.4.14", + "postcss-sort-media-queries": "^4.2.1", + "tslib": "^2.4.0" + }, + "engines": { + "node": ">=16.14" + } + }, "node_modules/@docusaurus/plugin-google-analytics/node_modules/@docusaurus/logger": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/@docusaurus/logger/-/logger-2.2.0.tgz", @@ -2670,6 +3148,37 @@ "node": ">=16.14" } }, + "node_modules/@docusaurus/plugin-google-analytics/node_modules/@docusaurus/mdx-loader": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/mdx-loader/-/mdx-loader-2.2.0.tgz", + "integrity": "sha512-X2bzo3T0jW0VhUU+XdQofcEeozXOTmKQMvc8tUnWRdTnCvj4XEcBVdC3g+/jftceluiwSTNRAX4VBOJdNt18jA==", + "dependencies": { + "@babel/parser": "^7.18.8", + "@babel/traverse": "^7.18.8", + "@docusaurus/logger": "2.2.0", + "@docusaurus/utils": "2.2.0", + "@mdx-js/mdx": "^1.6.22", + "escape-html": "^1.0.3", + "file-loader": "^6.2.0", + "fs-extra": "^10.1.0", + "image-size": "^1.0.1", + "mdast-util-to-string": "^2.0.0", + "remark-emoji": "^2.2.0", + "stringify-object": "^3.3.0", + "tslib": "^2.4.0", + "unified": "^9.2.2", + "unist-util-visit": "^2.0.3", + "url-loader": "^4.1.1", + "webpack": "^5.73.0" + }, + "engines": { + "node": ">=16.14" + }, + "peerDependencies": { + "react": "^16.8.4 || ^17.0.0", + "react-dom": "^16.8.4 || ^17.0.0" + } + }, "node_modules/@docusaurus/plugin-google-analytics/node_modules/@docusaurus/types": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/@docusaurus/types/-/types-2.2.0.tgz", @@ -2722,6 +3231,25 @@ } } }, + "node_modules/@docusaurus/plugin-google-analytics/node_modules/@docusaurus/utils-common": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/utils-common/-/utils-common-2.2.0.tgz", + "integrity": "sha512-qebnerHp+cyovdUseDQyYFvMW1n1nv61zGe5JJfoNQUnjKuApch3IVsz+/lZ9a38pId8kqehC1Ao2bW/s0ntDA==", + "dependencies": { + "tslib": "^2.4.0" + }, + "engines": { + "node": ">=16.14" + }, + "peerDependencies": { + "@docusaurus/types": "*" + }, + "peerDependenciesMeta": { + "@docusaurus/types": { + "optional": true + } + } + }, "node_modules/@docusaurus/plugin-google-analytics/node_modules/@docusaurus/utils-validation": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/@docusaurus/utils-validation/-/utils-validation-2.2.0.tgz", @@ -15206,9 +15734,9 @@ "optional": true }, "@docusaurus/core": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/@docusaurus/core/-/core-2.2.0.tgz", - "integrity": "sha512-Vd6XOluKQqzG12fEs9prJgDtyn6DPok9vmUWDR2E6/nV5Fl9SVkhEQOBxwObjk3kQh7OY7vguFaLh0jqdApWsA==", + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@docusaurus/core/-/core-2.3.0.tgz", + "integrity": "sha512-2AU5HfKyExO+/mi41SBnx5uY0aGZFXr3D93wntBY4lN1gsDKUpi7EE4lPBAXm9CoH4Pw6N24yDHy9CPR3sh/uA==", "requires": { "@babel/core": "^7.18.6", "@babel/generator": "^7.18.7", @@ -15220,13 +15748,13 @@ "@babel/runtime": "^7.18.6", "@babel/runtime-corejs3": "^7.18.6", "@babel/traverse": "^7.18.8", - "@docusaurus/cssnano-preset": "2.2.0", - "@docusaurus/logger": "2.2.0", - "@docusaurus/mdx-loader": "2.2.0", + "@docusaurus/cssnano-preset": "2.3.0", + "@docusaurus/logger": "2.3.0", + "@docusaurus/mdx-loader": "2.3.0", "@docusaurus/react-loadable": "5.5.2", - "@docusaurus/utils": "2.2.0", - "@docusaurus/utils-common": "2.2.0", - "@docusaurus/utils-validation": "2.2.0", + "@docusaurus/utils": "2.3.0", + "@docusaurus/utils-common": "2.3.0", + "@docusaurus/utils-validation": "2.3.0", "@slorber/static-site-generator-webpack-plugin": "^4.0.7", "@svgr/webpack": "^6.2.1", "autoprefixer": "^10.4.7", @@ -15284,23 +15812,23 @@ }, "dependencies": { "@docusaurus/logger": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/@docusaurus/logger/-/logger-2.2.0.tgz", - "integrity": "sha512-DF3j1cA5y2nNsu/vk8AG7xwpZu6f5MKkPPMaaIbgXLnWGfm6+wkOeW7kNrxnM95YOhKUkJUophX69nGUnLsm0A==", + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@docusaurus/logger/-/logger-2.3.0.tgz", + "integrity": "sha512-GO8s+FJpNT0vwt6kr/BZ/B1iB8EgHH/CF590i55Epy3TP2baQHGEHcAnQWvz5067OXIEke7Sa8sUNi0V9FrcJw==", "requires": { "chalk": "^4.1.2", "tslib": "^2.4.0" } }, "@docusaurus/mdx-loader": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/@docusaurus/mdx-loader/-/mdx-loader-2.2.0.tgz", - "integrity": "sha512-X2bzo3T0jW0VhUU+XdQofcEeozXOTmKQMvc8tUnWRdTnCvj4XEcBVdC3g+/jftceluiwSTNRAX4VBOJdNt18jA==", + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@docusaurus/mdx-loader/-/mdx-loader-2.3.0.tgz", + "integrity": "sha512-uxownG7dlg/l19rTIfUP0KDsbI8lTCgziWsdubMcWpGvOgXgm1p4mKSmWPzAwkRENn+un4L8DBhl3j1toeJy1A==", "requires": { "@babel/parser": "^7.18.8", "@babel/traverse": "^7.18.8", - "@docusaurus/logger": "2.2.0", - "@docusaurus/utils": "2.2.0", + "@docusaurus/logger": "2.3.0", + "@docusaurus/utils": "2.3.0", "@mdx-js/mdx": "^1.6.22", "escape-html": "^1.0.3", "file-loader": "^6.2.0", @@ -15317,12 +15845,13 @@ } }, "@docusaurus/utils": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/@docusaurus/utils/-/utils-2.2.0.tgz", - "integrity": "sha512-oNk3cjvx7Tt1Lgh/aeZAmFpGV2pDr5nHKrBVx6hTkzGhrnMuQqLt6UPlQjdYQ3QHXwyF/ZtZMO1D5Pfi0lu7SA==", + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@docusaurus/utils/-/utils-2.3.0.tgz", + "integrity": "sha512-6+GCurDsePHHbLM3ktcjv8N4zrjgrl1O7gOQNG4UMktcwHssFFVm+geVcB4M8siOmwUjV2VaNrp0hpGy8DOQHw==", "requires": { - "@docusaurus/logger": "2.2.0", + "@docusaurus/logger": "2.3.0", "@svgr/webpack": "^6.2.1", + "escape-string-regexp": "^4.0.0", "file-loader": "^6.2.0", "fs-extra": "^10.1.0", "github-slugger": "^1.4.0", @@ -15339,20 +15868,20 @@ } }, "@docusaurus/utils-common": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/@docusaurus/utils-common/-/utils-common-2.2.0.tgz", - "integrity": "sha512-qebnerHp+cyovdUseDQyYFvMW1n1nv61zGe5JJfoNQUnjKuApch3IVsz+/lZ9a38pId8kqehC1Ao2bW/s0ntDA==", + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@docusaurus/utils-common/-/utils-common-2.3.0.tgz", + "integrity": "sha512-nu5An+26FS7SQTwvyFR4g9lw3NU1u2RLcxJPZF+NCOG8Ne96ciuQosa7+N1kllm/heEJqfTaAUD0sFxpTZrDtw==", "requires": { "tslib": "^2.4.0" } }, "@docusaurus/utils-validation": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/@docusaurus/utils-validation/-/utils-validation-2.2.0.tgz", - "integrity": "sha512-I1hcsG3yoCkasOL5qQAYAfnmVoLei7apugT6m4crQjmDGxq+UkiRrq55UqmDDyZlac/6ax/JC0p+usZ6W4nVyg==", + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@docusaurus/utils-validation/-/utils-validation-2.3.0.tgz", + "integrity": "sha512-TBJCLqwAoiQQJ6dbgBpuLvzsn/XiTgbZkd6eJFUIQYLb1d473Zv58QrHXVmVQDLWiCgmJpHW2LpMfumTpCDgJw==", "requires": { - "@docusaurus/logger": "2.2.0", - "@docusaurus/utils": "2.2.0", + "@docusaurus/logger": "2.3.0", + "@docusaurus/utils": "2.3.0", "joi": "^17.6.0", "js-yaml": "^4.1.0", "tslib": "^2.4.0" @@ -15361,9 +15890,9 @@ } }, "@docusaurus/cssnano-preset": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/@docusaurus/cssnano-preset/-/cssnano-preset-2.2.0.tgz", - "integrity": "sha512-mAAwCo4n66TMWBH1kXnHVZsakW9VAXJzTO4yZukuL3ro4F+JtkMwKfh42EG75K/J/YIFQG5I/Bzy0UH/hFxaTg==", + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@docusaurus/cssnano-preset/-/cssnano-preset-2.3.0.tgz", + "integrity": "sha512-igmsXc1Q95lMeq07A1xua0/5wOPygDQ/ENSV7VVbiGhnvMv4gzkba8ZvbAtc7PmqK+kpYRfPzNCOk0GnQCvibg==", "requires": { "cssnano-preset-advanced": "^5.3.8", "postcss": "^8.4.14", @@ -15452,6 +15981,95 @@ "tslib": "^2.4.0" }, "dependencies": { + "@docusaurus/core": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/core/-/core-2.2.0.tgz", + "integrity": "sha512-Vd6XOluKQqzG12fEs9prJgDtyn6DPok9vmUWDR2E6/nV5Fl9SVkhEQOBxwObjk3kQh7OY7vguFaLh0jqdApWsA==", + "requires": { + "@babel/core": "^7.18.6", + "@babel/generator": "^7.18.7", + "@babel/plugin-syntax-dynamic-import": "^7.8.3", + "@babel/plugin-transform-runtime": "^7.18.6", + "@babel/preset-env": "^7.18.6", + "@babel/preset-react": "^7.18.6", + "@babel/preset-typescript": "^7.18.6", + "@babel/runtime": "^7.18.6", + "@babel/runtime-corejs3": "^7.18.6", + "@babel/traverse": "^7.18.8", + "@docusaurus/cssnano-preset": "2.2.0", + "@docusaurus/logger": "2.2.0", + "@docusaurus/mdx-loader": "2.2.0", + "@docusaurus/react-loadable": "5.5.2", + "@docusaurus/utils": "2.2.0", + "@docusaurus/utils-common": "2.2.0", + "@docusaurus/utils-validation": "2.2.0", + "@slorber/static-site-generator-webpack-plugin": "^4.0.7", + "@svgr/webpack": "^6.2.1", + "autoprefixer": "^10.4.7", + "babel-loader": "^8.2.5", + "babel-plugin-dynamic-import-node": "^2.3.3", + "boxen": "^6.2.1", + "chalk": "^4.1.2", + "chokidar": "^3.5.3", + "clean-css": "^5.3.0", + "cli-table3": "^0.6.2", + "combine-promises": "^1.1.0", + "commander": "^5.1.0", + "copy-webpack-plugin": "^11.0.0", + "core-js": "^3.23.3", + "css-loader": "^6.7.1", + "css-minimizer-webpack-plugin": "^4.0.0", + "cssnano": "^5.1.12", + "del": "^6.1.1", + "detect-port": "^1.3.0", + "escape-html": "^1.0.3", + "eta": "^1.12.3", + "file-loader": "^6.2.0", + "fs-extra": "^10.1.0", + "html-minifier-terser": "^6.1.0", + "html-tags": "^3.2.0", + "html-webpack-plugin": "^5.5.0", + "import-fresh": "^3.3.0", + "leven": "^3.1.0", + "lodash": "^4.17.21", + "mini-css-extract-plugin": "^2.6.1", + "postcss": "^8.4.14", + "postcss-loader": "^7.0.0", + "prompts": "^2.4.2", + "react-dev-utils": "^12.0.1", + "react-helmet-async": "^1.3.0", + "react-loadable": "npm:@docusaurus/react-loadable@5.5.2", + "react-loadable-ssr-addon-v5-slorber": "^1.0.1", + "react-router": "^5.3.3", + "react-router-config": "^5.1.1", + "react-router-dom": "^5.3.3", + "rtl-detect": "^1.0.4", + "semver": "^7.3.7", + "serve-handler": "^6.1.3", + "shelljs": "^0.8.5", + "terser-webpack-plugin": "^5.3.3", + "tslib": "^2.4.0", + "update-notifier": "^5.1.0", + "url-loader": "^4.1.1", + "wait-on": "^6.0.1", + "webpack": "^5.73.0", + "webpack-bundle-analyzer": "^4.5.0", + "webpack-dev-server": "^4.9.3", + "webpack-merge": "^5.8.0", + "webpackbar": "^5.0.2" + } + }, + "@docusaurus/cssnano-preset": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/cssnano-preset/-/cssnano-preset-2.2.0.tgz", + "integrity": "sha512-mAAwCo4n66TMWBH1kXnHVZsakW9VAXJzTO4yZukuL3ro4F+JtkMwKfh42EG75K/J/YIFQG5I/Bzy0UH/hFxaTg==", + "requires": { + "cssnano-preset-advanced": "^5.3.8", + "postcss": "^8.4.14", + "postcss-sort-media-queries": "^4.2.1", + "tslib": "^2.4.0" + } + }, "@docusaurus/logger": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/@docusaurus/logger/-/logger-2.2.0.tgz", @@ -15461,6 +16079,30 @@ "tslib": "^2.4.0" } }, + "@docusaurus/mdx-loader": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/mdx-loader/-/mdx-loader-2.2.0.tgz", + "integrity": "sha512-X2bzo3T0jW0VhUU+XdQofcEeozXOTmKQMvc8tUnWRdTnCvj4XEcBVdC3g+/jftceluiwSTNRAX4VBOJdNt18jA==", + "requires": { + "@babel/parser": "^7.18.8", + "@babel/traverse": "^7.18.8", + "@docusaurus/logger": "2.2.0", + "@docusaurus/utils": "2.2.0", + "@mdx-js/mdx": "^1.6.22", + "escape-html": "^1.0.3", + "file-loader": "^6.2.0", + "fs-extra": "^10.1.0", + "image-size": "^1.0.1", + "mdast-util-to-string": "^2.0.0", + "remark-emoji": "^2.2.0", + "stringify-object": "^3.3.0", + "tslib": "^2.4.0", + "unified": "^9.2.2", + "unist-util-visit": "^2.0.3", + "url-loader": "^4.1.1", + "webpack": "^5.73.0" + } + }, "@docusaurus/utils": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/@docusaurus/utils/-/utils-2.2.0.tgz", @@ -15521,17 +16163,131 @@ "feed": "^4.2.2", "fs-extra": "^10.1.0", "lodash": "^4.17.21", - "reading-time": "^1.5.0", + "reading-time": "^1.5.0", + "tslib": "^2.4.0", + "unist-util-visit": "^2.0.3", + "utility-types": "^3.10.0", + "webpack": "^5.73.0" + }, + "dependencies": { + "@docusaurus/core": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@docusaurus/core/-/core-2.1.0.tgz", + "integrity": "sha512-/ZJ6xmm+VB9Izbn0/s6h6289cbPy2k4iYFwWDhjiLsVqwa/Y0YBBcXvStfaHccudUC3OfP+26hMk7UCjc50J6Q==", + "requires": { + "@babel/core": "^7.18.6", + "@babel/generator": "^7.18.7", + "@babel/plugin-syntax-dynamic-import": "^7.8.3", + "@babel/plugin-transform-runtime": "^7.18.6", + "@babel/preset-env": "^7.18.6", + "@babel/preset-react": "^7.18.6", + "@babel/preset-typescript": "^7.18.6", + "@babel/runtime": "^7.18.6", + "@babel/runtime-corejs3": "^7.18.6", + "@babel/traverse": "^7.18.8", + "@docusaurus/cssnano-preset": "2.1.0", + "@docusaurus/logger": "2.1.0", + "@docusaurus/mdx-loader": "2.1.0", + "@docusaurus/react-loadable": "5.5.2", + "@docusaurus/utils": "2.1.0", + "@docusaurus/utils-common": "2.1.0", + "@docusaurus/utils-validation": "2.1.0", + "@slorber/static-site-generator-webpack-plugin": "^4.0.7", + "@svgr/webpack": "^6.2.1", + "autoprefixer": "^10.4.7", + "babel-loader": "^8.2.5", + "babel-plugin-dynamic-import-node": "^2.3.3", + "boxen": "^6.2.1", + "chalk": "^4.1.2", + "chokidar": "^3.5.3", + "clean-css": "^5.3.0", + "cli-table3": "^0.6.2", + "combine-promises": "^1.1.0", + "commander": "^5.1.0", + "copy-webpack-plugin": "^11.0.0", + "core-js": "^3.23.3", + "css-loader": "^6.7.1", + "css-minimizer-webpack-plugin": "^4.0.0", + "cssnano": "^5.1.12", + "del": "^6.1.1", + "detect-port": "^1.3.0", + "escape-html": "^1.0.3", + "eta": "^1.12.3", + "file-loader": "^6.2.0", + "fs-extra": "^10.1.0", + "html-minifier-terser": "^6.1.0", + "html-tags": "^3.2.0", + "html-webpack-plugin": "^5.5.0", + "import-fresh": "^3.3.0", + "leven": "^3.1.0", + "lodash": "^4.17.21", + "mini-css-extract-plugin": "^2.6.1", + "postcss": "^8.4.14", + "postcss-loader": "^7.0.0", + "prompts": "^2.4.2", + "react-dev-utils": "^12.0.1", + "react-helmet-async": "^1.3.0", + "react-loadable": "npm:@docusaurus/react-loadable@5.5.2", + "react-loadable-ssr-addon-v5-slorber": "^1.0.1", + "react-router": "^5.3.3", + "react-router-config": "^5.1.1", + "react-router-dom": "^5.3.3", + "rtl-detect": "^1.0.4", + "semver": "^7.3.7", + "serve-handler": "^6.1.3", + "shelljs": "^0.8.5", + "terser-webpack-plugin": "^5.3.3", + "tslib": "^2.4.0", + "update-notifier": "^5.1.0", + "url-loader": "^4.1.1", + "wait-on": "^6.0.1", + "webpack": "^5.73.0", + "webpack-bundle-analyzer": "^4.5.0", + "webpack-dev-server": "^4.9.3", + "webpack-merge": "^5.8.0", + "webpackbar": "^5.0.2" + } + }, + "@docusaurus/cssnano-preset": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@docusaurus/cssnano-preset/-/cssnano-preset-2.1.0.tgz", + "integrity": "sha512-pRLewcgGhOies6pzsUROfmPStDRdFw+FgV5sMtLr5+4Luv2rty5+b/eSIMMetqUsmg3A9r9bcxHk9bKAKvx3zQ==", + "requires": { + "cssnano-preset-advanced": "^5.3.8", + "postcss": "^8.4.14", + "postcss-sort-media-queries": "^4.2.1", + "tslib": "^2.4.0" + } + } + } + }, + "@docusaurus/plugin-content-docs": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/plugin-content-docs/-/plugin-content-docs-2.2.0.tgz", + "integrity": "sha512-BOazBR0XjzsHE+2K1wpNxz5QZmrJgmm3+0Re0EVPYFGW8qndCWGNtXW/0lGKhecVPML8yyFeAmnUCIs7xM2wPw==", + "requires": { + "@docusaurus/core": "2.2.0", + "@docusaurus/logger": "2.2.0", + "@docusaurus/mdx-loader": "2.2.0", + "@docusaurus/module-type-aliases": "2.2.0", + "@docusaurus/types": "2.2.0", + "@docusaurus/utils": "2.2.0", + "@docusaurus/utils-validation": "2.2.0", + "@types/react-router-config": "^5.0.6", + "combine-promises": "^1.1.0", + "fs-extra": "^10.1.0", + "import-fresh": "^3.3.0", + "js-yaml": "^4.1.0", + "lodash": "^4.17.21", "tslib": "^2.4.0", - "unist-util-visit": "^2.0.3", "utility-types": "^3.10.0", "webpack": "^5.73.0" }, "dependencies": { "@docusaurus/core": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/@docusaurus/core/-/core-2.1.0.tgz", - "integrity": "sha512-/ZJ6xmm+VB9Izbn0/s6h6289cbPy2k4iYFwWDhjiLsVqwa/Y0YBBcXvStfaHccudUC3OfP+26hMk7UCjc50J6Q==", + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/core/-/core-2.2.0.tgz", + "integrity": "sha512-Vd6XOluKQqzG12fEs9prJgDtyn6DPok9vmUWDR2E6/nV5Fl9SVkhEQOBxwObjk3kQh7OY7vguFaLh0jqdApWsA==", "requires": { "@babel/core": "^7.18.6", "@babel/generator": "^7.18.7", @@ -15543,13 +16299,13 @@ "@babel/runtime": "^7.18.6", "@babel/runtime-corejs3": "^7.18.6", "@babel/traverse": "^7.18.8", - "@docusaurus/cssnano-preset": "2.1.0", - "@docusaurus/logger": "2.1.0", - "@docusaurus/mdx-loader": "2.1.0", + "@docusaurus/cssnano-preset": "2.2.0", + "@docusaurus/logger": "2.2.0", + "@docusaurus/mdx-loader": "2.2.0", "@docusaurus/react-loadable": "5.5.2", - "@docusaurus/utils": "2.1.0", - "@docusaurus/utils-common": "2.1.0", - "@docusaurus/utils-validation": "2.1.0", + "@docusaurus/utils": "2.2.0", + "@docusaurus/utils-common": "2.2.0", + "@docusaurus/utils-validation": "2.2.0", "@slorber/static-site-generator-webpack-plugin": "^4.0.7", "@svgr/webpack": "^6.2.1", "autoprefixer": "^10.4.7", @@ -15607,41 +16363,16 @@ } }, "@docusaurus/cssnano-preset": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/@docusaurus/cssnano-preset/-/cssnano-preset-2.1.0.tgz", - "integrity": "sha512-pRLewcgGhOies6pzsUROfmPStDRdFw+FgV5sMtLr5+4Luv2rty5+b/eSIMMetqUsmg3A9r9bcxHk9bKAKvx3zQ==", + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/cssnano-preset/-/cssnano-preset-2.2.0.tgz", + "integrity": "sha512-mAAwCo4n66TMWBH1kXnHVZsakW9VAXJzTO4yZukuL3ro4F+JtkMwKfh42EG75K/J/YIFQG5I/Bzy0UH/hFxaTg==", "requires": { "cssnano-preset-advanced": "^5.3.8", "postcss": "^8.4.14", "postcss-sort-media-queries": "^4.2.1", "tslib": "^2.4.0" } - } - } - }, - "@docusaurus/plugin-content-docs": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/@docusaurus/plugin-content-docs/-/plugin-content-docs-2.2.0.tgz", - "integrity": "sha512-BOazBR0XjzsHE+2K1wpNxz5QZmrJgmm3+0Re0EVPYFGW8qndCWGNtXW/0lGKhecVPML8yyFeAmnUCIs7xM2wPw==", - "requires": { - "@docusaurus/core": "2.2.0", - "@docusaurus/logger": "2.2.0", - "@docusaurus/mdx-loader": "2.2.0", - "@docusaurus/module-type-aliases": "2.2.0", - "@docusaurus/types": "2.2.0", - "@docusaurus/utils": "2.2.0", - "@docusaurus/utils-validation": "2.2.0", - "@types/react-router-config": "^5.0.6", - "combine-promises": "^1.1.0", - "fs-extra": "^10.1.0", - "import-fresh": "^3.3.0", - "js-yaml": "^4.1.0", - "lodash": "^4.17.21", - "tslib": "^2.4.0", - "utility-types": "^3.10.0", - "webpack": "^5.73.0" - }, - "dependencies": { + }, "@docusaurus/logger": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/@docusaurus/logger/-/logger-2.2.0.tgz", @@ -15712,6 +16443,14 @@ "webpack": "^5.73.0" } }, + "@docusaurus/utils-common": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/utils-common/-/utils-common-2.2.0.tgz", + "integrity": "sha512-qebnerHp+cyovdUseDQyYFvMW1n1nv61zGe5JJfoNQUnjKuApch3IVsz+/lZ9a38pId8kqehC1Ao2bW/s0ntDA==", + "requires": { + "tslib": "^2.4.0" + } + }, "@docusaurus/utils-validation": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/@docusaurus/utils-validation/-/utils-validation-2.2.0.tgz", @@ -15741,6 +16480,95 @@ "webpack": "^5.73.0" }, "dependencies": { + "@docusaurus/core": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/core/-/core-2.2.0.tgz", + "integrity": "sha512-Vd6XOluKQqzG12fEs9prJgDtyn6DPok9vmUWDR2E6/nV5Fl9SVkhEQOBxwObjk3kQh7OY7vguFaLh0jqdApWsA==", + "requires": { + "@babel/core": "^7.18.6", + "@babel/generator": "^7.18.7", + "@babel/plugin-syntax-dynamic-import": "^7.8.3", + "@babel/plugin-transform-runtime": "^7.18.6", + "@babel/preset-env": "^7.18.6", + "@babel/preset-react": "^7.18.6", + "@babel/preset-typescript": "^7.18.6", + "@babel/runtime": "^7.18.6", + "@babel/runtime-corejs3": "^7.18.6", + "@babel/traverse": "^7.18.8", + "@docusaurus/cssnano-preset": "2.2.0", + "@docusaurus/logger": "2.2.0", + "@docusaurus/mdx-loader": "2.2.0", + "@docusaurus/react-loadable": "5.5.2", + "@docusaurus/utils": "2.2.0", + "@docusaurus/utils-common": "2.2.0", + "@docusaurus/utils-validation": "2.2.0", + "@slorber/static-site-generator-webpack-plugin": "^4.0.7", + "@svgr/webpack": "^6.2.1", + "autoprefixer": "^10.4.7", + "babel-loader": "^8.2.5", + "babel-plugin-dynamic-import-node": "^2.3.3", + "boxen": "^6.2.1", + "chalk": "^4.1.2", + "chokidar": "^3.5.3", + "clean-css": "^5.3.0", + "cli-table3": "^0.6.2", + "combine-promises": "^1.1.0", + "commander": "^5.1.0", + "copy-webpack-plugin": "^11.0.0", + "core-js": "^3.23.3", + "css-loader": "^6.7.1", + "css-minimizer-webpack-plugin": "^4.0.0", + "cssnano": "^5.1.12", + "del": "^6.1.1", + "detect-port": "^1.3.0", + "escape-html": "^1.0.3", + "eta": "^1.12.3", + "file-loader": "^6.2.0", + "fs-extra": "^10.1.0", + "html-minifier-terser": "^6.1.0", + "html-tags": "^3.2.0", + "html-webpack-plugin": "^5.5.0", + "import-fresh": "^3.3.0", + "leven": "^3.1.0", + "lodash": "^4.17.21", + "mini-css-extract-plugin": "^2.6.1", + "postcss": "^8.4.14", + "postcss-loader": "^7.0.0", + "prompts": "^2.4.2", + "react-dev-utils": "^12.0.1", + "react-helmet-async": "^1.3.0", + "react-loadable": "npm:@docusaurus/react-loadable@5.5.2", + "react-loadable-ssr-addon-v5-slorber": "^1.0.1", + "react-router": "^5.3.3", + "react-router-config": "^5.1.1", + "react-router-dom": "^5.3.3", + "rtl-detect": "^1.0.4", + "semver": "^7.3.7", + "serve-handler": "^6.1.3", + "shelljs": "^0.8.5", + "terser-webpack-plugin": "^5.3.3", + "tslib": "^2.4.0", + "update-notifier": "^5.1.0", + "url-loader": "^4.1.1", + "wait-on": "^6.0.1", + "webpack": "^5.73.0", + "webpack-bundle-analyzer": "^4.5.0", + "webpack-dev-server": "^4.9.3", + "webpack-merge": "^5.8.0", + "webpackbar": "^5.0.2" + } + }, + "@docusaurus/cssnano-preset": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/cssnano-preset/-/cssnano-preset-2.2.0.tgz", + "integrity": "sha512-mAAwCo4n66TMWBH1kXnHVZsakW9VAXJzTO4yZukuL3ro4F+JtkMwKfh42EG75K/J/YIFQG5I/Bzy0UH/hFxaTg==", + "requires": { + "cssnano-preset-advanced": "^5.3.8", + "postcss": "^8.4.14", + "postcss-sort-media-queries": "^4.2.1", + "tslib": "^2.4.0" + } + }, "@docusaurus/logger": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/@docusaurus/logger/-/logger-2.2.0.tgz", @@ -15811,6 +16639,14 @@ "webpack": "^5.73.0" } }, + "@docusaurus/utils-common": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/utils-common/-/utils-common-2.2.0.tgz", + "integrity": "sha512-qebnerHp+cyovdUseDQyYFvMW1n1nv61zGe5JJfoNQUnjKuApch3IVsz+/lZ9a38pId8kqehC1Ao2bW/s0ntDA==", + "requires": { + "tslib": "^2.4.0" + } + }, "@docusaurus/utils-validation": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/@docusaurus/utils-validation/-/utils-validation-2.2.0.tgz", @@ -15836,6 +16672,95 @@ "tslib": "^2.4.0" }, "dependencies": { + "@docusaurus/core": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/core/-/core-2.2.0.tgz", + "integrity": "sha512-Vd6XOluKQqzG12fEs9prJgDtyn6DPok9vmUWDR2E6/nV5Fl9SVkhEQOBxwObjk3kQh7OY7vguFaLh0jqdApWsA==", + "requires": { + "@babel/core": "^7.18.6", + "@babel/generator": "^7.18.7", + "@babel/plugin-syntax-dynamic-import": "^7.8.3", + "@babel/plugin-transform-runtime": "^7.18.6", + "@babel/preset-env": "^7.18.6", + "@babel/preset-react": "^7.18.6", + "@babel/preset-typescript": "^7.18.6", + "@babel/runtime": "^7.18.6", + "@babel/runtime-corejs3": "^7.18.6", + "@babel/traverse": "^7.18.8", + "@docusaurus/cssnano-preset": "2.2.0", + "@docusaurus/logger": "2.2.0", + "@docusaurus/mdx-loader": "2.2.0", + "@docusaurus/react-loadable": "5.5.2", + "@docusaurus/utils": "2.2.0", + "@docusaurus/utils-common": "2.2.0", + "@docusaurus/utils-validation": "2.2.0", + "@slorber/static-site-generator-webpack-plugin": "^4.0.7", + "@svgr/webpack": "^6.2.1", + "autoprefixer": "^10.4.7", + "babel-loader": "^8.2.5", + "babel-plugin-dynamic-import-node": "^2.3.3", + "boxen": "^6.2.1", + "chalk": "^4.1.2", + "chokidar": "^3.5.3", + "clean-css": "^5.3.0", + "cli-table3": "^0.6.2", + "combine-promises": "^1.1.0", + "commander": "^5.1.0", + "copy-webpack-plugin": "^11.0.0", + "core-js": "^3.23.3", + "css-loader": "^6.7.1", + "css-minimizer-webpack-plugin": "^4.0.0", + "cssnano": "^5.1.12", + "del": "^6.1.1", + "detect-port": "^1.3.0", + "escape-html": "^1.0.3", + "eta": "^1.12.3", + "file-loader": "^6.2.0", + "fs-extra": "^10.1.0", + "html-minifier-terser": "^6.1.0", + "html-tags": "^3.2.0", + "html-webpack-plugin": "^5.5.0", + "import-fresh": "^3.3.0", + "leven": "^3.1.0", + "lodash": "^4.17.21", + "mini-css-extract-plugin": "^2.6.1", + "postcss": "^8.4.14", + "postcss-loader": "^7.0.0", + "prompts": "^2.4.2", + "react-dev-utils": "^12.0.1", + "react-helmet-async": "^1.3.0", + "react-loadable": "npm:@docusaurus/react-loadable@5.5.2", + "react-loadable-ssr-addon-v5-slorber": "^1.0.1", + "react-router": "^5.3.3", + "react-router-config": "^5.1.1", + "react-router-dom": "^5.3.3", + "rtl-detect": "^1.0.4", + "semver": "^7.3.7", + "serve-handler": "^6.1.3", + "shelljs": "^0.8.5", + "terser-webpack-plugin": "^5.3.3", + "tslib": "^2.4.0", + "update-notifier": "^5.1.0", + "url-loader": "^4.1.1", + "wait-on": "^6.0.1", + "webpack": "^5.73.0", + "webpack-bundle-analyzer": "^4.5.0", + "webpack-dev-server": "^4.9.3", + "webpack-merge": "^5.8.0", + "webpackbar": "^5.0.2" + } + }, + "@docusaurus/cssnano-preset": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/cssnano-preset/-/cssnano-preset-2.2.0.tgz", + "integrity": "sha512-mAAwCo4n66TMWBH1kXnHVZsakW9VAXJzTO4yZukuL3ro4F+JtkMwKfh42EG75K/J/YIFQG5I/Bzy0UH/hFxaTg==", + "requires": { + "cssnano-preset-advanced": "^5.3.8", + "postcss": "^8.4.14", + "postcss-sort-media-queries": "^4.2.1", + "tslib": "^2.4.0" + } + }, "@docusaurus/logger": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/@docusaurus/logger/-/logger-2.2.0.tgz", @@ -15845,6 +16770,30 @@ "tslib": "^2.4.0" } }, + "@docusaurus/mdx-loader": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/mdx-loader/-/mdx-loader-2.2.0.tgz", + "integrity": "sha512-X2bzo3T0jW0VhUU+XdQofcEeozXOTmKQMvc8tUnWRdTnCvj4XEcBVdC3g+/jftceluiwSTNRAX4VBOJdNt18jA==", + "requires": { + "@babel/parser": "^7.18.8", + "@babel/traverse": "^7.18.8", + "@docusaurus/logger": "2.2.0", + "@docusaurus/utils": "2.2.0", + "@mdx-js/mdx": "^1.6.22", + "escape-html": "^1.0.3", + "file-loader": "^6.2.0", + "fs-extra": "^10.1.0", + "image-size": "^1.0.1", + "mdast-util-to-string": "^2.0.0", + "remark-emoji": "^2.2.0", + "stringify-object": "^3.3.0", + "tslib": "^2.4.0", + "unified": "^9.2.2", + "unist-util-visit": "^2.0.3", + "url-loader": "^4.1.1", + "webpack": "^5.73.0" + } + }, "@docusaurus/types": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/@docusaurus/types/-/types-2.2.0.tgz", @@ -15882,6 +16831,14 @@ "webpack": "^5.73.0" } }, + "@docusaurus/utils-common": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@docusaurus/utils-common/-/utils-common-2.2.0.tgz", + "integrity": "sha512-qebnerHp+cyovdUseDQyYFvMW1n1nv61zGe5JJfoNQUnjKuApch3IVsz+/lZ9a38pId8kqehC1Ao2bW/s0ntDA==", + "requires": { + "tslib": "^2.4.0" + } + }, "@docusaurus/utils-validation": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/@docusaurus/utils-validation/-/utils-validation-2.2.0.tgz", diff --git a/website/package.json b/website/package.json index ed778d065a4..e67360df40c 100644 --- a/website/package.json +++ b/website/package.json @@ -17,7 +17,7 @@ "fmt:write": "prettier --write ." }, "dependencies": { - "@docusaurus/core": "~2.2.0", + "@docusaurus/core": "~2.3.0", "@docusaurus/plugin-client-redirects": "~2.2.0", "@docusaurus/plugin-content-docs": "~2.2.0", "@docusaurus/plugin-content-pages": "~2.2.0", From ce93fd31ebdfb7b9e10c24d21fe2dd57d56a95c2 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 1 Feb 2023 14:41:08 +0000 Subject: [PATCH 27/76] Bump prettier from 2.8.1 to 2.8.3 in /website (#3104) Bumps [prettier](https://github.com/prettier/prettier) from 2.8.1 to 2.8.3. - [Release notes](https://github.com/prettier/prettier/releases) - [Changelog](https://github.com/prettier/prettier/blob/main/CHANGELOG.md) - [Commits](https://github.com/prettier/prettier/compare/2.8.1...2.8.3) --- updated-dependencies: - dependency-name: prettier dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- website/package-lock.json | 14 +++++++------- website/package.json | 2 +- 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/website/package-lock.json b/website/package-lock.json index 86f99efa7e5..7b88dc9a0ec 100644 --- a/website/package-lock.json +++ b/website/package-lock.json @@ -34,7 +34,7 @@ "@typescript-eslint/eslint-plugin": "^5.47.1", "@typescript-eslint/parser": "^5.50.0", "dir-compare": "^4.0.0", - "prettier": "2.8.1", + "prettier": "2.8.3", "typescript": "^4.8.3" } }, @@ -11314,9 +11314,9 @@ } }, "node_modules/prettier": { - "version": "2.8.1", - "resolved": "https://registry.npmjs.org/prettier/-/prettier-2.8.1.tgz", - "integrity": "sha512-lqGoSJBQNJidqCHE80vqZJHWHRFoNYsSpP9AjFhlhi9ODCJA541svILes/+/1GM3VaL/abZi7cpFzOpdR9UPKg==", + "version": "2.8.3", + "resolved": "https://registry.npmjs.org/prettier/-/prettier-2.8.3.tgz", + "integrity": "sha512-tJ/oJ4amDihPoufT5sM0Z1SKEuKay8LfVAMlbbhnnkvt6BUserZylqo2PN+p9KeljLr0OHa2rXHU1T8reeoTrw==", "dev": true, "bin": { "prettier": "bin-prettier.js" @@ -22577,9 +22577,9 @@ "integrity": "sha512-ravE6m9Atw9Z/jjttRUZ+clIXogdghyZAuWJ3qEzjT+jI/dL1ifAqhZeC5VHzQp1MSt1+jxKkFNemj/iO7tVUA==" }, "prettier": { - "version": "2.8.1", - "resolved": "https://registry.npmjs.org/prettier/-/prettier-2.8.1.tgz", - "integrity": "sha512-lqGoSJBQNJidqCHE80vqZJHWHRFoNYsSpP9AjFhlhi9ODCJA541svILes/+/1GM3VaL/abZi7cpFzOpdR9UPKg==", + "version": "2.8.3", + "resolved": "https://registry.npmjs.org/prettier/-/prettier-2.8.3.tgz", + "integrity": "sha512-tJ/oJ4amDihPoufT5sM0Z1SKEuKay8LfVAMlbbhnnkvt6BUserZylqo2PN+p9KeljLr0OHa2rXHU1T8reeoTrw==", "dev": true }, "pretty-error": { diff --git a/website/package.json b/website/package.json index e67360df40c..fe5c271bb69 100644 --- a/website/package.json +++ b/website/package.json @@ -55,7 +55,7 @@ "@typescript-eslint/eslint-plugin": "^5.47.1", "@typescript-eslint/parser": "^5.50.0", "dir-compare": "^4.0.0", - "prettier": "2.8.1", + "prettier": "2.8.3", "typescript": "^4.8.3" } } From 006fbefddc010c71ce386ad4391012a3f2762b56 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 1 Feb 2023 23:41:18 +0900 Subject: [PATCH 28/76] Bump @typescript-eslint/eslint-plugin from 5.47.1 to 5.50.0 in /website (#3105) Bumps [@typescript-eslint/eslint-plugin](https://github.com/typescript-eslint/typescript-eslint/tree/HEAD/packages/eslint-plugin) from 5.47.1 to 5.50.0. - [Release notes](https://github.com/typescript-eslint/typescript-eslint/releases) - [Changelog](https://github.com/typescript-eslint/typescript-eslint/blob/main/packages/eslint-plugin/CHANGELOG.md) - [Commits](https://github.com/typescript-eslint/typescript-eslint/commits/v5.50.0/packages/eslint-plugin) --- updated-dependencies: - dependency-name: "@typescript-eslint/eslint-plugin" dependency-type: direct:development update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- website/package-lock.json | 360 +++++--------------------------------- website/package.json | 2 +- 2 files changed, 40 insertions(+), 322 deletions(-) diff --git a/website/package-lock.json b/website/package-lock.json index 7b88dc9a0ec..82554823f13 100644 --- a/website/package-lock.json +++ b/website/package-lock.json @@ -31,7 +31,7 @@ "@types/react": "^17.0.43", "@types/react-helmet": "^6.1.6", "@types/react-router-dom": "^5.3.3", - "@typescript-eslint/eslint-plugin": "^5.47.1", + "@typescript-eslint/eslint-plugin": "^5.50.0", "@typescript-eslint/parser": "^5.50.0", "dir-compare": "^4.0.0", "prettier": "2.8.3", @@ -4939,15 +4939,16 @@ } }, "node_modules/@typescript-eslint/eslint-plugin": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.47.1.tgz", - "integrity": "sha512-r4RZ2Jl9kcQN7K/dcOT+J7NAimbiis4sSM9spvWimsBvDegMhKLA5vri2jG19PmIPbDjPeWzfUPQ2hjEzA4Nmg==", + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.50.0.tgz", + "integrity": "sha512-vwksQWSFZiUhgq3Kv7o1Jcj0DUNylwnIlGvKvLLYsq8pAWha6/WCnXUeaSoNNha/K7QSf2+jvmkxggC1u3pIwQ==", "dev": true, "dependencies": { - "@typescript-eslint/scope-manager": "5.47.1", - "@typescript-eslint/type-utils": "5.47.1", - "@typescript-eslint/utils": "5.47.1", + "@typescript-eslint/scope-manager": "5.50.0", + "@typescript-eslint/type-utils": "5.50.0", + "@typescript-eslint/utils": "5.50.0", "debug": "^4.3.4", + "grapheme-splitter": "^1.0.4", "ignore": "^5.2.0", "natural-compare-lite": "^1.4.0", "regexpp": "^3.2.0", @@ -4971,53 +4972,6 @@ } } }, - "node_modules/@typescript-eslint/eslint-plugin/node_modules/@typescript-eslint/scope-manager": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.47.1.tgz", - "integrity": "sha512-9hsFDsgUwrdOoW1D97Ewog7DYSHaq4WKuNs0LHF9RiCmqB0Z+XRR4Pf7u7u9z/8CciHuJ6yxNws1XznI3ddjEw==", - "dev": true, - "dependencies": { - "@typescript-eslint/types": "5.47.1", - "@typescript-eslint/visitor-keys": "5.47.1" - }, - "engines": { - "node": "^12.22.0 || ^14.17.0 || >=16.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, - "node_modules/@typescript-eslint/eslint-plugin/node_modules/@typescript-eslint/types": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.47.1.tgz", - "integrity": "sha512-CmALY9YWXEpwuu6377ybJBZdtSAnzXLSQcxLSqSQSbC7VfpMu/HLVdrnVJj7ycI138EHqocW02LPJErE35cE9A==", - "dev": true, - "engines": { - "node": "^12.22.0 || ^14.17.0 || >=16.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, - "node_modules/@typescript-eslint/eslint-plugin/node_modules/@typescript-eslint/visitor-keys": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.47.1.tgz", - "integrity": "sha512-rF3pmut2JCCjh6BLRhNKdYjULMb1brvoaiWDlHfLNVgmnZ0sBVJrs3SyaKE1XoDDnJuAx/hDQryHYmPUuNq0ig==", - "dev": true, - "dependencies": { - "@typescript-eslint/types": "5.47.1", - "eslint-visitor-keys": "^3.3.0" - }, - "engines": { - "node": "^12.22.0 || ^14.17.0 || >=16.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, "node_modules/@typescript-eslint/parser": { "version": "5.50.0", "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-5.50.0.tgz", @@ -5063,13 +5017,13 @@ } }, "node_modules/@typescript-eslint/type-utils": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-5.47.1.tgz", - "integrity": "sha512-/UKOeo8ee80A7/GJA427oIrBi/Gd4osk/3auBUg4Rn9EahFpevVV1mUK8hjyQD5lHPqX397x6CwOk5WGh1E/1w==", + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-5.50.0.tgz", + "integrity": "sha512-dcnXfZ6OGrNCO7E5UY/i0ktHb7Yx1fV6fnQGGrlnfDhilcs6n19eIRcvLBqx6OQkrPaFlDPk3OJ0WlzQfrV0bQ==", "dev": true, "dependencies": { - "@typescript-eslint/typescript-estree": "5.47.1", - "@typescript-eslint/utils": "5.47.1", + "@typescript-eslint/typescript-estree": "5.50.0", + "@typescript-eslint/utils": "5.50.0", "debug": "^4.3.4", "tsutils": "^3.21.0" }, @@ -5089,63 +5043,6 @@ } } }, - "node_modules/@typescript-eslint/type-utils/node_modules/@typescript-eslint/types": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.47.1.tgz", - "integrity": "sha512-CmALY9YWXEpwuu6377ybJBZdtSAnzXLSQcxLSqSQSbC7VfpMu/HLVdrnVJj7ycI138EHqocW02LPJErE35cE9A==", - "dev": true, - "engines": { - "node": "^12.22.0 || ^14.17.0 || >=16.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, - "node_modules/@typescript-eslint/type-utils/node_modules/@typescript-eslint/typescript-estree": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.47.1.tgz", - "integrity": "sha512-4+ZhFSuISAvRi2xUszEj0xXbNTHceV9GbH9S8oAD2a/F9SW57aJNQVOCxG8GPfSWH/X4eOPdMEU2jYVuWKEpWA==", - "dev": true, - "dependencies": { - "@typescript-eslint/types": "5.47.1", - "@typescript-eslint/visitor-keys": "5.47.1", - "debug": "^4.3.4", - "globby": "^11.1.0", - "is-glob": "^4.0.3", - "semver": "^7.3.7", - "tsutils": "^3.21.0" - }, - "engines": { - "node": "^12.22.0 || ^14.17.0 || >=16.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependenciesMeta": { - "typescript": { - "optional": true - } - } - }, - "node_modules/@typescript-eslint/type-utils/node_modules/@typescript-eslint/visitor-keys": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.47.1.tgz", - "integrity": "sha512-rF3pmut2JCCjh6BLRhNKdYjULMb1brvoaiWDlHfLNVgmnZ0sBVJrs3SyaKE1XoDDnJuAx/hDQryHYmPUuNq0ig==", - "dev": true, - "dependencies": { - "@typescript-eslint/types": "5.47.1", - "eslint-visitor-keys": "^3.3.0" - }, - "engines": { - "node": "^12.22.0 || ^14.17.0 || >=16.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, "node_modules/@typescript-eslint/types": { "version": "5.50.0", "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.50.0.tgz", @@ -5187,16 +5084,16 @@ } }, "node_modules/@typescript-eslint/utils": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-5.47.1.tgz", - "integrity": "sha512-l90SdwqfmkuIVaREZ2ykEfCezepCLxzWMo5gVfcJsJCaT4jHT+QjgSkYhs5BMQmWqE9k3AtIfk4g211z/sTMVw==", + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-5.50.0.tgz", + "integrity": "sha512-v/AnUFImmh8G4PH0NDkf6wA8hujNNcrwtecqW4vtQ1UOSNBaZl49zP1SHoZ/06e+UiwzHpgb5zP5+hwlYYWYAw==", "dev": true, "dependencies": { "@types/json-schema": "^7.0.9", "@types/semver": "^7.3.12", - "@typescript-eslint/scope-manager": "5.47.1", - "@typescript-eslint/types": "5.47.1", - "@typescript-eslint/typescript-estree": "5.47.1", + "@typescript-eslint/scope-manager": "5.50.0", + "@typescript-eslint/types": "5.50.0", + "@typescript-eslint/typescript-estree": "5.50.0", "eslint-scope": "^5.1.1", "eslint-utils": "^3.0.0", "semver": "^7.3.7" @@ -5212,80 +5109,6 @@ "eslint": "^6.0.0 || ^7.0.0 || ^8.0.0" } }, - "node_modules/@typescript-eslint/utils/node_modules/@typescript-eslint/scope-manager": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.47.1.tgz", - "integrity": "sha512-9hsFDsgUwrdOoW1D97Ewog7DYSHaq4WKuNs0LHF9RiCmqB0Z+XRR4Pf7u7u9z/8CciHuJ6yxNws1XznI3ddjEw==", - "dev": true, - "dependencies": { - "@typescript-eslint/types": "5.47.1", - "@typescript-eslint/visitor-keys": "5.47.1" - }, - "engines": { - "node": "^12.22.0 || ^14.17.0 || >=16.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, - "node_modules/@typescript-eslint/utils/node_modules/@typescript-eslint/types": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.47.1.tgz", - "integrity": "sha512-CmALY9YWXEpwuu6377ybJBZdtSAnzXLSQcxLSqSQSbC7VfpMu/HLVdrnVJj7ycI138EHqocW02LPJErE35cE9A==", - "dev": true, - "engines": { - "node": "^12.22.0 || ^14.17.0 || >=16.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, - "node_modules/@typescript-eslint/utils/node_modules/@typescript-eslint/typescript-estree": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.47.1.tgz", - "integrity": "sha512-4+ZhFSuISAvRi2xUszEj0xXbNTHceV9GbH9S8oAD2a/F9SW57aJNQVOCxG8GPfSWH/X4eOPdMEU2jYVuWKEpWA==", - "dev": true, - "dependencies": { - "@typescript-eslint/types": "5.47.1", - "@typescript-eslint/visitor-keys": "5.47.1", - "debug": "^4.3.4", - "globby": "^11.1.0", - "is-glob": "^4.0.3", - "semver": "^7.3.7", - "tsutils": "^3.21.0" - }, - "engines": { - "node": "^12.22.0 || ^14.17.0 || >=16.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependenciesMeta": { - "typescript": { - "optional": true - } - } - }, - "node_modules/@typescript-eslint/utils/node_modules/@typescript-eslint/visitor-keys": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.47.1.tgz", - "integrity": "sha512-rF3pmut2JCCjh6BLRhNKdYjULMb1brvoaiWDlHfLNVgmnZ0sBVJrs3SyaKE1XoDDnJuAx/hDQryHYmPUuNq0ig==", - "dev": true, - "dependencies": { - "@typescript-eslint/types": "5.47.1", - "eslint-visitor-keys": "^3.3.0" - }, - "engines": { - "node": "^12.22.0 || ^14.17.0 || >=16.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, "node_modules/@typescript-eslint/visitor-keys": { "version": "5.50.0", "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.50.0.tgz", @@ -8547,8 +8370,7 @@ "version": "1.0.4", "resolved": "https://registry.npmjs.org/grapheme-splitter/-/grapheme-splitter-1.0.4.tgz", "integrity": "sha512-bzh50DW9kTPM00T8y4o8vQg89Di9oLJVLW/KaOGIXJWP/iqCN6WKYkbNOF04vFLJhwcpYUh9ydh/+5vpOqV4YQ==", - "devOptional": true, - "peer": true + "devOptional": true }, "node_modules/gray-matter": { "version": "4.0.3", @@ -18082,48 +17904,21 @@ } }, "@typescript-eslint/eslint-plugin": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.47.1.tgz", - "integrity": "sha512-r4RZ2Jl9kcQN7K/dcOT+J7NAimbiis4sSM9spvWimsBvDegMhKLA5vri2jG19PmIPbDjPeWzfUPQ2hjEzA4Nmg==", + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.50.0.tgz", + "integrity": "sha512-vwksQWSFZiUhgq3Kv7o1Jcj0DUNylwnIlGvKvLLYsq8pAWha6/WCnXUeaSoNNha/K7QSf2+jvmkxggC1u3pIwQ==", "dev": true, "requires": { - "@typescript-eslint/scope-manager": "5.47.1", - "@typescript-eslint/type-utils": "5.47.1", - "@typescript-eslint/utils": "5.47.1", + "@typescript-eslint/scope-manager": "5.50.0", + "@typescript-eslint/type-utils": "5.50.0", + "@typescript-eslint/utils": "5.50.0", "debug": "^4.3.4", + "grapheme-splitter": "^1.0.4", "ignore": "^5.2.0", "natural-compare-lite": "^1.4.0", "regexpp": "^3.2.0", "semver": "^7.3.7", "tsutils": "^3.21.0" - }, - "dependencies": { - "@typescript-eslint/scope-manager": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.47.1.tgz", - "integrity": "sha512-9hsFDsgUwrdOoW1D97Ewog7DYSHaq4WKuNs0LHF9RiCmqB0Z+XRR4Pf7u7u9z/8CciHuJ6yxNws1XznI3ddjEw==", - "dev": true, - "requires": { - "@typescript-eslint/types": "5.47.1", - "@typescript-eslint/visitor-keys": "5.47.1" - } - }, - "@typescript-eslint/types": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.47.1.tgz", - "integrity": "sha512-CmALY9YWXEpwuu6377ybJBZdtSAnzXLSQcxLSqSQSbC7VfpMu/HLVdrnVJj7ycI138EHqocW02LPJErE35cE9A==", - "dev": true - }, - "@typescript-eslint/visitor-keys": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.47.1.tgz", - "integrity": "sha512-rF3pmut2JCCjh6BLRhNKdYjULMb1brvoaiWDlHfLNVgmnZ0sBVJrs3SyaKE1XoDDnJuAx/hDQryHYmPUuNq0ig==", - "dev": true, - "requires": { - "@typescript-eslint/types": "5.47.1", - "eslint-visitor-keys": "^3.3.0" - } - } } }, "@typescript-eslint/parser": { @@ -18149,48 +17944,15 @@ } }, "@typescript-eslint/type-utils": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-5.47.1.tgz", - "integrity": "sha512-/UKOeo8ee80A7/GJA427oIrBi/Gd4osk/3auBUg4Rn9EahFpevVV1mUK8hjyQD5lHPqX397x6CwOk5WGh1E/1w==", + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-5.50.0.tgz", + "integrity": "sha512-dcnXfZ6OGrNCO7E5UY/i0ktHb7Yx1fV6fnQGGrlnfDhilcs6n19eIRcvLBqx6OQkrPaFlDPk3OJ0WlzQfrV0bQ==", "dev": true, "requires": { - "@typescript-eslint/typescript-estree": "5.47.1", - "@typescript-eslint/utils": "5.47.1", + "@typescript-eslint/typescript-estree": "5.50.0", + "@typescript-eslint/utils": "5.50.0", "debug": "^4.3.4", "tsutils": "^3.21.0" - }, - "dependencies": { - "@typescript-eslint/types": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.47.1.tgz", - "integrity": "sha512-CmALY9YWXEpwuu6377ybJBZdtSAnzXLSQcxLSqSQSbC7VfpMu/HLVdrnVJj7ycI138EHqocW02LPJErE35cE9A==", - "dev": true - }, - "@typescript-eslint/typescript-estree": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.47.1.tgz", - "integrity": "sha512-4+ZhFSuISAvRi2xUszEj0xXbNTHceV9GbH9S8oAD2a/F9SW57aJNQVOCxG8GPfSWH/X4eOPdMEU2jYVuWKEpWA==", - "dev": true, - "requires": { - "@typescript-eslint/types": "5.47.1", - "@typescript-eslint/visitor-keys": "5.47.1", - "debug": "^4.3.4", - "globby": "^11.1.0", - "is-glob": "^4.0.3", - "semver": "^7.3.7", - "tsutils": "^3.21.0" - } - }, - "@typescript-eslint/visitor-keys": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.47.1.tgz", - "integrity": "sha512-rF3pmut2JCCjh6BLRhNKdYjULMb1brvoaiWDlHfLNVgmnZ0sBVJrs3SyaKE1XoDDnJuAx/hDQryHYmPUuNq0ig==", - "dev": true, - "requires": { - "@typescript-eslint/types": "5.47.1", - "eslint-visitor-keys": "^3.3.0" - } - } } }, "@typescript-eslint/types": { @@ -18215,62 +17977,19 @@ } }, "@typescript-eslint/utils": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-5.47.1.tgz", - "integrity": "sha512-l90SdwqfmkuIVaREZ2ykEfCezepCLxzWMo5gVfcJsJCaT4jHT+QjgSkYhs5BMQmWqE9k3AtIfk4g211z/sTMVw==", + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-5.50.0.tgz", + "integrity": "sha512-v/AnUFImmh8G4PH0NDkf6wA8hujNNcrwtecqW4vtQ1UOSNBaZl49zP1SHoZ/06e+UiwzHpgb5zP5+hwlYYWYAw==", "dev": true, "requires": { "@types/json-schema": "^7.0.9", "@types/semver": "^7.3.12", - "@typescript-eslint/scope-manager": "5.47.1", - "@typescript-eslint/types": "5.47.1", - "@typescript-eslint/typescript-estree": "5.47.1", + "@typescript-eslint/scope-manager": "5.50.0", + "@typescript-eslint/types": "5.50.0", + "@typescript-eslint/typescript-estree": "5.50.0", "eslint-scope": "^5.1.1", "eslint-utils": "^3.0.0", "semver": "^7.3.7" - }, - "dependencies": { - "@typescript-eslint/scope-manager": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.47.1.tgz", - "integrity": "sha512-9hsFDsgUwrdOoW1D97Ewog7DYSHaq4WKuNs0LHF9RiCmqB0Z+XRR4Pf7u7u9z/8CciHuJ6yxNws1XznI3ddjEw==", - "dev": true, - "requires": { - "@typescript-eslint/types": "5.47.1", - "@typescript-eslint/visitor-keys": "5.47.1" - } - }, - "@typescript-eslint/types": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.47.1.tgz", - "integrity": "sha512-CmALY9YWXEpwuu6377ybJBZdtSAnzXLSQcxLSqSQSbC7VfpMu/HLVdrnVJj7ycI138EHqocW02LPJErE35cE9A==", - "dev": true - }, - "@typescript-eslint/typescript-estree": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.47.1.tgz", - "integrity": "sha512-4+ZhFSuISAvRi2xUszEj0xXbNTHceV9GbH9S8oAD2a/F9SW57aJNQVOCxG8GPfSWH/X4eOPdMEU2jYVuWKEpWA==", - "dev": true, - "requires": { - "@typescript-eslint/types": "5.47.1", - "@typescript-eslint/visitor-keys": "5.47.1", - "debug": "^4.3.4", - "globby": "^11.1.0", - "is-glob": "^4.0.3", - "semver": "^7.3.7", - "tsutils": "^3.21.0" - } - }, - "@typescript-eslint/visitor-keys": { - "version": "5.47.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.47.1.tgz", - "integrity": "sha512-rF3pmut2JCCjh6BLRhNKdYjULMb1brvoaiWDlHfLNVgmnZ0sBVJrs3SyaKE1XoDDnJuAx/hDQryHYmPUuNq0ig==", - "dev": true, - "requires": { - "@typescript-eslint/types": "5.47.1", - "eslint-visitor-keys": "^3.3.0" - } - } } }, "@typescript-eslint/visitor-keys": { @@ -20658,8 +20377,7 @@ "version": "1.0.4", "resolved": "https://registry.npmjs.org/grapheme-splitter/-/grapheme-splitter-1.0.4.tgz", "integrity": "sha512-bzh50DW9kTPM00T8y4o8vQg89Di9oLJVLW/KaOGIXJWP/iqCN6WKYkbNOF04vFLJhwcpYUh9ydh/+5vpOqV4YQ==", - "devOptional": true, - "peer": true + "devOptional": true }, "gray-matter": { "version": "4.0.3", diff --git a/website/package.json b/website/package.json index fe5c271bb69..ca4d2683c05 100644 --- a/website/package.json +++ b/website/package.json @@ -52,7 +52,7 @@ "@types/react": "^17.0.43", "@types/react-helmet": "^6.1.6", "@types/react-router-dom": "^5.3.3", - "@typescript-eslint/eslint-plugin": "^5.47.1", + "@typescript-eslint/eslint-plugin": "^5.50.0", "@typescript-eslint/parser": "^5.50.0", "dir-compare": "^4.0.0", "prettier": "2.8.3", From 456a05ba404f2458b091989896d9980458df79ec Mon Sep 17 00:00:00 2001 From: Kaede Hoshikawa Date: Thu, 2 Feb 2023 01:57:05 +0900 Subject: [PATCH 29/76] Fix clippy for 1.67 (#3100) * Fix clippy for 1.67 * Fix trybuild. --- examples/async_clock/src/main.rs | 2 +- examples/boids/src/boid.rs | 2 +- examples/boids/src/slider.rs | 2 +- examples/communication_child_to_parent/src/main.rs | 2 +- .../src/main.rs | 4 ++-- examples/function_todomvc/src/main.rs | 2 +- examples/futures/src/markdown.rs | 2 +- examples/js_callback/src/main.rs | 2 +- examples/keyed_list/src/person.rs | 2 +- examples/password_strength/src/app.rs | 2 +- examples/ssr_router/src/bin/ssr_router_server.rs | 2 +- packages/yew-macro/src/classes/mod.rs | 5 ++--- packages/yew-macro/src/function_component.rs | 2 +- .../yew-macro/src/html_tree/html_dashed_name.rs | 2 +- packages/yew-macro/src/html_tree/html_element.rs | 11 ++++------- packages/yew-macro/src/html_tree/lint/mod.rs | 4 ++-- packages/yew-macro/src/html_tree/tag.rs | 2 +- packages/yew-macro/src/props/prop.rs | 10 ++++------ .../yew-macro/tests/html_macro/element-fail.stderr | 4 ++-- packages/yew-router-macro/src/routable_derive.rs | 13 +++++-------- packages/yew-router/src/navigator.rs | 4 ++-- packages/yew-router/src/utils.rs | 2 +- packages/yew-router/tests/utils.rs | 2 +- packages/yew/src/dom_bundle/btag/mod.rs | 2 +- packages/yew/src/dom_bundle/utils.rs | 2 +- .../hooks/use_prepared_state/feat_hydration.rs | 2 +- packages/yew/src/virtual_dom/mod.rs | 2 +- packages/yew/src/virtual_dom/vtag.rs | 2 +- tools/benchmark-ssr/src/main.rs | 3 +-- tools/changelog/src/cli.rs | 2 +- tools/changelog/src/create_log_line.rs | 6 +++--- tools/changelog/src/get_latest_version.rs | 4 ++-- tools/changelog/src/github_fetch.rs | 4 ++-- tools/changelog/src/github_issue_labels_fetcher.rs | 7 ++----- tools/changelog/src/github_user_fetcher.rs | 2 +- tools/changelog/src/write_changelog_file.rs | 11 +++++------ tools/changelog/src/write_log_lines.rs | 7 ++----- tools/website-test/build.rs | 10 +++++----- 38 files changed, 67 insertions(+), 84 deletions(-) diff --git a/examples/async_clock/src/main.rs b/examples/async_clock/src/main.rs index 712c37123ef..84ade6a82b0 100644 --- a/examples/async_clock/src/main.rs +++ b/examples/async_clock/src/main.rs @@ -99,7 +99,7 @@ impl Component for AsyncComponent { let joke = self.joke.as_deref().unwrap_or("Loading..."); let fun_score = self .fun_score - .map(|score| format!("Fun score: {}", score)) + .map(|score| format!("Fun score: {score}")) .unwrap_or_else(|| "Computing...".to_string()); html! { diff --git a/examples/boids/src/boid.rs b/examples/boids/src/boid.rs index fdc32a49eb9..88050bc7aba 100644 --- a/examples/boids/src/boid.rs +++ b/examples/boids/src/boid.rs @@ -132,7 +132,7 @@ impl Boid { let Vector2D { x, y } = self.position + offset; // Write to string will never fail. - let _ = write!(points, "{:.2},{:.2} ", x, y); + let _ = write!(points, "{x:.2},{y:.2} "); } html! { } diff --git a/examples/boids/src/slider.rs b/examples/boids/src/slider.rs index 4c0edfabb22..7e1e6ca72bc 100644 --- a/examples/boids/src/slider.rs +++ b/examples/boids/src/slider.rs @@ -61,7 +61,7 @@ impl Component for Slider { let display_value = if percentage { format!("{:.p$}%", 100.0 * value, p = precision) } else { - format!("{:.p$}", value, p = precision) + format!("{value:.precision$}") }; let id = format!("slider-{}", self.id); diff --git a/examples/communication_child_to_parent/src/main.rs b/examples/communication_child_to_parent/src/main.rs index 845ffb97a40..4559d95b9bd 100644 --- a/examples/communication_child_to_parent/src/main.rs +++ b/examples/communication_child_to_parent/src/main.rs @@ -40,7 +40,7 @@ impl Component for Parent { let msg = format!("My children have been clicked {} times", self.total_clicks); let last_updated_msg = if let Some(last_updated) = self.last_updated.as_ref() { - format!("The last child that was clicked was {}", last_updated) + format!("The last child that was clicked was {last_updated}") } else { "No child has been clicked yet".to_string() }; diff --git a/examples/communication_grandchild_with_grandparent/src/main.rs b/examples/communication_grandchild_with_grandparent/src/main.rs index 0773b9d87d6..61f5a7d2742 100644 --- a/examples/communication_grandchild_with_grandparent/src/main.rs +++ b/examples/communication_grandchild_with_grandparent/src/main.rs @@ -60,7 +60,7 @@ impl Component for GrandParent { ); let detail_msg = if let Some(last_clicked) = &self.state.last_clicked { - format!("{} was clicked last", last_clicked) + format!("{last_clicked} was clicked last") } else { "No one has been clicked yet".to_string() }; @@ -135,7 +135,7 @@ impl Component for Child { fn view(&self, ctx: &Context) -> Html { let my_name = ctx.props().name.clone(); - let name = format!("{}: ", my_name); + let name = format!("{my_name}: "); // Here we emit the callback to the grandparent component, whenever the button is clicked. let onclick = self.state.child_clicked.reform(move |_| (my_name.clone())); diff --git a/examples/function_todomvc/src/main.rs b/examples/function_todomvc/src/main.rs index a9eb5c6eb21..9deacca9d43 100644 --- a/examples/function_todomvc/src/main.rs +++ b/examples/function_todomvc/src/main.rs @@ -135,7 +135,7 @@ fn app() -> Html { }) } diff --git a/examples/futures/src/markdown.rs b/examples/futures/src/markdown.rs index 4bbbc0bedac..e51729308e5 100644 --- a/examples/futures/src/markdown.rs +++ b/examples/futures/src/markdown.rs @@ -92,7 +92,7 @@ pub fn render_markdown(src: &str) -> Html { Event::Rule => add_child!(VTag::new("hr").into()), Event::SoftBreak => add_child!(VText::new("\n").into()), Event::HardBreak => add_child!(VTag::new("br").into()), - _ => println!("Unknown event: {:#?}", ev), + _ => println!("Unknown event: {ev:#?}"), } } diff --git a/examples/js_callback/src/main.rs b/examples/js_callback/src/main.rs index 6ba10851ce5..4c999facb50 100644 --- a/examples/js_callback/src/main.rs +++ b/examples/js_callback/src/main.rs @@ -24,7 +24,7 @@ fn Important() -> Html { fn use_do_bye() -> SuspensionResult { let path = WASM_BINDGEN_SNIPPETS_PATH .get() - .map(|path| format!("{}/js/unimp.js", path)) + .map(|path| format!("{path}/js/unimp.js")) .unwrap(); let s = use_future(|| async move { let promise = bindings::import(&path); diff --git a/examples/keyed_list/src/person.rs b/examples/keyed_list/src/person.rs index c7eda7e0cbf..05e89e41399 100644 --- a/examples/keyed_list/src/person.rs +++ b/examples/keyed_list/src/person.rs @@ -23,7 +23,7 @@ impl PersonInfo { let city = CityName(EN).fake::(); let street = StreetName(EN).fake::(); - Rc::from(format!("{} {} St., {}, {}", no, street, city, state).as_str()) + Rc::from(format!("{no} {street} St., {city}, {state}").as_str()) }; Self { diff --git a/examples/password_strength/src/app.rs b/examples/password_strength/src/app.rs index b64f3e2829f..3ffbcfe58ae 100644 --- a/examples/password_strength/src/app.rs +++ b/examples/password_strength/src/app.rs @@ -34,7 +34,7 @@ impl App { 3 => "Good", _ => "Great!", }; - format!("Complexity = {}", estimate_text) + format!("Complexity = {estimate_text}") } } diff --git a/examples/ssr_router/src/bin/ssr_router_server.rs b/examples/ssr_router/src/bin/ssr_router_server.rs index d594b15efea..2ccae60f0a9 100644 --- a/examples/ssr_router/src/bin/ssr_router_server.rs +++ b/examples/ssr_router/src/bin/ssr_router_server.rs @@ -94,7 +94,7 @@ async fn main() { let handle_error = |e| async move { ( StatusCode::INTERNAL_SERVER_ERROR, - format!("error occurred: {}", e), + format!("error occurred: {e}"), ) }; diff --git a/packages/yew-macro/src/classes/mod.rs b/packages/yew-macro/src/classes/mod.rs index 76e7ee9b198..059b115a831 100644 --- a/packages/yew-macro/src/classes/mod.rs +++ b/packages/yew-macro/src/classes/mod.rs @@ -52,12 +52,11 @@ impl Parse for ClassExpr { if classes.len() > 1 { let fix = classes .into_iter() - .map(|class| format!("\"{}\"", class)) + .map(|class| format!("\"{class}\"")) .collect::>() .join(", "); let msg = format!( - "string literals must not contain more than one class (hint: use `{}`)", - fix + "string literals must not contain more than one class (hint: use `{fix}`)" ); Err(syn::Error::new(lit_str.span(), msg)) diff --git a/packages/yew-macro/src/function_component.rs b/packages/yew-macro/src/function_component.rs index 9e6a1df495f..852f82d9b29 100644 --- a/packages/yew-macro/src/function_component.rs +++ b/packages/yew-macro/src/function_component.rs @@ -332,7 +332,7 @@ impl FunctionComponent { let component_name = self.component_name(); let (impl_generics, ty_generics, where_clause) = self.generics.split_for_impl(); - let component_name_lit = LitStr::new(&format!("{}<_>", component_name), Span::mixed_site()); + let component_name_lit = LitStr::new(&format!("{component_name}<_>"), Span::mixed_site()); quote! { #[automatically_derived] diff --git a/packages/yew-macro/src/html_tree/html_dashed_name.rs b/packages/yew-macro/src/html_tree/html_dashed_name.rs index 5140f6daf4f..6699b779f5a 100644 --- a/packages/yew-macro/src/html_tree/html_dashed_name.rs +++ b/packages/yew-macro/src/html_tree/html_dashed_name.rs @@ -45,7 +45,7 @@ impl fmt::Display for HtmlDashedName { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { write!(f, "{}", self.name)?; for (_, ident) in &self.extended { - write!(f, "-{}", ident)?; + write!(f, "-{ident}")?; } Ok(()) } diff --git a/packages/yew-macro/src/html_tree/html_element.rs b/packages/yew-macro/src/html_tree/html_element.rs index 7991873b354..08f07ea5318 100644 --- a/packages/yew-macro/src/html_tree/html_element.rs +++ b/packages/yew-macro/src/html_tree/html_element.rs @@ -59,9 +59,8 @@ impl Parse for HtmlElement { return Err(syn::Error::new_spanned( open.to_spanned(), format!( - "the tag `<{}>` is a void element and cannot have children (hint: \ - rewrite this as `<{0}/>`)", - name + "the tag `<{name}>` is a void element and cannot have children (hint: \ + rewrite this as `<{name} />`)", ), )); } @@ -324,10 +323,8 @@ impl ToTokens for HtmlElement { emit_warning!( dashedname.span(), format!( - "The tag '{0}' is not matching its normalized form '{1}'. If you want \ - to keep this form, change this to a dynamic tag `@{{\"{0}\"}}`.", - dashedname, - name, + "The tag '{dashedname}' is not matching its normalized form '{name}'. If you want \ + to keep this form, change this to a dynamic tag `@{{\"{dashedname}\"}}`." ) ) } diff --git a/packages/yew-macro/src/html_tree/lint/mod.rs b/packages/yew-macro/src/html_tree/lint/mod.rs index f925f3a15ef..bbb34f24648 100644 --- a/packages/yew-macro/src/html_tree/lint/mod.rs +++ b/packages/yew-macro/src/html_tree/lint/mod.rs @@ -67,11 +67,11 @@ impl Lint for AHrefLint { match href_value.as_ref() { "#" | "javascript:void(0)" => emit_warning!( lit.span(), - format!("'{}' is not a suitable value for the `href` attribute. \ + format!("'{href_value}' is not a suitable value for the `href` attribute. \ Without a meaningful attribute assistive technologies \ will struggle to understand your webpage. \ https://developer.mozilla.org/en-US/docs/Learn/Accessibility/HTML#onclick_events" - ,href_value)), + )), _ => {} } diff --git a/packages/yew-macro/src/html_tree/tag.rs b/packages/yew-macro/src/html_tree/tag.rs index 7c492f9843f..bc3e090b54f 100644 --- a/packages/yew-macro/src/html_tree/tag.rs +++ b/packages/yew-macro/src/html_tree/tag.rs @@ -7,7 +7,7 @@ use syn::Token; /// The implementation is really silly but I couldn't find another way to do it on stable. /// This check isn't required to be fully accurate so it's not the end of the world if it breaks. fn span_eq_hack(a: &Span, b: &Span) -> bool { - format!("{:?}", a) == format!("{:?}", b) + format!("{a:?}") == format!("{b:?}") } /// Change all occurrences of span `from` to `to` in the given error. diff --git a/packages/yew-macro/src/props/prop.rs b/packages/yew-macro/src/props/prop.rs index 5ec04323ec0..ce85f3d29f8 100644 --- a/packages/yew-macro/src/props/prop.rs +++ b/packages/yew-macro/src/props/prop.rs @@ -88,9 +88,8 @@ impl Prop { syn::Error::new_spanned( &label, format!( - "`{}` doesn't have a value. (hint: set the value to `true` or `false` for \ - boolean attributes)", - label + "`{label}` doesn't have a value. (hint: set the value to `true` or `false` \ + for boolean attributes)" ), ) })?; @@ -132,8 +131,7 @@ fn parse_prop_value(input: &ParseBuffer) -> syn::Result { &expr, format!( "the property value must be either a literal or enclosed in braces. Consider \ - adding braces around your expression.: {:#?}", - exp + adding braces around your expression.: {exp:#?}" ), )), } @@ -244,7 +242,7 @@ impl PropList { if let Some(other_prop) = self.get_by_label(key) { return Err(syn::Error::new_spanned( &other_prop.label, - format!("`{}` can only be specified once", key), + format!("`{key}` can only be specified once"), )); } } diff --git a/packages/yew-macro/tests/html_macro/element-fail.stderr b/packages/yew-macro/tests/html_macro/element-fail.stderr index bce83a6b975..2673c1477e6 100644 --- a/packages/yew-macro/tests/html_macro/element-fail.stderr +++ b/packages/yew-macro/tests/html_macro/element-fail.stderr @@ -112,13 +112,13 @@ error: `ref` can only be specified once 63 | html! { }; | ^^^ -error: the tag `` is a void element and cannot have children (hint: rewrite this as ``) +error: the tag `` is a void element and cannot have children (hint: rewrite this as ``) --> tests/html_macro/element-fail.rs:66:13 | 66 | html! { }; | ^^^^^^^^^^^^^^^^^^^ -error: the tag `` is a void element and cannot have children (hint: rewrite this as ``) +error: the tag `` is a void element and cannot have children (hint: rewrite this as ``) --> tests/html_macro/element-fail.rs:68:13 | 68 | html! { }; diff --git a/packages/yew-router-macro/src/routable_derive.rs b/packages/yew-router-macro/src/routable_derive.rs index 992736e4294..76d8011f2ca 100644 --- a/packages/yew-router-macro/src/routable_derive.rs +++ b/packages/yew-router-macro/src/routable_derive.rs @@ -73,16 +73,13 @@ fn parse_variants_attributes( 0 => { return Err(syn::Error::new( variant.span(), - format!( - "{} attribute must be present on every variant", - AT_ATTR_IDENT - ), + format!("{AT_ATTR_IDENT} attribute must be present on every variant"), )) } _ => { return Err(syn::Error::new_spanned( quote! { #(#at_attrs)* }, - format!("only one {} attribute must be present", AT_ATTR_IDENT), + format!("only one {AT_ATTR_IDENT} attribute must be present"), )) } }; @@ -117,7 +114,7 @@ fn parse_variants_attributes( if not_founds.len() > 1 { return Err(syn::Error::new_spanned( quote! { #(#not_found_attrs)* }, - format!("there can only be one {}", NOT_FOUND_ATTR_IDENT), + format!("there can only be one {NOT_FOUND_ATTR_IDENT}"), )); } @@ -174,8 +171,8 @@ impl Routable { // :param -> {param} // *param -> {param} // so we can pass it to `format!("...", param)` - right = right.replace(&format!(":{}", field), &format!("{{{}}}", field)); - right = right.replace(&format!("*{}", field), &format!("{{{}}}", field)); + right = right.replace(&format!(":{field}"), &format!("{{{field}}}")); + right = right.replace(&format!("*{field}"), &format!("{{{field}}}")); } quote! { diff --git a/packages/yew-router/src/navigator.rs b/packages/yew-router/src/navigator.rs index 674cf03d1ad..48345609f83 100644 --- a/packages/yew-router/src/navigator.rs +++ b/packages/yew-router/src/navigator.rs @@ -162,7 +162,7 @@ impl Navigator { if route_s.is_empty() && route_s.is_empty() { Cow::from("/") } else { - Cow::from(format!("{}{}", base, route_s)) + Cow::from(format!("{base}{route_s}")) } } None => route_s.into(), @@ -178,7 +178,7 @@ impl Navigator { .unwrap_or(path); if !path.starts_with('/') { - path = format!("/{}", m).into(); + path = format!("/{m}").into(); } path diff --git a/packages/yew-router/src/utils.rs b/packages/yew-router/src/utils.rs index c87555ca4ff..ba356701725 100644 --- a/packages/yew-router/src/utils.rs +++ b/packages/yew-router/src/utils.rs @@ -60,7 +60,7 @@ pub fn compose_path(pathname: &str, query: &str) -> Option { let query = query.trim(); if !query.is_empty() { - Some(format!("{}?{}", pathname, query)) + Some(format!("{pathname}?{query}")) } else { Some(pathname.to_owned()) } diff --git a/packages/yew-router/tests/utils.rs b/packages/yew-router/tests/utils.rs index 3185990aba3..ee0a70eb241 100644 --- a/packages/yew-router/tests/utils.rs +++ b/packages/yew-router/tests/utils.rs @@ -33,7 +33,7 @@ pub fn link_href(selector: &str) -> String { gloo::utils::document() .query_selector(selector) .expect("Failed to run query selector") - .unwrap_or_else(|| panic!("No such link: {}", selector)) + .unwrap_or_else(|| panic!("No such link: {selector}")) .get_attribute("href") .expect("No href attribute") } diff --git a/packages/yew/src/dom_bundle/btag/mod.rs b/packages/yew/src/dom_bundle/btag/mod.rs index 8bb4b51f97e..7d2f06106db 100644 --- a/packages/yew/src/dom_bundle/btag/mod.rs +++ b/packages/yew/src/dom_bundle/btag/mod.rs @@ -311,7 +311,7 @@ mod feat_hydration { let node = fragment .pop_front() - .unwrap_or_else(|| panic!("expected element of type {}, found EOF.", tag_name)); + .unwrap_or_else(|| panic!("expected element of type {tag_name}, found EOF.")); assert_eq!( node.node_type(), diff --git a/packages/yew/src/dom_bundle/utils.rs b/packages/yew/src/dom_bundle/utils.rs index 1a66e32c8fa..b877da9002d 100644 --- a/packages/yew/src/dom_bundle/utils.rs +++ b/packages/yew/src/dom_bundle/utils.rs @@ -30,7 +30,7 @@ mod feat_hydration { .map(|m| m.tag_name().to_lowercase()) .unwrap_or_else(|| "unknown".to_owned()); - format!("{} element node", tag).into() + format!("{tag} element node").into() } Node::ATTRIBUTE_NODE => "attribute node".into(), Node::TEXT_NODE => "text node".into(), diff --git a/packages/yew/src/functional/hooks/use_prepared_state/feat_hydration.rs b/packages/yew/src/functional/hooks/use_prepared_state/feat_hydration.rs index 16609a219d3..6ca568b2cf2 100644 --- a/packages/yew/src/functional/hooks/use_prepared_state/feat_hydration.rs +++ b/packages/yew/src/functional/hooks/use_prepared_state/feat_hydration.rs @@ -75,7 +75,7 @@ where let data = data.clone(); ctx.next_prepared_state(move |_re_render, buf| -> PreparedStateBase { if let Some(buf) = buf { - let buf = format!("data:application/octet-binary;base64,{}", buf); + let buf = format!("data:application/octet-binary;base64,{buf}"); spawn_local(async move { let buf = decode_base64(&buf) diff --git a/packages/yew/src/virtual_dom/mod.rs b/packages/yew/src/virtual_dom/mod.rs index 503d6610f7f..3fa5a0fc696 100644 --- a/packages/yew/src/virtual_dom/mod.rs +++ b/packages/yew/src/virtual_dom/mod.rs @@ -101,7 +101,7 @@ mod feat_ssr_hydration { pub fn name(&self) -> Cow<'static, str> { match self { #[cfg(debug_assertions)] - Self::Component(m) => format!("Component({})", m).into(), + Self::Component(m) => format!("Component({m})").into(), #[cfg(not(debug_assertions))] Self::Component(_) => "Component".into(), Self::Suspense => "Suspense".into(), diff --git a/packages/yew/src/virtual_dom/vtag.rs b/packages/yew/src/virtual_dom/vtag.rs index 5949ae30bb3..6d066c51e0f 100644 --- a/packages/yew/src/virtual_dom/vtag.rs +++ b/packages/yew/src/virtual_dom/vtag.rs @@ -527,7 +527,7 @@ mod feat_ssr { let _ = w.write_str(">"); } else { // We don't write children of void elements nor closing tags. - debug_assert!(children.is_empty(), "{} cannot have any children!", tag); + debug_assert!(children.is_empty(), "{tag} cannot have any children!"); } } } diff --git a/tools/benchmark-ssr/src/main.rs b/tools/benchmark-ssr/src/main.rs index b0f5eb29bb7..410bbfa68cb 100644 --- a/tools/benchmark-ssr/src/main.rs +++ b/tools/benchmark-ssr/src/main.rs @@ -197,8 +197,7 @@ fn create_progress(tests: usize, rounds: usize) -> ProgressBar { ProgressStyle::default_bar() .template(&format!( "{{spinner:.green}} {{prefix}} [{{elapsed_precise}}] [{{bar:40.cyan/blue}}] round \ - {{msg}}/{}", - rounds + {{msg}}/{rounds}", )) .expect("failed to parse template") // .tick_chars("-\\|/") diff --git a/tools/changelog/src/cli.rs b/tools/changelog/src/cli.rs index 99a10b00a2e..4d1e434d3f7 100644 --- a/tools/changelog/src/cli.rs +++ b/tools/changelog/src/cli.rs @@ -72,7 +72,7 @@ impl Cli { let from_ref = match from { Some(some) => some, - None => format!("refs/tags/{}-v{}", package, latest_version), + None => format!("refs/tags/{package}-v{latest_version}"), }; (from_ref, next_version) }; diff --git a/tools/changelog/src/create_log_line.rs b/tools/changelog/src/create_log_line.rs index b18a1164120..29afafaf54c 100644 --- a/tools/changelog/src/create_log_line.rs +++ b/tools/changelog/src/create_log_line.rs @@ -19,7 +19,7 @@ pub fn create_log_line( oid: Result, token: Option, ) -> Result> { - println!("Commit oid: {:?}", oid); + println!("Commit oid: {oid:?}"); let oid = oid?; let commit = repo.find_commit(oid)?; let commit_first_line = commit @@ -69,9 +69,9 @@ pub fn create_log_line( let issue_labels = GITHUB_ISSUE_LABELS_FETCHER .lock() - .map_err(|err| anyhow!("Failed to lock GITHUB_ISSUE_LABELS_FETCHER: {}", err))? + .map_err(|err| anyhow!("Failed to lock GITHUB_ISSUE_LABELS_FETCHER: {err}"))? .fetch_issue_labels(issue_id.clone(), token) - .with_context(|| format!("Could not find GitHub labels for issue: {}", issue_id))?; + .with_context(|| format!("Could not find GitHub labels for issue: {issue_id}"))?; let is_issue_for_this_package = issue_labels .iter() diff --git a/tools/changelog/src/get_latest_version.rs b/tools/changelog/src/get_latest_version.rs index a1634877d5f..56e54be832a 100644 --- a/tools/changelog/src/get_latest_version.rs +++ b/tools/changelog/src/get_latest_version.rs @@ -5,8 +5,8 @@ use semver::{Error, Version}; use crate::yew_package::YewPackage; pub fn get_latest_version(package: &YewPackage) -> Result { - let common_tag_pattern = format!("{}-v", package); - let search_pattern = format!("{}*", common_tag_pattern); + let common_tag_pattern = format!("{package}-v"); + let search_pattern = format!("{common_tag_pattern}*"); let mut tags: Vec = Repository::open_from_env()? .tag_names(Some(&search_pattern))? diff --git a/tools/changelog/src/github_fetch.rs b/tools/changelog/src/github_fetch.rs index 7f6f07ca297..8b759da5bb6 100644 --- a/tools/changelog/src/github_fetch.rs +++ b/tools/changelog/src/github_fetch.rs @@ -10,7 +10,7 @@ pub fn github_fetch(url: &str, token: Option) -> Re thread::sleep(Duration::from_secs(1)); let mut optional_headers = HeaderMap::new(); if let Some(token) = token { - optional_headers.insert(AUTHORIZATION, format!("Bearer {}", token).parse().unwrap()); + optional_headers.insert(AUTHORIZATION, format!("Bearer {token}").parse().unwrap()); } let request_client = Client::new(); @@ -27,7 +27,7 @@ pub fn github_fetch(url: &str, token: Option) -> Re bail!("GitHub API limit reached."); } } - bail!("GitHub API request error: {}", status); + bail!("GitHub API request error: {status}"); } Ok(resp.json()?) } diff --git a/tools/changelog/src/github_issue_labels_fetcher.rs b/tools/changelog/src/github_issue_labels_fetcher.rs index 76dccf7a084..276aca39f97 100644 --- a/tools/changelog/src/github_issue_labels_fetcher.rs +++ b/tools/changelog/src/github_issue_labels_fetcher.rs @@ -26,7 +26,7 @@ impl GitHubIssueLabelsFetcher { .or_insert_with(|| match Self::inner_fetch(&issue, token) { Ok(labels) => labels, Err(err) => { - eprintln!("fetch_issue_labels Error: {}", err); + eprintln!("fetch_issue_labels Error: {err}"); None } }) @@ -34,10 +34,7 @@ impl GitHubIssueLabelsFetcher { } fn inner_fetch(q: &str, token: Option) -> Result>> { - let url = format!( - "https://api.github.com/repos/yewstack/yew/issues/{}/labels", - q, - ); + let url = format!("https://api.github.com/repos/yewstack/yew/issues/{q}/labels"); let body: Vec = github_fetch(&url, token)?; let label_names: Vec = body.into_iter().map(|label| label.name).collect(); Ok(Some(label_names)) diff --git a/tools/changelog/src/github_user_fetcher.rs b/tools/changelog/src/github_user_fetcher.rs index b6bb8944f59..0843c65194e 100644 --- a/tools/changelog/src/github_user_fetcher.rs +++ b/tools/changelog/src/github_user_fetcher.rs @@ -32,7 +32,7 @@ impl GitHubUsersFetcher { .or_insert_with(|| match Self::inner_fetch(commit, token) { Ok(value) => value, Err(err) => { - eprintln!("fetch_user_by_commit_author Error: {}", err); + eprintln!("fetch_user_by_commit_author Error: {err}"); None } }) diff --git a/tools/changelog/src/write_changelog_file.rs b/tools/changelog/src/write_changelog_file.rs index bfd615530a7..4eb95d99943 100644 --- a/tools/changelog/src/write_changelog_file.rs +++ b/tools/changelog/src/write_changelog_file.rs @@ -6,17 +6,17 @@ use anyhow::{Context, Result}; pub fn write_changelog(changelog_path: &str, version_changelog: &[u8]) -> Result<()> { let old_changelog = File::open(changelog_path) - .context(format!("could not open {} for reading", changelog_path))?; + .context(format!("could not open {changelog_path} for reading"))?; let old_changelog_reader = BufReader::new(old_changelog); - let changelog_path_new = &format!("../{}.new", changelog_path); + let changelog_path_new = &format!("../{changelog_path}.new"); let mut new_changelog = fs::OpenOptions::new() .write(true) .create(true) .truncate(true) .open(changelog_path_new) - .context(format!("could not open {} for writing", changelog_path_new))?; + .context(format!("could not open {changelog_path_new} for writing"))?; new_changelog.write_all(version_changelog)?; @@ -26,10 +26,9 @@ pub fn write_changelog(changelog_path: &str, version_changelog: &[u8]) -> Result drop(new_changelog); - fs::remove_file(changelog_path).context(format!("Could not delete {}", changelog_path))?; + fs::remove_file(changelog_path).context(format!("Could not delete {changelog_path}"))?; fs::rename(changelog_path_new, changelog_path).context(format!( - "Could not replace {} with {}", - changelog_path, changelog_path_new + "Could not replace {changelog_path} with {changelog_path_new}" ))?; Ok(()) diff --git a/tools/changelog/src/write_log_lines.rs b/tools/changelog/src/write_log_lines.rs index 12260c2460f..152dcf0735d 100644 --- a/tools/changelog/src/write_log_lines.rs +++ b/tools/changelog/src/write_log_lines.rs @@ -14,11 +14,8 @@ pub fn write_log_lines(log_lines: Vec) -> Result> { { writeln!( logs_list, - "- {message}. [[@{user}](https://github.com/{user}), [#{issue_id}](https://github.com/yewstack/yew/pull/{issue_id})]", - message = message, - user = user, - issue_id = issue_id - )?; + "- {message}. [[@{user}](https://github.com/{user}), [#{issue_id}](https://github.com/yewstack/yew/pull/{issue_id})]", + )?; } Ok(logs_list) } diff --git a/tools/website-test/build.rs b/tools/website-test/build.rs index 4f5076eaa18..45b5746cdbc 100644 --- a/tools/website-test/build.rs +++ b/tools/website-test/build.rs @@ -13,10 +13,10 @@ struct Level { fn main() { let home = env::var("CARGO_MANIFEST_DIR").unwrap(); - let pattern = format!("{}/../../website/docs/**/*.md*", home); - let base = format!("{}/../../website", home); + let pattern = format!("{home}/../../website/docs/**/*.md*"); + let base = format!("{home}/../../website"); let base = Path::new(&base).canonicalize().unwrap(); - let dir_pattern = format!("{}/../../website/docs/**", home); + let dir_pattern = format!("{home}/../../website/docs/**"); for dir in glob(&dir_pattern).unwrap() { println!("cargo:rerun-if-changed={}", dir.unwrap().display()); } @@ -63,7 +63,7 @@ impl Level { fn write_into(&self, dst: &mut String, name: &str, level: usize) -> fmt::Result { self.write_space(dst, level); let name = name.replace(|c| c == '-' || c == '.', "_"); - writeln!(dst, "pub mod {} {{", name)?; + writeln!(dst, "pub mod {name} {{")?; self.write_inner(dst, level + 1)?; @@ -92,7 +92,7 @@ impl Level { writeln!(dst, "#[doc = include_str!(r\"{}\")]", file.display())?; self.write_space(dst, level); - writeln!(dst, "pub fn {}_md() {{}}", stem)?; + writeln!(dst, "pub fn {stem}_md() {{}}")?; } Ok(()) From 65b930acb656656089bd99c317cac1edbe4083f5 Mon Sep 17 00:00:00 2001 From: Kaede Hoshikawa Date: Thu, 2 Feb 2023 02:04:43 +0900 Subject: [PATCH 30/76] Deduplicate suspensions when considering subsequent renders for suspensions (#3099) * FIx duplicate suspension. * Fix tests. * Fix tests. * Fix tests. --- packages/yew/src/suspense/component.rs | 5 ++++ packages/yew/tests/suspense.rs | 37 ++++++++++++++++++++++++++ 2 files changed, 42 insertions(+) diff --git a/packages/yew/src/suspense/component.rs b/packages/yew/src/suspense/component.rs index 163a6c3d558..6d5a8d616b3 100644 --- a/packages/yew/src/suspense/component.rs +++ b/packages/yew/src/suspense/component.rs @@ -87,6 +87,11 @@ mod feat_csr_ssr { return false; } + // If a suspension already exists, ignore it. + if self.suspensions.iter().any(|n| n == &m) { + return false; + } + self.suspensions.push(m); true diff --git a/packages/yew/tests/suspense.rs b/packages/yew/tests/suspense.rs index 10393f5fe91..fd2f642fe1f 100644 --- a/packages/yew/tests/suspense.rs +++ b/packages/yew/tests/suspense.rs @@ -786,3 +786,40 @@ async fn resume_after_unmount() { let result = obtain_result(); assert_eq!(result.as_str(), "
Content replacement
"); } + +#[wasm_bindgen_test] +async fn test_duplicate_suspension() { + use yew::html::ChildrenProps; + + #[function_component] + fn FetchingProvider(props: &ChildrenProps) -> HtmlResult { + use_future(|| async { + sleep(Duration::ZERO).await; + })?; + Ok(html! { <>{props.children.clone()} }) + } + + #[function_component] + fn Child() -> Html { + html! {
{"hello!"}
} + } + + #[function_component] + fn App() -> Html { + let fallback = Html::default(); + html! { + + + + + + } + } + + yew::Renderer::::with_root(gloo::utils::document().get_element_by_id("output").unwrap()) + .render(); + + sleep(Duration::from_millis(50)).await; + let result = obtain_result(); + assert_eq!(result.as_str(), "hello!"); +} From 8d308fb6172343a25bc6deb64b0cea661fce434c Mon Sep 17 00:00:00 2001 From: Kaede Hoshikawa Date: Thu, 2 Feb 2023 02:11:43 +0900 Subject: [PATCH 31/76] Separate PR and master size collection. (#3101) --- .github/workflows/post-size-cmp.yml | 16 ++++++++++--- .github/workflows/size-cmp.yml | 37 ++++++++++------------------- ci/collect_sizes.py | 9 ++----- ci/make_example_size_cmt.py | 19 +++++++++++---- 4 files changed, 42 insertions(+), 39 deletions(-) diff --git a/.github/workflows/post-size-cmp.yml b/.github/workflows/post-size-cmp.yml index 3baba67b990..cf2d50a7a91 100644 --- a/.github/workflows/post-size-cmp.yml +++ b/.github/workflows/post-size-cmp.yml @@ -17,14 +17,24 @@ jobs: uses: actions/checkout@v2 - if: github.event.workflow_run.event == 'pull_request' - name: Download Artifact + name: Download Artifact (master) uses: Legit-Labs/action-download-artifact@v2 with: github_token: "${{ secrets.GITHUB_TOKEN }}" workflow: size-cmp.yml run_id: ${{ github.event.workflow_run.id }} - name: size-cmp-info - path: "size-cmp-info/" + name: size-cmp-master-info + path: "size-cmp-master-info/" + + - if: github.event.workflow_run.event == 'pull_request' + name: Download Artifact (PR) + uses: Legit-Labs/action-download-artifact@v2 + with: + github_token: "${{ secrets.GITHUB_TOKEN }}" + workflow: size-cmp.yml + run_id: ${{ github.event.workflow_run.id }} + name: size-cmp-pr-info + path: "size-cmp-pr-info/" - name: Make pull request comment run: python3 ci/make_example_size_cmt.py diff --git a/.github/workflows/size-cmp.yml b/.github/workflows/size-cmp.yml index fb935523a4e..37c1c44c268 100644 --- a/.github/workflows/size-cmp.yml +++ b/.github/workflows/size-cmp.yml @@ -13,21 +13,23 @@ on: jobs: size-cmp: - name: Compare Size between master and current Pull Request + name: Collect ${{ matrix.target }} Size runs-on: ubuntu-latest + strategy: + matrix: + target: ["master", "pr"] steps: - name: Checkout master uses: actions/checkout@v3 + if: ${{ matrix.target == 'master' }} with: - repository: 'yewstack/yew' + repository: "yewstack/yew" ref: master - path: yew-master - name: Checkout pull request uses: actions/checkout@v3 - with: - path: current-pr + if: ${{ matrix.target == 'pr' }} - name: Setup toolchain uses: dtolnay/rust-toolchain@master @@ -38,42 +40,27 @@ jobs: - name: Restore Rust cache for master uses: Swatinem/rust-cache@v2 - with: - working-directory: yew-master - key: master - - - name: Restore Rust cache for current pull request - uses: Swatinem/rust-cache@v2 - with: - working-directory: current-pr - key: pr - name: Setup Trunk uses: jetli/trunk-action@v0.4.0 with: - version: 'latest' - - - name: Build master examples - run: find ./*/index.html | xargs -I '{}' trunk build --release '{}' || exit 0 - working-directory: yew-master/examples - env: - RUSTUP_TOOLCHAIN: nightly + version: "latest" - - name: Build pull request examples + - name: Build examples run: find ./*/index.html | xargs -I '{}' trunk build --release '{}' || exit 0 - working-directory: current-pr/examples + working-directory: examples env: RUSTUP_TOOLCHAIN: nightly RUSTFLAGS: --cfg nightly_yew - name: Collect size information - run: python3 current-pr/ci/collect_sizes.py + run: python3 ci/collect_sizes.py env: ISSUE_NUMBER: ${{ github.event.number }} - name: Upload Artifact uses: actions/upload-artifact@v3 with: - name: size-cmp-info + name: size-cmp-${{ matrix.target }}-info path: ".SIZE_CMP_INFO" retention-days: 1 diff --git a/ci/collect_sizes.py b/ci/collect_sizes.py index 71688b5b9a6..2f980ffc78a 100644 --- a/ci/collect_sizes.py +++ b/ci/collect_sizes.py @@ -32,15 +32,10 @@ def find_example_sizes(parent_dir: Path) -> Dict[str, int]: def main() -> None: - master_sizes = find_example_sizes(Path("yew-master")) - pr_sizes = find_example_sizes(Path("current-pr")) - - example_names = sorted(set([*master_sizes.keys(), *pr_sizes.keys()])) - - joined_sizes = [(i, [master_sizes.get(i), pr_sizes.get(i)]) for i in example_names] + sizes = find_example_sizes(Path.cwd()) size_cmp_info = { - "sizes": joined_sizes, + "sizes": sizes, "issue_number": os.environ["ISSUE_NUMBER"], } diff --git a/ci/make_example_size_cmt.py b/ci/make_example_size_cmt.py index 7be01aed28f..8171128e366 100644 --- a/ci/make_example_size_cmt.py +++ b/ci/make_example_size_cmt.py @@ -35,11 +35,22 @@ def format_diff_size( def main() -> None: - with open("size-cmp-info/.SIZE_CMP_INFO") as f: - content = json.loads(f.read()) + with open("size-cmp-pr-info/.SIZE_CMP_INFO") as f: + pr_content = json.loads(f.read()) - joined_sizes = content["sizes"] - issue_number = content["issue_number"] + with open("size-cmp-master-info/.SIZE_CMP_INFO") as f: + master_content = json.loads(f.read()) + + master_sizes: dict[str, int] = master_content["sizes"] + pr_sizes: dict[str, int] = pr_content["sizes"] + + example_names = sorted(set([*master_sizes.keys(), *pr_sizes.keys()])) + joined_sizes = [(i, [master_sizes.get(i), pr_sizes.get(i)]) for i in example_names] + + assert pr_content["issue_number"] == master_content["issue_number"], \ + "Issue number differs between master and pr?" + + issue_number = pr_content["issue_number"] lines: List[str] = [] significant_lines: List[str] = [] From 95562660611dcd418751ad85f5d46e2eb8086a8a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Johannes=20Sj=C3=B6lund?= Date: Wed, 1 Feb 2023 18:21:31 +0100 Subject: [PATCH 32/76] Improve grammar in website/docs (#3092) * Improve grammar in website/docs * Futuresolo's changes to website/docs --- website/docs/advanced-topics/how-it-works.mdx | 20 +++--- website/docs/advanced-topics/immutable.mdx | 2 +- .../docs/advanced-topics/optimizations.mdx | 22 +++--- website/docs/advanced-topics/portals.mdx | 2 +- .../advanced-topics/server-side-rendering.md | 72 +++++++++---------- .../struct-components/callbacks.mdx | 2 +- .../advanced-topics/struct-components/hoc.mdx | 6 +- .../struct-components/introduction.mdx | 10 +-- .../struct-components/lifecycle.mdx | 20 +++--- .../struct-components/properties.mdx | 10 +-- .../struct-components/scope.mdx | 4 +- website/docs/concepts/agents.mdx | 4 +- .../concepts/basic-web-technologies/css.mdx | 8 +-- .../concepts/basic-web-technologies/html.mdx | 14 ++-- .../concepts/basic-web-technologies/js.mdx | 10 +-- .../basic-web-technologies/wasm-bindgen.mdx | 45 ++++++------ .../basic-web-technologies/web-sys.mdx | 36 +++++----- website/docs/concepts/contexts.mdx | 30 ++++---- .../function-components/callbacks.mdx | 2 +- .../concepts/function-components/children.mdx | 2 +- .../function-components/communication.mdx | 2 +- .../hooks/custom-hooks.mdx | 10 +-- .../hooks/introduction.mdx | 16 ++--- .../function-components/introduction.mdx | 10 +-- .../function-components/properties.mdx | 10 +-- .../function-components/pure-components.mdx | 6 +- .../concepts/function-components/state.mdx | 2 +- website/docs/concepts/html/classes.mdx | 7 +- website/docs/concepts/html/components.mdx | 4 +- website/docs/concepts/html/elements.mdx | 12 ++-- website/docs/concepts/html/events.mdx | 16 ++--- website/docs/concepts/html/fragments.mdx | 2 +- website/docs/concepts/html/introduction.mdx | 4 +- website/docs/concepts/html/lists.mdx | 26 +++---- .../html/literals-and-expressions.mdx | 2 +- website/docs/concepts/router.mdx | 52 +++++++------- .../getting-started/build-a-sample-app.mdx | 10 +-- website/docs/getting-started/examples.mdx | 2 +- website/docs/getting-started/introduction.mdx | 14 ++-- website/docs/more/css.mdx | 4 +- website/docs/more/debugging.mdx | 4 +- website/docs/more/deployment.mdx | 12 ++-- website/docs/more/testing.mdx | 6 +- website/docs/tutorial/index.mdx | 62 ++++++++-------- 44 files changed, 307 insertions(+), 309 deletions(-) diff --git a/website/docs/advanced-topics/how-it-works.mdx b/website/docs/advanced-topics/how-it-works.mdx index 2415e5f1fda..2a281690057 100644 --- a/website/docs/advanced-topics/how-it-works.mdx +++ b/website/docs/advanced-topics/how-it-works.mdx @@ -15,25 +15,25 @@ update of `yew-macro`, the generated code will be more efficient and handle any without many (if any) modifications to the `html!` syntax. Because the `html!` macro allows you to write code in a declarative style, your UI layout code will -closely match the HTML that is generated to the page. This becomes increasingly useful as your -application gets more interactive and your codebase gets larger. Rather than manually writing the +closely match the HTML that is generated for the page. This becomes increasingly useful as your +application gets more interactive and your codebase gets larger. Rather than manually writing all of the code to manipulate the DOM yourself, the macro will handle it for you. -Using the `html!` macro can feel pretty magic, but it has nothing to hide. If you're curious about -how it works, try expanding the `html!` macro calls in your program. There's a useful command called -`cargo expand` which allows you to see the expansion of Rust macros. `cargo expand` isn't shipped with -`cargo` by default so you'll need to install it with `cargo install cargo-expand` if you haven't +Using the `html!` macro can feel pretty magical, but it has nothing to hide. If you are curious about +how it works, try expanding the `html!` macro calls in your program. There is a useful command called +`cargo expand` which allows you to see the expansion of Rust macros. `cargo expand` does not ship with +`cargo` by default so you will need to install it with `cargo install cargo-expand` if you have not already. [Rust-Analyzer](https://rust-analyzer.github.io/) also provides a mechanism for [obtaining macro output from within an IDE](https://rust-analyzer.github.io/manual.html#expand-macro-recursively). Output from the `html!` macro is often pretty terse! This is a feature: machine-generated code can -sometimes clash with other code in an application. In order to prevent issues, `proc_macro` +sometimes clash with other code in an application. To prevent issues, `proc_macro` "hygiene" is adhered to. Some examples include: 1. Instead of using `yew::` the macro generates `::yew::` to make sure that the Yew package is referenced correctly. This is also why `::alloc::vec::Vec::new()` is called instead of just `Vec::new()`. -2. Due to potential trait method name collisions, `` is used to make sure that we're +2. Due to potential trait method name collisions, `` is used to make sure that we are using members from the correct trait. ## What is a virtual DOM? @@ -43,11 +43,11 @@ for your web page. A "virtual" DOM is simply a copy of the DOM that is held in a a virtual DOM results in a higher memory overhead, but allows for batching and faster reads by avoiding or delaying the use of browser APIs. -Having a copy of the DOM in memory can be really helpful for libraries which promote the use of +Having a copy of the DOM in memory can be helpful for libraries that promote the use of declarative UIs. Rather than needing specific code for describing how the DOM should be modified in response to a user event, the library can use a generalized approach with DOM "diffing". When a Yew component is updated and wants to change how it is rendered, the Yew library will build a second copy -of the virtual DOM and directly compare to a virtual DOM which mirrors what is currently on screen. +of the virtual DOM and directly compare it to a virtual DOM which mirrors what is currently on screen. The "diff" (or difference) between the two can be broken down into incremental updates and applied in a batch with browser APIs. Once the updates are applied, the old virtual DOM copy is discarded and the new copy is saved for future diff checks. diff --git a/website/docs/advanced-topics/immutable.mdx b/website/docs/advanced-topics/immutable.mdx index 0ae35885c37..332ed94164f 100644 --- a/website/docs/advanced-topics/immutable.mdx +++ b/website/docs/advanced-topics/immutable.mdx @@ -12,7 +12,7 @@ to update a value, you must instantiate a new value. Properties, like in React, are propagated from ancestors to children. This means that the properties must live when each component is -updated. This is why properties should —ideally— be cheap to clone. In order to +updated. This is why properties should —ideally— be cheap to clone. To achieve this we usually wrap things in `Rc`. Immutable types are a great fit for holding property's values because they can diff --git a/website/docs/advanced-topics/optimizations.mdx b/website/docs/advanced-topics/optimizations.mdx index 5bf394a20bf..9aef595c93b 100644 --- a/website/docs/advanced-topics/optimizations.mdx +++ b/website/docs/advanced-topics/optimizations.mdx @@ -9,7 +9,7 @@ description: 'Make your app faster' **Note: if you're unsure about some of the terms used in this section, the Rust Book has a useful [chapter about smart pointers](https://doc.rust-lang.org/book/ch15-00-smart-pointers.html).** -In an effort to avoid cloning large amounts of data to create props when re-rendering, we can use +To avoid cloning large amounts of data to create props when re-rendering, we can use smart pointers to only clone a reference to the data instead of the data itself. If you pass references to the relevant data in your props and child components instead of the actual data you can avoid cloning any data until you need to modify it in the child component, where you can @@ -31,12 +31,12 @@ data cheaply, then it isn't worth putting it behind a smart pointer. For structu can be data-heavy like `Vec`s, `HashMap`s, and `String`s using smart pointers is likely to bring performance improvements. -This optimization works best if the values are never updated by the children, and even better, if +This optimization works best if the values are never updated by the children, and even better if they are rarely updated by parents. This makes `Rc<_>s` a good choice for wrapping property values -in for pure components. +in pure components. However, it must be noted that unless you need to clone the data yourself in the child component, -this optimization is not only useless, it also adds unnecessary cost of reference counting. Props +this optimization is not only useless, but it also adds the unnecessary cost of reference counting. Props in Yew are already reference counted and no data clones occur internally. ## View functions @@ -62,22 +62,22 @@ identical props. Yew compares the props internally and so the UI is only re-rend Arguably, the largest drawback to using Yew is the long time it takes to compile Yew apps. The time taken to compile a project seems to be related to the quantity of code passed to the `html!` macro. -This tends to not be much of an issue for smaller projects, but for larger applications it makes +This tends to not be much of an issue for smaller projects, but for larger applications, it makes sense to split code across multiple crates to minimize the amount of work the compiler has to do for each change made to the application. One possible approach is to make your main crate handle routing/page selection, and then make a -different crate for each page, where each page could be a different component, or just a big -function that produces `Html`. Code which is shared between the crates containing different parts of -the application could be stored in a separate crate which is depended on throughout the project. -In the best case scenario, you go from rebuilding all of your code on each compile to rebuilding +different crate for each page, where each page could be a different component or just a big +function that produces `Html`. Code that is shared between the crates containing different parts of +the application could be stored in a separate crate which the project depends on. +In the best-case scenario, you go from rebuilding all of your code on each compile to rebuilding only the main crate, and one of your page crates. In the worst case, where you edit something in the "common" crate, you will be right back to where you started: compiling all code that depends on that commonly shared crate, which is probably everything else. If your main crate is too heavyweight, or you want to rapidly iterate on a deeply nested page \(eg. a page that renders on top of another page\), you can use an example crate to create a simplified -implementation of the main page and render the component you are working on on top of that. +implementation of the main page and additionally render the component you are working on. ## Reducing binary sizes @@ -133,7 +133,7 @@ that require occasional attention and tweaking. Use these experimental options w ### wasm-opt -Further more it is possible to optimize size of `wasm` code. +Further, it is possible to optimize the size of `wasm` code. The Rust Wasm Book has a section about reducing the size of Wasm binaries: [Shrinking .wasm size](https://rustwasm.github.io/book/game-of-life/code-size.html) diff --git a/website/docs/advanced-topics/portals.mdx b/website/docs/advanced-topics/portals.mdx index a8dae1e80a9..3a5d1de28bd 100644 --- a/website/docs/advanced-topics/portals.mdx +++ b/website/docs/advanced-topics/portals.mdx @@ -6,7 +6,7 @@ description: 'Rendering into out-of-tree DOM nodes' ## What is a portal? Portals provide a first-class way to render children into a DOM node that exists outside the DOM hierarchy of the parent component. -`yew::create_portal(child, host)` returns a `Html` value that renders `child` not hierarchically under its parent component, +`yew::create_portal(child, host)` returns an `Html` value that renders `child` not hierarchically under its parent component, but as a child of the `host` element. ## Usage diff --git a/website/docs/advanced-topics/server-side-rendering.md b/website/docs/advanced-topics/server-side-rendering.md index b9104bed575..a9a382c6bcb 100644 --- a/website/docs/advanced-topics/server-side-rendering.md +++ b/website/docs/advanced-topics/server-side-rendering.md @@ -5,17 +5,17 @@ description: 'Render Yew on the server-side.' # Server-side Rendering -By default, Yew components render at the client side. When a viewer -visits a website, the server sends a skeleton html file without any actual +By default, Yew components render on the client side. When a viewer +visits a website, the server sends a skeleton HTML file without any actual content and a WebAssembly bundle to the browser. -Everything is rendered at the client side by the WebAssembly +Everything is rendered on the client side by the WebAssembly bundle. This is known as client-side rendering. This approach works fine for most websites, with some caveats: 1. Users will not be able to see anything until the entire WebAssembly - bundle is downloaded and initial render has completed. - This can result in poor user experience if the user is using a slow network. + bundle is downloaded and the initial render has been completed. + This can result in a poor experience for users on a slow network. 2. Some search engines do not support dynamically rendered web content and those who do usually rank dynamic websites lower in the search results. @@ -24,9 +24,9 @@ To solve these problems, we can render our website on the server side. ## How it Works Yew provides a `ServerRenderer` to render pages on the -server-side. +server side. -To render Yew components at the server-side, you can create a renderer +To render Yew components on the server side, you can create a renderer with `ServerRenderer::::new()` and call `renderer.render().await` to render `` into a `String`. @@ -66,20 +66,19 @@ for the first time. :::caution Web APIs are not available! Web APIs such as `web_sys` are not available when your component is -rendering on the server-side. +rendering on the server side. Your application will panic if you try to use them. You should isolate logics that need Web APIs in `use_effect` or -`use_effect_with_deps` as effects are not executed during server side -rendering. +`use_effect_with_deps` as effects are not executed during server-side rendering. ::: :::danger Struct Components -Whilst it's possible to use Struct Components with server-side rendering, -there's no clear boundaries between client-side safe logic like the +While it is possible to use Struct Components with server-side rendering, +there are no clear boundaries between client-side safe logic like the `use_effect` hook for function components and lifecycle events are invoked -in a different order than client side. +in a different order than the client side. In addition, Struct Components will continue to accept messages until all of its children are rendered and `destroy` method is called. Developers need to @@ -93,33 +92,32 @@ prefer function components unless you have a good reason not to. ## Data Fetching during Server-side Rendering -Data fetching is one of the difficult point with server side rendering -and hydration. +Data fetching is one of the difficult points with server-side rendering and hydration. Traditionally, when a component renders, it is instantly available -(outputs a virtual dom to be rendered). This works fine when the +(outputs a virtual DOM to be rendered). This works fine when the component does not want to fetch any data. But what happens if the component wants to fetch some data during rendering? -In the past, there's no mechanism for Yew to detect whether a component is still -fetching data. The data fetching client is responsible to implement -a solution to detect what's being requested during initial render and triggers +In the past, there was no mechanism for Yew to detect whether a component is still +fetching data. The data-fetching client is responsible to implement +a solution to detect what is being requested during the initial render and triggers a second render after requests are fulfilled. The server repeats this process until no more pending requests are added during a render before returning a response. -Not only this wastes CPU resources by repeatedly rendering components, -but the data client also needs to provide a way to make the data fetched on -the server-side available during hydration process to make sure that the -virtual dom returned by initial render is consistent with the +This not only wastes CPU resources by repeatedly rendering components, +but the data client also needs to provide a way to make the data fetched on the +server side available during the hydration process to make sure that the +virtual DOM returned by the initial render is consistent with the server-side rendered DOM tree which can be hard to implement. Yew takes a different approach by trying to solve this issue with ``. -Suspense is a special component that when used on the client-side, -provides a way to show a fallback UI while the component is fetching +Suspense is a special component that when used on the client side, provides a +way to show a fallback UI while the component is fetching data (suspended) and resumes to normal UI when the data fetching completes. -When the application is rendered on the server-side, Yew waits until a +When the application is rendered on the server side, Yew waits until a component is no longer suspended before serializing it into the string buffer. @@ -127,21 +125,21 @@ During the hydration process, elements within a `` component remains dehydrated until all of its child components are no longer suspended. -With this approach, developers can build a client-agnostic, SSR ready +With this approach, developers can build a client-agnostic, SSR-ready application with data fetching with very little effort. ## SSR Hydration Hydration is the process that connects a Yew application to the server-side generated HTML file. By default, `ServerRender` prints -hydratable html string which includes additional information to facilitate hydration. -When the `Renderer::hydrate` method is called, instead of start rendering from +hydratable HTML string which includes additional information to facilitate hydration. +When the `Renderer::hydrate` method is called, instead of starting rendering from scratch, Yew will reconcile the Virtual DOM generated by the application -with the html string generated by the server renderer. +with the HTML string generated by the server renderer. :::caution -To successfully hydrate an html representation created by the +To successfully hydrate an HTML representation created by the `ServerRenderer`, the client must produce a Virtual DOM layout that exactly matches the one used for SSR including components that do not contain any elements. If you have any component that is only useful in @@ -153,15 +151,15 @@ position of the extra component. During Hydration, components schedule 2 consecutive renders after it is created. Any effects are called after the second render completes. -It is important to make sure that the render function of the your -component is side-effect free. It should not mutate any states or trigger +It is important to make sure that the render function of your +component is free of side effects. It should not mutate any states or trigger additional renders. If your component currently mutates states or triggers -additional renders, move them into an `use_effect` hook. +additional renders, move them into a `use_effect` hook. -It's possible to use Struct Components with server-side rendering in +It is possible to use Struct Components with server-side rendering in hydration, the view function will be called multiple times before the rendered function will be called. -The DOM is considered as not connected until rendered function is called, +The DOM is considered as not connected until the rendered function is called, you should prevent any access to rendered nodes until `rendered()` method is called. @@ -190,7 +188,7 @@ Example: [ssr_router](https://github.com/yewstack/yew/tree/master/examples/ssr_r :::caution -Server-side rendering is currently experiemental. If you find a bug, please file +Server-side rendering is currently experimental. If you find a bug, please file an issue on [GitHub](https://github.com/yewstack/yew/issues/new?assignees=&labels=bug&template=bug_report.md&title=). ::: diff --git a/website/docs/advanced-topics/struct-components/callbacks.mdx b/website/docs/advanced-topics/struct-components/callbacks.mdx index 2bc611588d5..8153778f496 100644 --- a/website/docs/advanced-topics/struct-components/callbacks.mdx +++ b/website/docs/advanced-topics/struct-components/callbacks.mdx @@ -40,7 +40,7 @@ impl Component for Comp { } ``` -The function passed to `callback` must always take a parameter. For example, the `onclick` handler requires a function which takes a parameter of type `MouseEvent`. The handler can then decide what kind of message should be sent to the component. This message is scheduled for the next update loop unconditionally. +The function passed to `callback` must always take a parameter. For example, the `onclick` handler requires a function that takes a parameter of type `MouseEvent`. The handler can then decide what kind of message should be sent to the component. This message is scheduled for the next update loop unconditionally. If you need a callback that might not need to cause an update, use `batch_callback`. diff --git a/website/docs/advanced-topics/struct-components/hoc.mdx b/website/docs/advanced-topics/struct-components/hoc.mdx index 2a9487de0d3..eea2038c116 100644 --- a/website/docs/advanced-topics/struct-components/hoc.mdx +++ b/website/docs/advanced-topics/struct-components/hoc.mdx @@ -2,13 +2,13 @@ title: 'Higher Order Components' --- -There are several cases where Struct components dont directly support a feature (ex. Suspense) or require a lot of boiler plate to use the features (ex. Context). +There are several cases where Struct components do not directly support a feature (ex. Suspense) or require a lot of boilerplate code to use the features (ex. Context). -In those cases it is recommended to create function components that are higher order components. +In those cases, it is recommended to create function components that are higher-order components. ## Higher Order Components Definition -Higher Order Components are components that dont add any new Html and only wrap some other component to provide extra functionality. +Higher Order Components are components that do not add any new HTML and only wrap some other components to provide extra functionality. ### Example diff --git a/website/docs/advanced-topics/struct-components/introduction.mdx b/website/docs/advanced-topics/struct-components/introduction.mdx index 675c76be66e..311fe6ae5a1 100644 --- a/website/docs/advanced-topics/struct-components/introduction.mdx +++ b/website/docs/advanced-topics/struct-components/introduction.mdx @@ -5,22 +5,22 @@ description: 'Components in Yew' ## What are Components? -Components are the building blocks of Yew. They manage their own state and can render themselves to the DOM. +Components are the building blocks of Yew. They manage an internal state and can render elements to the DOM. Components are created by implementing the `Component` trait for a type. ## Writing Component's markup Yew uses Virtual DOM to render elements to the DOM. The Virtual DOM tree can be constructed by using the -`html!` macro. `html!` uses syntax which is similar to HTML but is not exactly the same. The rules are also -much stricter. It also provides super-powers like conditional rendering and rendering of lists using iterators. +`html!` macro. `html!` uses a syntax which is similar to HTML but is not the same. The rules are also +much stricter. It also provides superpowers like conditional rendering and rendering of lists using iterators. :::info -[Learn more about the `html!` macro, how it's used and its syntax](concepts/html/introduction.mdx) +[Learn more about the `html!` macro, how it is used and its syntax](concepts/html/introduction.mdx) ::: ## Passing data to a component -Yew components use _props_ to communicate between parent and children. A parent component may pass any data as props to +Yew components use _props_ to communicate between parents and children. A parent component may pass any data as props to its children. Props are similar to HTML attributes but any Rust type can be passed as props. :::info diff --git a/website/docs/advanced-topics/struct-components/lifecycle.mdx b/website/docs/advanced-topics/struct-components/lifecycle.mdx index fae9aa4ae0a..e9cfdbe9d2d 100644 --- a/website/docs/advanced-topics/struct-components/lifecycle.mdx +++ b/website/docs/advanced-topics/struct-components/lifecycle.mdx @@ -17,7 +17,7 @@ stages in the lifecycle of a component. ### Create When a component is created, it receives properties from its parent component and is stored within -the `Context` that's passed down to the `create` method. The properties can be used to +the `Context` that is passed down to the `create` method. The properties can be used to initialize the component's state and the "link" can be used to register callbacks or send messages to the component. ```rust @@ -137,7 +137,7 @@ impl Component for MyComponent { ``` :::tip note -Note that this lifecycle method does not require an implementation and will do nothing by default. +Note that this lifecycle method does not require implementation and will do nothing by default. ::: ### Update @@ -147,7 +147,7 @@ Communication with components happens primarily through messages which are handl based on what the message was, and determine if it needs to re-render itself. Messages can be sent by event listeners, child components, Agents, Services, or Futures. -Here's an example of what an implementation of `update` could look like: +Here is an example of what an implementation of `update` could look like: ```rust use yew::{Component, Context, html, Html}; @@ -200,8 +200,8 @@ impl Component for MyComponent { ### Changed Components may be re-rendered by their parents. When this happens, they could receive new properties -and need to re-render. This design facilitates parent to child component communication by just -changing the values of a property. There is a default implementation which re-renders the component +and need to re-render. This design facilitates parent-to-child component communication by just +changing the values of a property. There is a default implementation that re-renders the component when props are changed. ### Destroy @@ -212,8 +212,8 @@ before it is destroyed. This method is optional and does nothing by default. ### Infinite loops -Infinite loops are possible with Yew's lifecycle methods, but are only caused when trying to update -the same component after every render when that update also requests the component to be rendered. +Infinite loops are possible with Yew's lifecycle methods but are only caused when trying to update +the same component after every render, when that update also requests the component to be rendered. A simple example can be seen below: @@ -259,7 +259,7 @@ Let's run through what happens here: component needs to re-render. 7. Jump back to 2. -You can still schedule updates in the `rendered` method and it's often useful to do so, but +You can still schedule updates in the `rendered` method and it is often useful to do so, but consider how your component will terminate this loop when you do. ## Associated Types @@ -276,7 +276,7 @@ impl Component for MyComponent { ``` The `Message` type is used to send messages to a component after an event has taken place; for -example you might want to undertake some action when a user clicks a button or scrolls down the +example, you might want to undertake some action when a user clicks a button or scrolls down the page. Because components tend to have to respond to more than one event, the `Message` type will normally be an enum, where each variant is an event to be handled. @@ -301,5 +301,5 @@ enum Msg { ## Lifecycle Context -All component lifecycle methods take a context object. This object provides a reference to component's scope, which +All component lifecycle methods take a context object. This object provides a reference to the component's scope, which allows sending messages to a component and the props passed to the component. diff --git a/website/docs/advanced-topics/struct-components/properties.mdx b/website/docs/advanced-topics/struct-components/properties.mdx index f9663a81375..e1eb7bdc678 100644 --- a/website/docs/advanced-topics/struct-components/properties.mdx +++ b/website/docs/advanced-topics/struct-components/properties.mdx @@ -5,7 +5,7 @@ description: 'Parent to child communication' Properties enable child and parent components to communicate with each other. Every component has an associated properties type which describes what is passed down from the parent. -In theory this can be any type that implements the `Properties` trait, but in practice there's no +In theory, this can be any type that implements the `Properties` trait, but in practice, there is no reason for it to be anything but a struct where each field represents a property. ## Derive macro @@ -17,7 +17,7 @@ Types for which you derive `Properties` must also implement `PartialEq`. ### Field attributes When deriving `Properties`, all fields are required by default. -The following attributes allow you to give your props initial values which will be used unless they're set to another value. +The following attributes allow you to give your props initial values which will be used unless they are set to another value. :::tip Attributes aren't visible in Rustdoc generated documentation. @@ -75,7 +75,7 @@ fn create_default_link_color() -> LinkColor { pub struct LinkProps { /// The link must have a target. href: AttrValue, - /// Also notice that we're using AttrValue instead of String + /// Also notice that we are using AttrValue instead of String text: AttrValue, /// Color of the link. Defaults to `Blue`. #[prop_or_else(create_default_link_color)] @@ -83,7 +83,7 @@ pub struct LinkProps { /// The view function will not specify a size if this is None. #[prop_or_default] size: Option, - /// When the view function doesn't specify active, it defaults to true. + /// When the view function does not specify active, it defaults to true. #[prop_or(true)] active: bool, } @@ -93,7 +93,7 @@ pub struct LinkProps { The `yew::props!` macro allows you to build properties the same way the `html!` macro does it. -The macro uses the same syntax as a struct expression except that you can't use attributes or a base expression (`Foo { ..base }`). +The macro uses the same syntax as a struct expression except that you cannot use attributes or a base expression (`Foo { ..base }`). The type path can either point to the props directly (`path::to::Props`) or the associated properties of a component (`MyComp::Properties`). ```rust diff --git a/website/docs/advanced-topics/struct-components/scope.mdx b/website/docs/advanced-topics/struct-components/scope.mdx index 0a4b0551c70..db4f5974fa7 100644 --- a/website/docs/advanced-topics/struct-components/scope.mdx +++ b/website/docs/advanced-topics/struct-components/scope.mdx @@ -5,7 +5,7 @@ description: "Component's Scope" ## Component's `Scope<_>` API -The component "`Scope`" is the mechanism through which components are able to create callbacks and update themselves +The component "`Scope`" is the mechanism through which components can create callbacks and update themselves using messages. We obtain a reference to this by calling `link()` on the context object passed to the component. ### `send_message` @@ -19,7 +19,7 @@ Sends multiple messages to the component at the same time. This is similar to `send_message` but if any of the messages cause the `update` method to return `true`, the component will re-render after all messages in the batch have been processed. -If the given vector is empty, this function doesn't do anything. +If the given vector is empty, this function does nothing. ### `callback` diff --git a/website/docs/concepts/agents.mdx b/website/docs/concepts/agents.mdx index 2a21d6d8fab..dc35203fa43 100644 --- a/website/docs/concepts/agents.mdx +++ b/website/docs/concepts/agents.mdx @@ -36,7 +36,7 @@ The code can be found in the tag of the svgs. - Private - Spawn a new agent in a web worker for every new bridge. This is good for moving shared but independent behavior that communicates with the browser out of components. When - the the connected bridge is dropped, the agent will disappear. + the connected bridge is dropped, the agent will disappear. - Global \(WIP\) @@ -61,4 +61,4 @@ with other threads, so the cost is substantially higher than just calling a func ## Further reading - The [web_worker_fib](https://github.com/yewstack/yew/tree/master/examples/web_worker_fib) example shows how - components can send message to and receive message from agents. + components can send messages to and receive messages from agents. diff --git a/website/docs/concepts/basic-web-technologies/css.mdx b/website/docs/concepts/basic-web-technologies/css.mdx index d5efddc82b8..4c76748dd1c 100644 --- a/website/docs/concepts/basic-web-technologies/css.mdx +++ b/website/docs/concepts/basic-web-technologies/css.mdx @@ -1,14 +1,14 @@ --- title: 'CSS with classes!' description: 'A handy macro to handle classes' -comment: 'Keep this file as short and simple as possible. Its purpose is to ease in the reader into components in Yew instead of providing proper API docs' +comment: 'Keep this file as short and simple as possible. Its purpose is to ease the reader into components in Yew instead of providing proper API docs' --- import Tabs from '@theme/Tabs' import TabItem from '@theme/TabItem' -Yew does not natively provide a css in rust solution, but helps with styling by providing -programmatic ways to interact with the html `class` attribute. +Yew does not natively provide a CSS-in-Rust solution but helps with styling by providing +programmatic ways to interact with the HTML `class` attribute. ## Classes @@ -88,7 +88,7 @@ We will expand upon this concept in [more CSS](../../more/css). ## Inline Styles Currently Yew does not provide any special help with inline styles specified via the `styles` attribute, -but you can use it like any other html attribute: +but you can use it like any other HTML attribute: ```rust use yew::{classes, html}; diff --git a/website/docs/concepts/basic-web-technologies/html.mdx b/website/docs/concepts/basic-web-technologies/html.mdx index 8861c3f5c80..a2070935ec7 100644 --- a/website/docs/concepts/basic-web-technologies/html.mdx +++ b/website/docs/concepts/basic-web-technologies/html.mdx @@ -1,13 +1,13 @@ --- title: 'HTML with html!' description: 'Its HTML but not quite!' -comment: 'Keep this file as short and simple as possible. Its purpose is to ease in the reader into components in Yew instead of providing proper API docs' +comment: 'Keep this file as short and simple as possible. Its purpose is to ease the reader into components in Yew instead of providing proper API docs' --- import Tabs from '@theme/Tabs' import TabItem from '@theme/TabItem' -You can write expressions resembling HTML with the `html!` macro. Behind the scenes Yew turns +You can write expressions resembling HTML with the `html!` macro. Behind the scenes, Yew turns it into rust code representing the DOM to generate. ```rust @@ -19,7 +19,7 @@ let my_header: Html = html! { ``` Similar to format expressions, there is an easy way to embed values from the surrounding -context into the html by applying curly brackets: +context into the HTML by applying curly brackets: ```rust use yew::prelude::*; @@ -39,9 +39,9 @@ let combined_html: Html = html! { }; ``` -One rule major rule comes with use of `html!` - you can only return 1 wrapping node. +One major rule comes with the use of `html!` - you can only return 1 wrapping node. To render a list of multiple elements, `html!` allows fragments. Fragments are tags -without a name, that produce no html element by themselves. +without a name, that produce no HTML element by themselves. @@ -49,7 +49,7 @@ without a name, that produce no html element by themselves. ```rust , compile_fail use yew::html; -// error: only one root html element allowed +// error: only one root HTML element allowed html! {
@@ -64,7 +64,7 @@ html! { ```rust use yew::html; -// fixed: using html fragments +// fixed: using HTML fragments html! { <>
diff --git a/website/docs/concepts/basic-web-technologies/js.mdx b/website/docs/concepts/basic-web-technologies/js.mdx index bcce54f7f53..b38fcde085b 100644 --- a/website/docs/concepts/basic-web-technologies/js.mdx +++ b/website/docs/concepts/basic-web-technologies/js.mdx @@ -1,7 +1,7 @@ --- title: 'JS with RS' -description: 'Javascript with Rust' -comment: 'Keep this file as short and simple as possible. Its purpose is to ease in the reader into components in Yew instead of providing proper API docs' +description: 'JavaScript with Rust' +comment: 'Keep this file as short and simple as possible. Its purpose is to ease the reader into components in Yew instead of providing proper API docs' --- import Tabs from '@theme/Tabs' @@ -12,17 +12,17 @@ import TabItem from '@theme/TabItem' > accessible where necessary. As of today, WebAssembly is not feature-complete for DOM interactions. This means even in Yew we -sometimes rely on calling Javascript. What follows is an overview of the involved libraries. +sometimes rely on calling JavaScript. What follows is an overview of the involved libraries. ## wasm-bindgen -[`wasm-bindgen`](https://github.com/rustwasm/wasm-bindgen) is a library and tool that enables calls to javascript from rust and back to rust from javascript. +[`wasm-bindgen`](https://github.com/rustwasm/wasm-bindgen) is a library and tool that bridges calls between JavaScript and Rust functions. We highly recommend you take a look at their [documentation](https://rustwasm.github.io/docs/wasm-bindgen/) and our [quick guide](./wasm-bindgen.mdx). ## web-sys -The [`web-sys` crate](https://crates.io/crates/web-sys) provides bindings for Web APIs and allows us to write Javascript code in a rustyfied and safe way. +The [`web-sys` crate](https://crates.io/crates/web-sys) provides bindings for Web APIs and allows us to write JavaScript code in a rustyfied and safe way. Example: diff --git a/website/docs/concepts/basic-web-technologies/wasm-bindgen.mdx b/website/docs/concepts/basic-web-technologies/wasm-bindgen.mdx index 0c718c4cd9b..e34c895ca8c 100644 --- a/website/docs/concepts/basic-web-technologies/wasm-bindgen.mdx +++ b/website/docs/concepts/basic-web-technologies/wasm-bindgen.mdx @@ -14,7 +14,7 @@ Yew uses `wasm-bindgen` to interact with the browser through a number of crates: - [`wasm-bindgen-futures`](https://crates.io/crates/wasm-bindgen-futures) - [`web-sys`](https://crates.io/crates/web-sys) -This section will explore some of these crates in a high level in order to make it easier to understand +This section will explore some of these crates at a high level, to make it easier to understand and use `wasm-bindgen` APIs with Yew. For a more in-depth guide to `wasm-bindgen` and its associated crates then check out [The `wasm-bindgen` Guide](https://rustwasm.github.io/docs/wasm-bindgen/). @@ -29,14 +29,14 @@ over using `wasm-bindgen`. This crate provides many of the building blocks for the rest of the crates above. In this section we are only going to cover two main areas of the `wasm-bindgen` crate and that is the macro and some -types / traits you will see pop up again and again. +types/traits you will see pop up again and again. ### `#[wasm_bindgen]` macro The `#[wasm_bindgen]` macro provides an interface between Rust and JavaScript, providing a system -for translating between the two. Using this macro is more advanced, and you shouldn't need to reach +for translating between the two. Using this macro is more advanced, and you should not need to reach for it unless you are trying to use an external JavaScript library. The `js-sys` and `web-sys` -crates expose `wasm-bindgen` definitions for built-in Javascript types and browser APIs. +crates expose `wasm-bindgen` definitions for built-in JavaScript types and browser APIs. Let's go over a simple example of using the `#[wasm-bindgen]` macro to import some specific flavours of the [`console.log`](https://developer.mozilla.org/en-US/docs/Web/API/Console/log) function. @@ -77,11 +77,11 @@ _This example was adapted from [1.2 Using console.log of The `wasm-bindgen` Guid ### Simulating inheritance -Inheritance between JavaScript classes is a core feature of the Javascript language, and the DOM +Inheritance between JavaScript classes is a core feature of the Javascript language and the DOM (Document Object Model) is designed around it. When types are imported using `wasm-bindgen` you can also add attributes that describe their inheritance. -In Rust this inheritance is represented using the [`Deref`](https://doc.rust-lang.org/std/ops/trait.Deref.html) +In Rust, this inheritance is represented using the [`Deref`](https://doc.rust-lang.org/std/ops/trait.Deref.html) and [`AsRef`](https://doc.rust-lang.org/std/convert/trait.AsRef.html) traits. An example of this might help; so say you have three types `A`, `B`, and `C` where `C` extends `B` which in turn extends `A`. @@ -97,17 +97,17 @@ traits in the following way: These implementations allow you to call a method from `A` on an instance of `C` and to use `C` as if it was `&B` or `&A`. -Its important to note that every single type imported using `#[wasm-bindgen]` has the same root type, +It is important to note that every single type imported using `#[wasm-bindgen]` has the same root type, you can think of it as the `A` in the example above, this type is [`JsValue`](#jsvalue) which has -its own section below. +its section below. _[extends section in The `wasm-bindgen` Guide](https://rustwasm.github.io/docs/wasm-bindgen/reference/attributes/on-js-imports/extends.html)_ ### [`JsValue`](https://rustwasm.github.io/wasm-bindgen/api/wasm_bindgen/struct.JsValue.html) {#jsvalue} This is a representation of an object owned by JavaScript, this is a root catch-all type for `wasm-bindgen`. -Any type that comes from `wasm-bindgen` is a `JsValue` and this is because JavaScript doesn't have -a strong type system so any function that accepts a variable `x` doesn't define its type so `x` can be +Any type that comes from `wasm-bindgen` is a `JsValue` and this is because JavaScript does not have +a strong type system so any function that accepts a variable `x` does not define its type so `x` can be a valid JavaScript value; hence `JsValue`. If you are working with imported functions or types that accept a `JsValue`, then any imported value is _technically_ valid. @@ -119,12 +119,12 @@ _[`JsValue` documentation](https://rustwasm.github.io/wasm-bindgen/api/wasm_bind ### [`JsCast`](https://rustwasm.github.io/wasm-bindgen/api/wasm_bindgen/trait.JsCast.html) {#JsCast} -Rust has a strong type system and JavaScript...doesn't 😞. In order for Rust to maintain these -strong types but still be convenient the WebAssembly group came up with a pretty neat trait `JsCast`. +Rust has a strong type system and JavaScript...doesn't 😞. For Rust to maintain these +strong types but still be convenient, the WebAssembly group came up with a pretty neat trait `JsCast`. Its job is to help you move from one JavaScript "type" to another, which sounds vague, but it means -that if you have one type which you know is really another then you can use the functions of `JsCast` -to jump from one type to the other. It's a nice trait to get to know when working with `web-sys`, -`wasm_bindgen`, `js-sys` - you'll notice lots of types will implement `JsCast` from those crates. +that if you have one type which you know is another, then you can use the functions of `JsCast` +to jump from one type to the other. It is a nice trait to get to know when working with `web-sys`, +`wasm_bindgen`, `js-sys` - you will notice lots of types will implement `JsCast` from those crates. `JsCast` provides both checked and unchecked methods of casting - so that at runtime if you are unsure what type a certain object is you can try to cast it which returns possible failure types like @@ -132,9 +132,9 @@ unsure what type a certain object is you can try to cast it which returns possib [`Result`](https://doc.rust-lang.org/std/result/enum.Result.html). A common example of this in [`web-sys`](./web-sys.mdx) is when you are trying to get the -target of an event, you might know what the target element is but the -[`web_sys::Event`](https://rustwasm.github.io/wasm-bindgen/api/web_sys/struct.Event.html) API will always return an [`Option`](https://rustwasm.github.io/wasm-bindgen/api/web_sys/struct.Event.html#method.target) -so you will need to cast it to the element type. so you can call its methods. +target of an event. You might know what the target element is but the +[`web_sys::Event`](https://rustwasm.github.io/wasm-bindgen/api/web_sys/struct.Event.html) API will always return an [`Option`](https://rustwasm.github.io/wasm-bindgen/api/web_sys/struct.Event.html#method.target). +You will need to cast it to the element type so you can call its methods. ```rust // need to import the trait. @@ -161,7 +161,7 @@ The [`dyn_ref`](https://rustwasm.github.io/wasm-bindgen/api/wasm_bindgen/trait.J method is a checked cast that returns an `Option<&T>` which means the original type can be used again if the cast failed and thus returned `None`. The [`dyn_into`](https://rustwasm.github.io/wasm-bindgen/api/wasm_bindgen/trait.JsCast.html#method.dyn_into) -method will consume `self`, as per convention for into methods in Rust, and the type returned is +method will consume `self`, as per convention for `into` methods in Rust, and the type returned is `Result`. If the casting fails, the original `Self` value is returned in `Err`. You can try again or do something else with the original type. @@ -185,7 +185,7 @@ _[`Closure` documentation](https://rustwasm.github.io/wasm-bindgen/api/wasm_bind ## [`js-sys`](https://crates.io/crates/js-sys) -The `js-sys` crate provides bindings / imports of JavaScript's standard, built-in objects, including +The `js-sys` crate provides bindings/imports of JavaScript's standard, built-in objects, including their methods and properties. This does not include any web APIs as this is what [`web-sys`](./web-sys.mdx) is for! @@ -204,8 +204,9 @@ There are three main interfaces in this crate currently: 1. [`JsFuture`](https://rustwasm.github.io/wasm-bindgen/api/wasm_bindgen_futures/struct.JsFuture.html) - A type that is constructed with a [`Promise`](https://rustwasm.github.io/wasm-bindgen/api/js_sys/struct.Promise.html) - and can then be used as a `Future>`. This Rust future will resolve - or reject with the value coming out of the `Promise`. + and can then be used as a `Future>`. This `Future` will resolve to `Ok` if + the `Promise` is resolved and `Err` if the `Promise` is rejected, containing the resolved or rejected + value from the `Promise` respectively. 2. [`future_to_promise`](https://rustwasm.github.io/wasm-bindgen/api/wasm_bindgen_futures/fn.future_to_promise.html) - Converts a Rust `Future>` into a diff --git a/website/docs/concepts/basic-web-technologies/web-sys.mdx b/website/docs/concepts/basic-web-technologies/web-sys.mdx index 6709d41be69..daffd9ad2b6 100644 --- a/website/docs/concepts/basic-web-technologies/web-sys.mdx +++ b/website/docs/concepts/basic-web-technologies/web-sys.mdx @@ -11,18 +11,18 @@ procedurally generated from browser WebIDL which is why some names are so long a ## Features in `web-sys` -The `web-sys` crate with all of it's features enabled can add lots of bloat to a Wasm application, -in order to get around this issue most types are feature gated so that you only include the types -you require for your application. Yew includes a number of features from `web-sys` and -exposes some types in it's public API, you will often need to add `web-sys` as a dependency yourself. +The `web-sys` crate with all of its features enabled can add lots of bloat to a Wasm application. +To get around this issue most types are feature gated so that you only include the types +you require for your application. Yew enables several features from `web-sys` and +exposes some types in its public API. You will often need to add `web-sys` as a dependency yourself. ## Inheritance in `web-sys` In the [Simulating inheritance section](./wasm-bindgen.mdx#simulating-inheritance) you can read how in general Rust provides an approach to simulate inheritance in JavaScript. This is very important in -`web-sys` as understanding what methods are available on a type means understanding it's inheritance. +`web-sys` as understanding what methods are available on a type means understanding its inheritance. -This section is going to look at a specific element and list out it's inheritance using Rust by +This section is going to look at a specific element and list out its inheritance using Rust by calling [`Deref::deref`](https://doc.rust-lang.org/std/ops/trait.Deref.html#tymethod.deref) until the value is [`JsValue`](./wasm-bindgen.mdx#jsvalue): @@ -46,11 +46,11 @@ fn inheritance_of_text_area(text_area: HtmlTextAreaElement) { let event_target: &EventTarget = node.deref(); - // Notice we've moved from web-sys types now into built-in + // Notice we have moved from web-sys types now into built-in // JavaScript types which are in the js-sys crate. let object: &js_sys::Object = event_target.deref(); - // Notice we've moved from js-sys type to the root JsValue from + // Notice we have moved from js-sys type to the root JsValue from // the wasm-bindgen crate. let js_value: &wasm_bindgen::JsValue = object.deref(); @@ -79,13 +79,13 @@ _[Inheritance in `web-sys` in The `wasm-bindgen` Guide](https://rustwasm.github. ## The `Node` in `NodeRef` -Yew uses a [`NodeRef`](concepts/function-components/node-refs.mdx) in order to provide a way for keeping a reference to +Yew uses a [`NodeRef`](concepts/function-components/node-refs.mdx) to provide a way for keeping a reference to a `Node` made by the [`html!`](concepts/html/introduction.mdx) macro. The `Node` part of `NodeRef` is referring to [`web_sys::Node`](https://rustwasm.github.io/wasm-bindgen/api/web_sys/struct.Node.html). The `NodeRef::get` method will return a `Option` value, however, most of the time in Yew you want -to cast this value to a specific element so you can use it's specific methods. This casting +to cast this value to a specific element so you can use its specific methods. This casting can be done using [`JsCast`](./wasm-bindgen.mdx#JsCast) on the `Node` value, if present, but Yew -provides the `NodeRef::cast` method to perform this casting for convenience and so that you don't +provides the `NodeRef::cast` method to perform this casting for convenience and so that you do not necessarily have to include the `wasm-bindgen` dependency for the `JsCast` trait. The two code blocks below do essentially the same thing, the first is using `NodeRef::cast` and @@ -128,8 +128,8 @@ fn with_jscast(node_ref: NodeRef) { ## JavaScript example to Rust -This section is to help show that any examples that use JavaScript to interact with the Web APIs -can be adapted and written using Rust with `web-sys`. +This section demonstrates examples of how JavaScript code which interact with the +Web APIs can be rewritten with `web-sys` in Rust. ### JavaScript example @@ -191,9 +191,9 @@ Document::new() ``` This version is much more verbose, but you will probably notice part of that is because of failure -types reminding us that some of these function calls have invariants that must be held otherwise will -cause a panic in Rust. Another part of the verbosity is the calls to `JsCast` in order to cast into -different types so that you can call it's specific methods. +types reminding us that some of these function calls have invariants that must be held, or otherwise will +cause a panic in Rust. Another part of the verbosity is the calls to `JsCast` to cast into +different types so that you can call its specific methods. ### Yew example @@ -204,7 +204,7 @@ the approach above: ```toml title=Cargo.toml [dependencies.web-sys] version = "0.3" -# We need to enable the `DomRect` feature in order to use the +# We need to enable the `DomRect` feature to use the # `get_bounding_client_rect` method. features = [ "console", @@ -239,7 +239,7 @@ html! { ## External libraries `web-sys` is a raw binding to the Web API so it comes with some pain in Rust because it was not -designed with Rust or even a strong type system in mind, this is where community crates come in to +designed with Rust or even a strong type system in mind, this is where community crates provide abstractions over `web-sys` to provide more idiomatic Rust APIs. _[External libraries page](/community/external-libs)_ diff --git a/website/docs/concepts/contexts.mdx b/website/docs/concepts/contexts.mdx index a33d6587c2d..b599f81ec8a 100644 --- a/website/docs/concepts/contexts.mdx +++ b/website/docs/concepts/contexts.mdx @@ -6,16 +6,16 @@ description: 'Using contexts to pass deeply nested data' Usually, data is passed from a parent component to a child component via props. But passing props can become verbose and annoying if you have to pass them through many components in the middle, -or if many components in your app need the same information. Context solve this problem by allowing a +or if many components in your app need the same information. Context solves this problem by allowing a parent component to make data available to _any_ component in the tree below it, no matter how deep, without having to pass it down with props. ## The problem with props: "Prop Drilling" -Passing [props](./function-components/properties.mdx) is a great way to pass data directly from parent to a child. -They become cumbersome to pass down through deeply nested component tree or when multiple components share the same data. +Passing [props](./function-components/properties.mdx) is a great way to pass data directly from a parent to a child. +They become cumbersome to pass down through deeply nested component trees or when multiple components share the same data. A common solution to data sharing is lifting the data to a common ancestor and making the children take it as props. -However, this can lead to cases where the prop has to go through multiple components in order to reach the component needs it. +However, this can lead to cases where the prop has to go through multiple components to reach the component that needs it. This situation is called "Prop Drilling". Consider the following example which passes down the theme using props: @@ -84,14 +84,14 @@ fn App() -> Html { We "drill" the theme prop through `Navbar` so that it can reach `Title` and `NavButton`. It would be nice if `Title` and `NavButton`, the components that need access to the theme, can just access the theme -without having to pass it to them as prop. Contexts solve this problem by allowing a parent to pass data, theme in this case, +without having to pass it to them as a prop. Contexts solve this problem by allowing a parent to pass data, theme in this case, to its children. ## Using Contexts ### Step 1: Providing the context -A context provider is required to consume the context. `ContextProvider`, where `T` is the context struct is used as the provider. +A context provider is required to consume the context. `ContextProvider`, where `T` is the context struct used as the provider. `T` must implement `Clone` and `PartialEq`. `ContextProvider` is the component whose children will have the context available to them. The children are re-rendered when the context changes. A struct is used to define what data is to be passed. The `ContextProvider` can be used as: @@ -140,30 +140,30 @@ See [docs for use_context](https://yew-rs-api.web.app/next/yew/functional/fn.use We have 2 options to consume contexts in struct components: -- [Higher Order Components](../advanced-topics/struct-components/hoc.mdx): A higher order function component will consume the context and pass the data to the struct component which requires it. -- Consume context directly in struct component. See [example of struct component as a consumer](https://github.com/yewstack/yew/tree/master/examples/contexts/src/struct_component_subscriber.rs) +- [Higher Order Components](../advanced-topics/struct-components/hoc.mdx): A higher-order function component will consume the context and pass the data to the struct component which requires it. +- Consume context directly in the struct component. See [example of struct component as a consumer](https://github.com/yewstack/yew/tree/master/examples/contexts/src/struct_component_subscriber.rs) ## Use cases -Generally, if some data is needed by distant components in different parts of the tree, it's likely that context will help you. -Here's some examples of such cases: +Generally, if some data is needed by distant components in different parts of the tree, context will likely help you. +Here are some examples of such cases: - **Theming**: You can put a context at the top of the app that holds your app theme and use it to adjust the visual appearance, as shown in the above example. -- **Current user account**: In many cases, components need to know the current logged-in user. You can use a context to provide the current user object to the components. +- **Current user account**: In many cases, components need to know the currently logged-in user. You can use a context to provide the current user object to the components. ### Considerations to make before using contexts Contexts are very easy to use. That makes them very easy to misuse/overuse. -Just because you can use a context to share props to components multiple levels deep, doesn't mean that you should. +Just because you can use a context to share props to components multiple levels deep, does not mean that you should. For example, you may be able to extract a component and pass that component as a child to another component. For example, -you may have a `Layout` component which takes `articles` as prop and passes it down to `ArticleList` component. +you may have a `Layout` component that takes `articles` as a prop and passes it down to `ArticleList` component. You should refactor the `Layout` component to take children as props and display ` `. -## Mutating context value a child +## Mutating the context value of a child Because of Rust's ownership rules, a context cannot have a method that takes `&mut self` that can be called by children. -In order to mutate a context's value, we must combine it with a reducer. This is done by using the +To mutate a context's value, we must combine it with a reducer. This is done by using the [`use_reducer`](https://yew-rs-api.web.app/next/yew/functional/fn.use_reducer.html) hook. The [contexts example](https://github.com/yewstack/yew/tree/master/examples/contexts) demonstrates mutable contexts diff --git a/website/docs/concepts/function-components/callbacks.mdx b/website/docs/concepts/function-components/callbacks.mdx index 2c3bbf4d1ed..7e84d0f6d93 100644 --- a/website/docs/concepts/function-components/callbacks.mdx +++ b/website/docs/concepts/function-components/callbacks.mdx @@ -55,7 +55,7 @@ fn App() -> Html { Callbacks are also used to hook into DOM events. -For example here we define a callback that will be called when the user clicks the button: +For example, here we define a callback that will be called when the user clicks the button: ```rust use yew::{function_component, html, Html, Properties, Callback}; diff --git a/website/docs/concepts/function-components/children.mdx b/website/docs/concepts/function-components/children.mdx index 05e0105aa6a..5acafbf0b29 100644 --- a/website/docs/concepts/function-components/children.mdx +++ b/website/docs/concepts/function-components/children.mdx @@ -2,7 +2,7 @@ title: 'Children' --- -`Children` is a special prop type that allows you to recieve nested `Html` that is provided like html child elements. +`Children` is a special prop type that allows you to receive nested `Html` that is provided like html child elements. ```rust use yew::{function_component, html, Html, Properties, Children}; diff --git a/website/docs/concepts/function-components/communication.mdx b/website/docs/concepts/function-components/communication.mdx index 6b9c342faa8..dcd3660572a 100644 --- a/website/docs/concepts/function-components/communication.mdx +++ b/website/docs/concepts/function-components/communication.mdx @@ -4,7 +4,7 @@ title: 'Communication between components' ## Parent to child messaging -Pass data as [props](./properties) that cause a rerender, this is the way to pass messages to children. +Pass data as [props](./properties) that cause a re-render, this is the way to pass messages to children. ## Child to parent messaging diff --git a/website/docs/concepts/function-components/hooks/custom-hooks.mdx b/website/docs/concepts/function-components/hooks/custom-hooks.mdx index 0a1c2b094ce..cd0783a65ff 100644 --- a/website/docs/concepts/function-components/hooks/custom-hooks.mdx +++ b/website/docs/concepts/function-components/hooks/custom-hooks.mdx @@ -4,7 +4,7 @@ title: 'Custom Hooks' ## Defining custom Hooks -Component's stateful logic can be extracted into reusable function by creating custom Hooks. +The stateful logic of a component can be extracted into reusable functions by creating custom Hooks. Consider that we wish to create an event listener that listens to an event on the `window` object. @@ -34,13 +34,13 @@ pub fn show_storage_changed() -> Html { ``` There's one problem with this code: the logic can't be reused by another component. -If we build another component which keeps track of the an event, +If we build another component that listens to a different event, instead of copying the code, we can move the logic into a custom hook. We'll start by creating a new function called `use_event`. The `use_` prefix denotes that a function is a hook. -This function will take an event target, an event type and a callback. -All hooks must be marked by `#[hook]` to function as as hook. +This function will take an event target, an event type, and a callback. +All hooks must be marked by `#[hook]` on their function definition. ```rust use web_sys::{Event, EventTarget}; @@ -58,7 +58,7 @@ where } ``` -This is a simple hook which can be created by composing built-in hooks. For this example, we'll use the +This simple hook can be created by composing built-in hooks. For this example, we'll use the `use_effect_with_deps` hook, so an event listener can be recreated when the hook arguments change. ```rust diff --git a/website/docs/concepts/function-components/hooks/introduction.mdx b/website/docs/concepts/function-components/hooks/introduction.mdx index 7c884b6060b..461f06b0157 100644 --- a/website/docs/concepts/function-components/hooks/introduction.mdx +++ b/website/docs/concepts/function-components/hooks/introduction.mdx @@ -5,21 +5,21 @@ slug: /concepts/function-components/hooks ## Hooks -Hooks are functions that let you store state and perform side-effects. +Hooks are functions that let you store state and perform side effects. -Yew comes with a few pre-defined Hooks. You can also create your own or discover many [community made hooks](/community/awesome#hooks). +Yew comes with a few pre-defined hooks. You can also create your own or discover many [community-made hooks](/community/awesome#hooks). ## Rules of hooks 1. A hook function name always has to start with `use_` 2. Hooks can only be used in the following locations: - - Top level of a function / hook. - - Blocks inside a function / hook, given it's not already branched. - - In the condition of a top level `if` expression inside a function / hook. - - In the scrutinee of a top level `match` expression inside a function / hook. + - Top-level of a function/hook. + - Blocks inside a function/hook, given it is not already branched. + - In the condition of a top-level `if` expression inside a function/hook. + - In the scrutinee of a top-level `match` expression inside a function/hook. 3. Hooks must be called in the same order for every render. Returning early is only allowed when using [Suspense](../../suspense.mdx) -These rules are enforced by either compile time or run-time errors. +These rules are enforced by either compile-time or run-time errors. ### Pre-defined Hooks @@ -48,4 +48,4 @@ See the [Defining custom hooks](concepts/function-components/hooks/custom-hooks. ## Further reading - The React documentation has a section on [React hooks](https://reactjs.org/docs/hooks-intro.html). - These are not exactly the same as Yew's hooks, but the underlying concept is similar. + These are not the same as Yew's hooks, but the underlying concept is similar. diff --git a/website/docs/concepts/function-components/introduction.mdx b/website/docs/concepts/function-components/introduction.mdx index 994b6e94e22..8acf12b6296 100644 --- a/website/docs/concepts/function-components/introduction.mdx +++ b/website/docs/concepts/function-components/introduction.mdx @@ -3,13 +3,13 @@ title: 'Function Components' slug: /concepts/function-components --- -Lets revisit this previous statement: +Let's revisit this previous statement: > Yew centrally operates on the idea of keeping everything that a reusable piece of > UI may need in one place - rust files. We will refine this statement, by introducing the concept that will define the logic and -presentation behaviour of an application: "components". +presentation behavior of an application: "components". ## What are Components? @@ -21,7 +21,7 @@ They: - Can have their own state - Compute pieces of HTML visible to the user (DOM) -## Two flavours of Yew Components +## Two flavors of Yew Components You are currently reading about function components - the recommended way to write components when starting with Yew and when writing simple presentation logic. @@ -55,7 +55,7 @@ fn App() -> Html { When rendering, Yew will build a virtual tree of these components. It will call the view function of each (function) component to compute a virtual version (VDOM) of the DOM that you as the library user see as the `Html` type. -For the previous example this would look like this: +For the previous example, this would look like this: ```xhtml @@ -71,6 +71,6 @@ This is what we call **rendering**. :::note -Behind the scenes `Html` is just an alias for `VNode` - virtual node. +Behind the scenes, `Html` is just an alias for `VNode` - a virtual node. ::: diff --git a/website/docs/concepts/function-components/properties.mdx b/website/docs/concepts/function-components/properties.mdx index 8761b3fe6a6..320dc7a5054 100644 --- a/website/docs/concepts/function-components/properties.mdx +++ b/website/docs/concepts/function-components/properties.mdx @@ -18,9 +18,9 @@ A type has to implement the `Properties` trait before it can be used as the prop ## Reactivity -Yew checks if props have changed when reconciling the vdom during rerendering, to know if nested components needs to be rerendered. -This way Yew can be considered a very reactive framework as changes from the parent will always be propagated downwards -and the view will never be out of sync from the data coming from props/state. +Yew checks if props have changed when reconciling the Virtual DOM during re-rendering, to know if nested components need to be re-rendered. +This way Yew can be considered a very reactive framework, as changes from the parent will always be propagated downward, +and the view will never be out of sync with the data coming from props/state. :::tip @@ -102,7 +102,7 @@ fn App() -> Html { ## Derive macro field attributes When deriving `Properties` all fields are required by default. -The following attributes allow you to give your props default values which will be used when parent has not set them. +The following attributes allow you to give your props default values which will be used when the parent has not set them. :::tip Attributes aren't visible in Rustdoc generated documentation. @@ -294,7 +294,7 @@ These include, but are not limited to: See that crate to learn more. 2. Using interior mutability.
**Why is this bad?** Interior mutability (such as with `RefCell`, `Mutex`, etc.) should - _generally_ be avoided. It can cause problems with re-renders (Yew doesn't know when state has changed) + _generally_ be avoided. It can cause problems with re-renders (Yew doesn't know when the state has changed) so you may have to manually force a render. Like all things, it has its place. Use it with caution. 3. You tell us. Did you run into an edge-case you wish you knew about earlier? Feel free to create an issue or PR a fix to this documentation. diff --git a/website/docs/concepts/function-components/pure-components.mdx b/website/docs/concepts/function-components/pure-components.mdx index 4ae25155bc4..ec6285f9ab9 100644 --- a/website/docs/concepts/function-components/pure-components.mdx +++ b/website/docs/concepts/function-components/pure-components.mdx @@ -3,11 +3,11 @@ title: 'Pure Components' --- A function component is considered [pure] when the returned `Html` is deterministically derived -from its props, and its view function mutates no state or has other side-effects. +from its props when its view function does not mutate its state or has other side effects. [pure]: https://en.wikipedia.org/wiki/Pure_function -For example below is a pure component. For a given prop `is_loading` it will always result in the same `Html` without any side effects. +The example below is a pure component. For a given prop `is_loading` it will always result in the same `Html` without any side effects. ```rust use yew::{Properties, function_component, Html, html}; @@ -35,5 +35,5 @@ as a normal function returning `Html` and avoid a bit of overhead for Yew, relat ## Impure components -You might wonder if a component can be impure if it does not use any globals, since its just a function that is called every render. +You might wonder if a component can be impure if it does not use any globals, since it is just a function that is called every render. This is where the next topic comes in - [hooks](./hooks) diff --git a/website/docs/concepts/function-components/state.mdx b/website/docs/concepts/function-components/state.mdx index c4fdc713e66..316de772830 100644 --- a/website/docs/concepts/function-components/state.mdx +++ b/website/docs/concepts/function-components/state.mdx @@ -4,7 +4,7 @@ title: 'State' ## General view of how to store state -This table can be used as a guide when deciding what state storing type fits best for your use case: +This table can be used as a guide when deciding what state-storing type fits best for your use case: | Hook | Type | Rerender when? | Scope | | ------------------------ | -------------------------- | ---------------------------- | ------------------- | diff --git a/website/docs/concepts/html/classes.mdx b/website/docs/concepts/html/classes.mdx index 01e2ef3942e..a2b823ddb45 100644 --- a/website/docs/concepts/html/classes.mdx +++ b/website/docs/concepts/html/classes.mdx @@ -14,12 +14,11 @@ When pushing a string to the set, `Classes` ensures that there is one element for every class even if a single string might contain multiple classes. `Classes` can also be merged by using `Extend` (i.e. -`classes1.extend(classes2)`) or `push()` (i.e. `classes1.push(classes2)`). In -fact, anything that implements `Into` can be used to push new classes -to the set. +`classes1.extend(classes2)`) or `push()` (i.e. `classes1.push(classes2)`). +Any type that implements `Into` can be pushed onto an existing `Classes`. The macro `classes!` is a convenient macro that creates one single `Classes`. -Its input accepts a comma separated list of expressions. The only requirement +Its input accepts a comma-separated list of expressions. The only requirement is that every expression implements `Into`. diff --git a/website/docs/concepts/html/components.mdx b/website/docs/concepts/html/components.mdx index 3344a9fd85c..81cf19a0dae 100644 --- a/website/docs/concepts/html/components.mdx +++ b/website/docs/concepts/html/components.mdx @@ -55,7 +55,7 @@ html!{ ## Nested -Components can be passed children if they have a `children` field in their `Properties`. +Components can accept child components/elements if they have a `children` field in their `Properties` ```rust title="parent.rs" use yew::prelude::*; @@ -121,7 +121,7 @@ html! { ## Nested Children with Props -Nested component properties can be accessed and mutated if the containing component types its children. In the following example, the `List` component can wrap `ListItem` components. For a real world example of this pattern, check out the `yew-router` source code. For a more advanced example, check out the `nested-list` example in the main yew repository. +Nested component properties can be accessed and mutated if the containing component types its children. In the following example, the `List` component can wrap `ListItem` components. For a real-world example of this pattern, check out the `yew-router` source code. For a more advanced example, check out the `nested-list` example in the main yew repository. ```rust use std::rc::Rc; diff --git a/website/docs/concepts/html/elements.mdx b/website/docs/concepts/html/elements.mdx index 800550d7fd4..046e654957c 100644 --- a/website/docs/concepts/html/elements.mdx +++ b/website/docs/concepts/html/elements.mdx @@ -12,7 +12,7 @@ There are many reasons why you might want to create or manage DOM nodes manually when integrating with JS libraries that can cause conflicts with managed components. Using `web-sys`, you can create DOM elements and convert them into a `Node` - which can then be -used as a `Html` value using `VRef`: +used as an `Html` value using `VRef`: ```rust use web_sys::{Element, Node}; @@ -44,8 +44,8 @@ fn MyComponent() -> Html { ## Dynamic tag names -When building a higher-order component you might find yourself in a situation where the element's tag name isn't static. -For example, you might have a `Title` component which can render anything from `h1` to `h6` depending on a level prop. +When building a higher-order component you might find yourself in a situation where the element's tag name is not static. +For example, you might have a `Title` component that can render anything from `h1` to `h6` depending on a level prop. Instead of having to use a big match expression, Yew allows you to set the tag name dynamically using `@{name}` where `name` can be any expression that returns a string. @@ -75,7 +75,7 @@ html! { }; ``` -This will result in **HTML** that's functionally equivalent to this: +This will result in **HTML** that is functionally equivalent to this: ```html @@ -104,7 +104,7 @@ This will result in the following **HTML**: ## String-like attributes -But apart from a select few boolean attributes, you will probably be dealing with a lot of string-like HTML attributes and Yew has a few option for those +But apart from a select few boolean attributes, you will probably be dealing with a lot of string-like HTML attributes and Yew has a few options to pass string-like values to components. ```rust use yew::{html, virtual_dom::AttrValue}; @@ -138,7 +138,7 @@ html! { }; ``` -If the attribute is set to `None`, the attribute won't be set in the DOM. +If the attribute is set to `None`, the attribute will not be set in the DOM. ## Relevant examples diff --git a/website/docs/concepts/html/events.mdx b/website/docs/concepts/html/events.mdx index d38a2b45e6b..dea7dc559f3 100644 --- a/website/docs/concepts/html/events.mdx +++ b/website/docs/concepts/html/events.mdx @@ -16,7 +16,7 @@ below, see [Manual event listener](#manual-event-listener). :::tip All the event types mentioned in the following table are re-exported under `yew::events`. Using the types from `yew::events` makes it easier to ensure version compatibility than -if you were to manually include `web-sys` as a dependency in your crate because you won't +if you were to manually include `web-sys` as a dependency in your crate because you will not end up using a version which conflicts with the version that Yew specifies. ::: @@ -41,8 +41,8 @@ listens for `click` events. See the end of this page for a [full list of availab Events dispatched by Yew follow the virtual DOM hierarchy when bubbling up to listeners. Currently, only the bubbling phase is supported for listeners. Note that the virtual DOM hierarchy is most often, but not always, identical to the actual DOM hierarchy. The distinction is important when working with [portals](../../advanced-topics/portals.mdx) and other -more advanced techniques. The intuition for well implemented components should be that events bubble from children -to parents, so that the hierarchy in your coded `html!` is the one observed by event handlers. +more advanced techniques. The intuition for well-implemented components should be that events bubble from children +to parents. In this way the hierarchy in your coded `html!` is the one observed by event handlers. If you are not interested in event bubbling, you can turn it off by calling @@ -50,20 +50,20 @@ If you are not interested in event bubbling, you can turn it off by calling yew::set_event_bubbling(false); ``` -_before_ starting your app. This speeds up event handling, but some components may break from not receiving events they expect. +_before_ starting your app. This speeds up event handling, but some components may break from not receiving the events they expect. Use this with care! ## Event delegation It can be surprising that event listeners are _not_ directly registered on the element where they are rendered. Instead, events are delegated from the subtree root of the Yew app. Still, events are delivered in their native form, and no synthetic -form is created. This can lead to mismatches between the event you'd expect in html listeners and those showing up in Yew. +form is created. This can lead to mismatches between the event you would expect in HTML listeners and those showing up in Yew. - [`Event::current_target`] points to the Yew subtree root instead of the element the listener is added on. Use [`NodeRef`](../function-components/node-refs.mdx) if you want access to the underlying `HtmlElement`. - [`Event::event_phase`] is always [`Event::CAPTURING_PHASE`]. Internally, the event will behave as if it was in the bubbling phase, the event propagation is replayed and the event [bubbles _up_](#event-bubbling), i.e. event listeners higher up in - the virtual DOM will trigger _after_ event listeners below them. Currently, capturing listeners are not supported by Yew. + the virtual DOM will trigger _after_ event listeners below them. Currently, capturing listeners is not supported by Yew. This also means that events registered by Yew will usually fire before other event listeners. @@ -88,8 +88,8 @@ them here. Calling [`web_sys::Event::target`](https://rustwasm.github.io/wasm-bi on an event returns an optional [`web_sys::EventTarget`](https://rustwasm.github.io/wasm-bindgen/api/web_sys/struct.EventTarget.html) type, which might not seem very useful when you want to know the value of your input element. -In all the approaches below we are going to tackle the same problem, so it's clear where the approach -differs opposed to the problem at hand. +In all the approaches below we are going to tackle the same problem, so it is clear where the approach +differs as opposed to the problem at hand. **The Problem:** diff --git a/website/docs/concepts/html/fragments.mdx b/website/docs/concepts/html/fragments.mdx index 81d6672c1ba..21a6ca3388a 100644 --- a/website/docs/concepts/html/fragments.mdx +++ b/website/docs/concepts/html/fragments.mdx @@ -5,7 +5,7 @@ title: 'Fragments' import Tabs from '@theme/Tabs' import TabItem from '@theme/TabItem' -The `html!` macro always requires a single root node. In order to get around this restriction, you +The `html!` macro always requires a single root node. To get around this restriction, you can use an "empty tag" (these are also called "fragments"). diff --git a/website/docs/concepts/html/introduction.mdx b/website/docs/concepts/html/introduction.mdx index 3c5dca501dc..8886778e87d 100644 --- a/website/docs/concepts/html/introduction.mdx +++ b/website/docs/concepts/html/introduction.mdx @@ -9,7 +9,7 @@ import Tabs from '@theme/Tabs' import TabItem from '@theme/TabItem' The `html!` macro allows you to write HTML and SVG code declaratively. It is similar to JSX -(an extension to JavaScript which allows you to write HTML-like code inside of JavaScript). +(an extension to JavaScript that allows you to write HTML-like code inside of JavaScript). **Important notes** @@ -17,7 +17,7 @@ The `html!` macro allows you to write HTML and SVG code declaratively. It is sim [fragments](./fragments.mdx) or [iterators](./../html/lists.mdx)) 2. An empty `html! {}` invocation is valid and will not render anything 3. Literals must always be quoted and wrapped in braces: `html! {

{ "Hello, World" }

}` -4. The `html!` macro will make all tag names lower case. To use upper case characters (which are required for some SVG elements) use [dynamic tag names](concepts/html/elements.mdx#dynamic-tag-names): `html! { <@{"myTag"}> }` +4. The `html!` macro will make all tag names lowercase. To use upper case characters (which are required for some SVG elements) use [dynamic tag names](concepts/html/elements.mdx#dynamic-tag-names): `html! { <@{"myTag"}> }` :::note The `html!` macro can reach the default recursion limit of the compiler. If you encounter compilation errors, diff --git a/website/docs/concepts/html/lists.mdx b/website/docs/concepts/html/lists.mdx index 0b327494b7e..6dca5da6c48 100644 --- a/website/docs/concepts/html/lists.mdx +++ b/website/docs/concepts/html/lists.mdx @@ -51,11 +51,11 @@ html! { ## Keyed lists A keyed list is an optimized list that has keys on **all** children. -`key` is a special prop provided by Yew which gives an html element or component a unique identifier -which is used for optimization purposes inside Yew. +`key` is a special prop provided by Yew that gives an HTML element or component a unique identifier +that is used for optimization purposes inside Yew. :::caution -Key has to be unique only in each list, in constrast to the global uniqueness of html `id`s. It must not depend on the order of the list. +Key has to be unique only in each list, in contrast to the global uniqueness of HTML `id`s. It must not depend on the order of the list. ::: It is always recommended to add keys to lists. @@ -81,7 +81,7 @@ html! { ### Performance increases -We have [Keyed list](https://github.com/yewstack/yew/tree/master/examples/keyed_list) example that lets you test the performance improvements, but here is rough rundown: +We have [Keyed list](https://github.com/yewstack/yew/tree/master/examples/keyed_list) example that lets you test the performance improvements, but here is a rough rundown: 1. Go to [Keyed list](https://github.com/yewstack/yew/tree/master/examples/keyed_list) hosted demo 2. Add 500 elements. @@ -92,14 +92,14 @@ We have [Keyed list](https://github.com/yewstack/yew/tree/master/examples/keyed_ 7. Reverse the list. 8. Look at "The last rendering took Xms" (At the time of writing this it was ~30ms) -So just at the time of writing this, for 500 components its a x2 increase of speed. +So just at the time of writing this, for 500 components it is a 2x increase of speed. ### Detailed explanation -Usually you just need a key on every list item when you iterate and the order of data can change. +Usually, you just need a key on every list item when you iterate and the order of data can change. It's used to speed up the reconciliation process when re-rendering the list. -Without keys, lets assume you iterate through `["bob","sam","rob"]`, ending up with the html: +Without keys, assume you iterate through `["bob", "sam", "rob"]`, ending up with the HTML: ```html
My name is Bob
@@ -107,16 +107,16 @@ Without keys, lets assume you iterate through `["bob","sam","rob"]`, ending up w
My name is rob
``` -Then on the next render, if your list changed to `["bob","rob"]`, yew could delete +Then on the next render, if your list changed to `["bob", "rob"]`, yew could delete the element with id="rob" and update id="sam" to be id="rob" -If you had added a key to each element, the initial html would be the same, but after -the render with the modified list, `["bob","rob"]`, yew would just delete the second -html element and leave the rest untouched since it can use the keys to associate them. +If you had added a key to each element, the initial HTML would be the same, but after +the render with the modified list, `["bob", "rob"]`, yew would just delete the second +HTML element and leave the rest untouched since it can use the keys to associate them. If you ever encounter a bug/"feature" where you switch from one component to another but both have a div as the highest rendered element. -Yew reuses the rendered html div in those cases as an optimization. -If you need that div to be recreated instead of reused, then you can add different keys and they wont be reused +Yew reuses the rendered HTML div in those cases as an optimization. +If you need that div to be recreated instead of reused, then you can add different keys and they will not be reused. ## Further reading diff --git a/website/docs/concepts/html/literals-and-expressions.mdx b/website/docs/concepts/html/literals-and-expressions.mdx index 69b6e6f7a02..df1fa4dc3e6 100644 --- a/website/docs/concepts/html/literals-and-expressions.mdx +++ b/website/docs/concepts/html/literals-and-expressions.mdx @@ -9,7 +9,7 @@ If expressions resolve to types that implement `Display`, they will be converted String literals create `Text` nodes, which are treated as strings by the browser. Hence, even if the expression contains a `